Compare commits
966
Commits
release-1.11.0
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
49495eacfd | ||
|
|
aa1eefe02c | ||
|
|
002d14757f | ||
|
|
02e50550c6 | ||
|
|
963dd8ea18 | ||
|
|
d89aac5f0d | ||
|
|
4cb0ab12a1 | ||
|
|
c0afb7f69d | ||
|
|
4f472747b1 | ||
|
|
b607d9f590 | ||
|
|
c5a47cc5bd | ||
|
|
488c47cc68 | ||
|
|
5f9ad7d401 | ||
|
|
51725d1111 | ||
|
|
92f71eddb0 | ||
|
|
1b6f64d659 | ||
|
|
3940de9189 | ||
|
|
a0f06a70e3 | ||
|
|
3ff51c3e80 | ||
|
|
c6f04243ed | ||
|
|
af4c3cfcb3 | ||
|
|
ecb18f0b03 | ||
|
|
b78aa5ee64 | ||
|
|
56cf341d9c | ||
|
|
136a6b8865 | ||
|
|
425811f10e | ||
|
|
679a61d3a8 | ||
|
|
80b3670e1a | ||
|
|
44f4904703 | ||
|
|
fef8e5e23b | ||
|
|
a798392000 | ||
|
|
c914e89e2a | ||
|
|
0dbcd8d006 | ||
|
|
1269db9643 | ||
|
|
a901203eff | ||
|
|
d4e2591485 | ||
|
|
7ec05f657d | ||
|
|
a503186d79 | ||
|
|
7f7595f67d | ||
|
|
e331081278 | ||
|
|
08da6214b8 | ||
|
|
1be4946590 | ||
|
|
30a3151b0c | ||
|
|
51109ebb47 | ||
|
|
fcd5e26089 | ||
|
|
fa005b296f | ||
|
|
4141c384aa | ||
|
|
a25f43576e | ||
|
|
b973ccb9ab | ||
|
|
f132c89311 | ||
|
|
961158b5e3 | ||
|
|
86ec940f63 | ||
|
|
bc410696f4 | ||
|
|
8240fa7d62 | ||
|
|
7d012aa162 | ||
|
|
cd975499e8 | ||
|
|
3064a609c7 | ||
|
|
3549aa63f2 | ||
|
|
985d542c73 | ||
|
|
18c6bc3dc4 | ||
|
|
22bda2ba15 | ||
|
|
df4fdc5cfd | ||
|
|
1c2082e8bd | ||
|
|
5b39f4c876 | ||
|
|
973323ed64 | ||
|
|
78f6d54f9f | ||
|
|
8b53336594 | ||
|
|
aa40ee603e | ||
|
|
d4a1a3599b | ||
|
|
1fc11dea10 | ||
|
|
0b1e895ba4 | ||
|
|
44f22083d7 | ||
|
|
b7ced159db | ||
|
|
7140cd416c | ||
|
|
a721f1b20c | ||
|
|
8736d2cd5c | ||
|
|
09f45f51fb | ||
|
|
add971c7cb | ||
|
|
4969916f0c | ||
|
|
dc3c9eda2f | ||
|
|
d72f9c8aea | ||
|
|
5fddfab2d2 | ||
|
|
2461743991 | ||
|
|
015950a936 | ||
|
|
f38004c441 | ||
|
|
94be250af7 | ||
|
|
a35bc7693c | ||
|
|
f426a71abf | ||
|
|
73a63ea05d | ||
|
|
a407966592 | ||
|
|
73e0fc18eb | ||
|
|
e9907112b4 | ||
|
|
850cb69efd | ||
|
|
77f6bd3e75 | ||
|
|
f68374efa7 | ||
|
|
ef6cf65af5 | ||
|
|
5a9c3f9e8d | ||
|
|
32c3dce34b | ||
|
|
872d386a87 | ||
|
|
2151d93c2f | ||
|
|
7c3b4d54e3 | ||
|
|
56efe39831 | ||
|
|
5fd443cdc3 | ||
|
|
85087857ad | ||
|
|
ff6133ab49 | ||
|
|
cb1bd88191 | ||
|
|
5554fcaab4 | ||
|
|
7d7e750850 | ||
|
|
76cd89bcf1 | ||
|
|
9156d4caac | ||
|
|
065127f1e4 | ||
|
|
0b65649543 | ||
|
|
1b96fa13f5 | ||
|
|
085af2cc08 | ||
|
|
37678c92fb | ||
|
|
dedab73a68 | ||
|
|
d54d30fecb | ||
|
|
ae2b601bea | ||
|
|
6ec14dfd8c | ||
|
|
17d335d7c7 | ||
|
|
4fe3307fb2 | ||
|
|
b2b9072ecb | ||
|
|
e17e37a115 | ||
|
|
8dbd60f7d5 | ||
|
|
2ce9d8f2e8 | ||
|
|
279f847946 | ||
|
|
de1c609262 | ||
|
|
9706f75b8f | ||
|
|
50b8600c63 | ||
|
|
0934b7e112 | ||
|
|
4969d0ad54 | ||
|
|
9df216cc9d | ||
|
|
7917641ff9 | ||
|
|
eb2d85edd0 | ||
|
|
6986c2b575 | ||
|
|
a05c091507 | ||
|
|
244cec869d | ||
|
|
373af2e3df | ||
|
|
32f9f4c82a | ||
|
|
7e17b15f15 | ||
|
|
309dab8d4b | ||
|
|
3983f67e32 | ||
|
|
c67de11737 | ||
|
|
a45468c0fc | ||
|
|
f8ed0e687c | ||
|
|
35b75a2cba | ||
|
|
175c1b55cf | ||
|
|
1aeec48a1d | ||
|
|
0fe21ac6ef | ||
|
|
fd15f51d57 | ||
|
|
6230d316e1 | ||
|
|
28e9d1f267 | ||
|
|
7e2c425db2 | ||
|
|
e9092b12dc | ||
|
|
7427a6b5e3 | ||
|
|
7da55820cc | ||
|
|
3abc68be30 | ||
|
|
09ffd00153 | ||
|
|
6aa03e6774 | ||
|
|
16d4f8eff6 | ||
|
|
bac6a8fd8a | ||
|
|
fa8438ae6b | ||
|
|
571930618f | ||
|
|
9f79a9597a | ||
|
|
8b8ef3ff0d | ||
|
|
90a4152114 | ||
|
|
04ee1b4f2a | ||
|
|
54915d462b | ||
|
|
59c924bc47 | ||
|
|
00b2154e8e | ||
|
|
cd430b47a5 | ||
|
|
155b337c93 | ||
|
|
e90fe24856 | ||
|
|
50a9511f50 | ||
|
|
52204f78f9 | ||
|
|
2ae29b52fd | ||
|
|
c2ceb2b09b | ||
|
|
e7b26b7246 | ||
|
|
3af834740f | ||
|
|
4902ea2d7c | ||
|
|
4ee4b17bf5 | ||
|
|
0bdccf4aa2 | ||
|
|
e88cb95b92 | ||
|
|
24a9e940d4 | ||
|
|
72189081ca | ||
|
|
144d335538 | ||
|
|
e5669fdffc | ||
|
|
54501746a6 | ||
|
|
3fbe4db9a3 | ||
|
|
a6ce08abf7 | ||
|
|
c00fd25b71 | ||
|
|
4a00a24fff | ||
|
|
a866428a78 | ||
|
|
445e9bd8d0 | ||
|
|
e5443e5c65 | ||
|
|
e235eb34c6 | ||
|
|
66d7401378 | ||
|
|
b4aae50ce1 | ||
|
|
2b6b042a77 | ||
|
|
e4ece4881d | ||
|
|
005254dae2 | ||
|
|
504ea69cf7 | ||
|
|
4bbf80823c | ||
|
|
7d76a231b0 | ||
|
|
e54519b094 | ||
|
|
f3c355f9dd | ||
|
|
79219e26e0 | ||
|
|
d122c0d435 | ||
|
|
35d0c36560 | ||
|
|
7927f8e93d | ||
|
|
d144031940 | ||
|
|
1204d63444 | ||
|
|
5ed2186395 | ||
|
|
df1544bcee | ||
|
|
62df7bdbc1 | ||
|
|
71815bbf7d | ||
|
|
a1e255a582 | ||
|
|
6dae7eb4a5 | ||
|
|
0953a17a42 | ||
|
|
ff233bdd4c | ||
|
|
3e3b44c300 | ||
|
|
ffa31aec1c | ||
|
|
5bcb2d78a1 | ||
|
|
352788321f | ||
|
|
57e107a10e | ||
|
|
cee1ba1f24 | ||
|
|
9ff2450a56 | ||
|
|
b62593aceb | ||
|
|
d49a665484 | ||
|
|
417158b8bc | ||
|
|
7321f950df | ||
|
|
4b21f1abdd | ||
|
|
b4aaf97d8f | ||
|
|
3ef16ef8b3 | ||
|
|
34ad51b3dc | ||
|
|
1d17ea141d | ||
|
|
a7f443b80b | ||
|
|
305e5a238b | ||
|
|
9b4993ca7d | ||
|
|
c8393f8554 | ||
|
|
33af80a883 | ||
|
|
fa6de7f438 | ||
|
|
2d684efe87 | ||
|
|
2d16ed055d | ||
|
|
2954cb8d87 | ||
|
|
5035ef3473 | ||
|
|
fbc93e61c4 | ||
|
|
d83fee138a | ||
|
|
5a37b517ad | ||
|
|
5197b1a8e6 | ||
|
|
b1a777f319 | ||
|
|
3d73dee972 | ||
|
|
f10e11fb27 | ||
|
|
0af976647f | ||
|
|
61db1e1740 | ||
|
|
d3a29ff624 | ||
|
|
f16770d63d | ||
|
|
ec7b38672c | ||
|
|
a2f106c7e2 | ||
|
|
c4fec74514 | ||
|
|
77afe8e014 | ||
|
|
a7678dd0db | ||
|
|
f7a6bba24c | ||
|
|
53ee0fc0b2 | ||
|
|
f1269cc220 | ||
|
|
eff443c6ef | ||
|
|
a1a608348e | ||
|
|
c231e6f5b1 | ||
|
|
b479e7a3c1 | ||
|
|
e1a38bc370 | ||
|
|
31993dfa6b | ||
|
|
b9059aaa4c | ||
|
|
926f681a90 | ||
|
|
e4fdb87e76 | ||
|
|
e15c5a51b8 | ||
|
|
3b6d48e8d5 | ||
|
|
814ba36338 | ||
|
|
4c676b94b8 | ||
|
|
9d43b27f7a | ||
|
|
db38b59fa0 | ||
|
|
5df0241ea4 | ||
|
|
9756ee7cba | ||
|
|
6eb225cb88 | ||
|
|
f5448b3d71 | ||
|
|
b75ecf1bed | ||
|
|
96519a4019 | ||
|
|
64be1c79fa | ||
|
|
48729681ad | ||
|
|
456574145c | ||
|
|
3cb7ce90b3 | ||
|
|
6fdb4c303f | ||
|
|
fc0076ffc4 | ||
|
|
6a5938233b | ||
|
|
563ebf1769 | ||
|
|
1cab76c7b8 | ||
|
|
bd30c39d61 | ||
|
|
ffc477e705 | ||
|
|
96cd50c082 | ||
|
|
f6f920d2ba | ||
|
|
cfe5076a8b | ||
|
|
778badf63a | ||
|
|
f57505314b | ||
|
|
7c07a86369 | ||
|
|
7f409cb3c0 | ||
|
|
3b26f7e53b | ||
|
|
dda72ef321 | ||
|
|
dddb219c3e | ||
|
|
96eadf659f | ||
|
|
cde9a745a6 | ||
|
|
8495449f07 | ||
|
|
530d5c8c84 | ||
|
|
eb80f759d5 | ||
|
|
b3a9ba2b8e | ||
|
|
8760db154a | ||
|
|
48b373f6e0 | ||
|
|
76bb2afb8b | ||
|
|
b10fad38c4 | ||
|
|
5b7fd63d6d | ||
|
|
7f036c5563 | ||
|
|
518387203b | ||
|
|
116b7e5528 | ||
|
|
9bb354fa83 | ||
|
|
829c19901d | ||
|
|
2dd1c13195 | ||
|
|
beb552fb47 | ||
|
|
a6d7fa8c0c | ||
|
|
2d09ed35cf | ||
|
|
e47544ad31 | ||
|
|
5bd0f08e0d | ||
|
|
e40661d89b | ||
|
|
80306a7b5e | ||
|
|
167a2255ae | ||
|
|
e27b194c27 | ||
|
|
adc5145386 | ||
|
|
8be20cce69 | ||
|
|
d1467f5813 | ||
|
|
728ec52d21 | ||
|
|
af5ddbde4d | ||
|
|
eab0e7e289 | ||
|
|
b86bf840d1 | ||
|
|
edf9b4964d | ||
|
|
8a6feabf04 | ||
|
|
460ae98267 | ||
|
|
f0eae4b399 | ||
|
|
cb5cd96bca | ||
|
|
c374da15c5 | ||
|
|
61332bd7e8 | ||
|
|
762d3a7f66 | ||
|
|
c759a58a2d | ||
|
|
722daa3da6 | ||
|
|
9fce548044 | ||
|
|
14d05f4708 | ||
|
|
5e47c767ff | ||
|
|
f42da0e443 | ||
|
|
e24cced08d | ||
|
|
987e225614 | ||
|
|
dd9a956904 | ||
|
|
6513d0272d | ||
|
|
fc234d6d18 | ||
|
|
d76e9e0dd9 | ||
|
|
8ca57f194a | ||
|
|
5b5ef29950 | ||
|
|
622ee5cf29 | ||
|
|
619601c5e2 | ||
|
|
7e33b6a1c4 | ||
|
|
89b25572db | ||
|
|
77485ff004 | ||
|
|
22eb2de1ef | ||
|
|
46db91ef6f | ||
|
|
6abc9e3d79 | ||
|
|
9ef5e82269 | ||
|
|
455fcb7773 | ||
|
|
429432e341 | ||
|
|
843976e4f5 | ||
|
|
f8d7d77c06 | ||
|
|
96683ee668 | ||
|
|
58e37f7e99 | ||
|
|
e7fd109b53 | ||
|
|
717d8ab5e0 | ||
|
|
6f6ab4212a | ||
|
|
efe6bb1db8 | ||
|
|
c875c4e224 | ||
|
|
2f83a6e8f8 | ||
|
|
40412d8512 | ||
|
|
01e18376ef | ||
|
|
1ed6a8c67a | ||
|
|
f014396910 | ||
|
|
d66ce58510 | ||
|
|
c541e7c110 | ||
|
|
cc366710bb | ||
|
|
c88e0b4673 | ||
|
|
4a1a299b20 | ||
|
|
3044657e7a | ||
|
|
be03d00f5f | ||
|
|
1f531be3a1 | ||
|
|
251e720391 | ||
|
|
687c589949 | ||
|
|
2acd538244 | ||
|
|
f269e15c5c | ||
|
|
091d7eb897 | ||
|
|
8e32de89cf | ||
|
|
372e81d814 | ||
|
|
b2a2d36f3a | ||
|
|
e3d405f62b | ||
|
|
1361c77c4d | ||
|
|
ec4fed9321 | ||
|
|
af39146b45 | ||
|
|
812f35b26b | ||
|
|
fb11778f43 | ||
|
|
efd8db1627 | ||
|
|
5924e5b355 | ||
|
|
29836977ef | ||
|
|
6c08816416 | ||
|
|
4fed5f2850 | ||
|
|
124bc587f0 | ||
|
|
9b12f749fa | ||
|
|
148b327ffa | ||
|
|
18fa6a4db3 | ||
|
|
4c7aee827e | ||
|
|
e9078161e6 | ||
|
|
65cfeca1a1 | ||
|
|
334704df26 | ||
|
|
23f642ab23 | ||
|
|
001f281926 | ||
|
|
5ca3ab8331 | ||
|
|
ad1b28b4a9 | ||
|
|
a5b94f6819 | ||
|
|
06f44bc951 | ||
|
|
04cf298916 | ||
|
|
a7833a19bd | ||
|
|
f625681bc4 | ||
|
|
ded275d75e | ||
|
|
029d3dddd4 | ||
|
|
e032d57642 | ||
|
|
4580469122 | ||
|
|
aa99ce5a0d | ||
|
|
cb455a71fb | ||
|
|
d6fb5e3bf7 | ||
|
|
60c3602aaa | ||
|
|
e42cc2294f | ||
|
|
bb2941fcc6 | ||
|
|
a8e067ae5f | ||
|
|
7345a66cbd | ||
|
|
88295d64a7 | ||
|
|
0eb33cfa5c | ||
|
|
a7fa9b3708 | ||
|
|
bc860af087 | ||
|
|
a3580180d1 | ||
|
|
76bce79a34 | ||
|
|
f345b2ca6a | ||
|
|
797b0ad2a3 | ||
|
|
0bdaac5a14 | ||
|
|
dea0484e4d | ||
|
|
97408cae55 | ||
|
|
ccdeec888e | ||
|
|
51eeae5a55 | ||
|
|
783d00fd19 | ||
|
|
baf182e006 | ||
|
|
a5308bb992 | ||
|
|
9c1efac2a1 | ||
|
|
d7fb5e1af4 | ||
|
|
d8a5fb7ee6 | ||
|
|
01bcf8c70d | ||
|
|
d25e625364 | ||
|
|
922e0b7d80 | ||
|
|
952560d3ec | ||
|
|
12a5852e45 | ||
|
|
8fa9461cc2 | ||
|
|
7f6f9c12ad | ||
|
|
057b4e904f | ||
|
|
7ee260c549 | ||
|
|
b5fd99bbd5 | ||
|
|
0cd05c6ea9 | ||
|
|
ca0d46e95d | ||
|
|
3656c2713e | ||
|
|
13b1900717 | ||
|
|
88af49efa7 | ||
|
|
e9fb5c7bac | ||
|
|
a0ced33ac6 | ||
|
|
6f01e3dc12 | ||
|
|
5d6ba6d3b0 | ||
|
|
5fce13091d | ||
|
|
974e18ee6f | ||
|
|
e9faae170f | ||
|
|
fa87209829 | ||
|
|
3288c4deae | ||
|
|
471087fbfc | ||
|
|
9fd3fb00ff | ||
|
|
28219b169c | ||
|
|
837f2229a9 | ||
|
|
e49c6b946a | ||
|
|
f53219cdcb | ||
|
|
abad8af018 | ||
|
|
391ce627de | ||
|
|
038e392ebd | ||
|
|
2d3b36d40a | ||
|
|
50e07d1c92 | ||
|
|
48a1b11058 | ||
|
|
82a570453c | ||
|
|
a798c2f102 | ||
|
|
678c1c73de | ||
|
|
cf4f4400db | ||
|
|
1a727c27aa | ||
|
|
92f0d72507 | ||
|
|
e1ee0fa3e1 | ||
|
|
d92a270d2d | ||
|
|
2ddba26691 | ||
|
|
0bdd45085a | ||
|
|
16feffa8fa | ||
|
|
dc10c3b5e5 | ||
|
|
7b1ced0682 | ||
|
|
a08c03c5f5 | ||
|
|
23142843f7 | ||
|
|
cead3d57c9 | ||
|
|
2d4f208765 | ||
|
|
555486f408 | ||
|
|
6f1c4b3d7b | ||
|
|
8aa75fa771 | ||
|
|
c7d0bc8309 | ||
|
|
6882aa0987 | ||
|
|
2ce822ac55 | ||
|
|
95d8c7ac43 | ||
|
|
3d787f5a0d | ||
|
|
d0ba3ccc76 | ||
|
|
39a26e12d6 | ||
|
|
d9a4bbcaf2 | ||
|
|
10493e3854 | ||
|
|
750d67d809 | ||
|
|
810fb81153 | ||
|
|
fe5b7ef71e | ||
|
|
7a7231c442 | ||
|
|
f063cd25c9 | ||
|
|
2057566e4e | ||
|
|
b80a07ffe6 | ||
|
|
097f64e986 | ||
|
|
b73f27fd16 | ||
|
|
0570e2d930 | ||
|
|
ee33b34bec | ||
|
|
3d568bdda5 | ||
|
|
3f9c7fcaa3 | ||
|
|
2f2e72bae9 | ||
|
|
deaf5615f1 | ||
|
|
4f7c63d991 | ||
|
|
6f21175f57 | ||
|
|
ebedaa18c7 | ||
|
|
394a8a568c | ||
|
|
fd36851c8d | ||
|
|
0a3b403fe0 | ||
|
|
d9251171f5 | ||
|
|
4fb7039fda | ||
|
|
f1c05d4544 | ||
|
|
e3dbee4b35 | ||
|
|
b72202078d | ||
|
|
403a968d3c | ||
|
|
0194f90d0e | ||
|
|
4b4c56aff6 | ||
|
|
b495f72f1f | ||
|
|
f47d75faf3 | ||
|
|
137dcd18cc | ||
|
|
643862d8ad | ||
|
|
d1ad27e0a4 | ||
|
|
6c65a1ca35 | ||
|
|
2491710524 | ||
|
|
408471e20c | ||
|
|
544c96ed5b | ||
|
|
ec25eea8f8 | ||
|
|
bdb3b0a493 | ||
|
|
bba28fa8b2 | ||
|
|
5cd81a7848 | ||
|
|
9d697cc81c | ||
|
|
b796f7d446 | ||
|
|
ac7a126f39 | ||
|
|
356fc30125 | ||
|
|
b5401fef68 | ||
|
|
a652ae0575 | ||
|
|
9345421658 | ||
|
|
e5e46b09a1 | ||
|
|
0296d7d370 | ||
|
|
64e0945546 | ||
|
|
3a99ab6d83 | ||
|
|
ab669cad0e | ||
|
|
71140c3ca7 | ||
|
|
5ab508a01f | ||
|
|
b3bfebd796 | ||
|
|
a4e0be898b | ||
|
|
3fa7f983c6 | ||
|
|
41fe6be7d7 | ||
|
|
e38ef3be88 | ||
|
|
ad54e90f57 | ||
|
|
b0846aaf37 | ||
|
|
516940f16d | ||
|
|
d454936a0c | ||
|
|
97459e54ec | ||
|
|
1f643f71d4 | ||
|
|
a16bfcfda1 | ||
|
|
e68764c147 | ||
|
|
519beb0e52 | ||
|
|
834698cc9b | ||
|
|
9c332145b7 | ||
|
|
4408a0288b | ||
|
|
0e6aac2571 | ||
|
|
42c6f57f3c | ||
|
|
148ab827ca | ||
|
|
9c990a7b1e | ||
|
|
912db74253 | ||
|
|
4b7f9453c5 | ||
|
|
44c03643cf | ||
|
|
6b63c98ac4 | ||
|
|
386c7665f5 | ||
|
|
a4f02ef389 | ||
|
|
66366cea56 | ||
|
|
3026483ae5 | ||
|
|
90171d1061 | ||
|
|
03597a01ee | ||
|
|
09e1c64f86 | ||
|
|
0d26378919 | ||
|
|
f3eb2b7e38 | ||
|
|
e07617d6c6 | ||
|
|
6bad847991 | ||
|
|
f372c76026 | ||
|
|
26d3ab5442 | ||
|
|
6d71d901e1 | ||
|
|
88c59752c0 | ||
|
|
6f149520a1 | ||
|
|
a9b2f0495c | ||
|
|
137b6e2770 | ||
|
|
a41c3d0fb8 | ||
|
|
67174c7675 | ||
|
|
d29b143bda | ||
|
|
1d505b8e40 | ||
|
|
d9bb8412d6 | ||
|
|
671cfb7dbf | ||
|
|
0231584a60 | ||
|
|
9fbb657503 | ||
|
|
67e264834a | ||
|
|
08935483cb | ||
|
|
4052e05c29 | ||
|
|
8c4dc11539 | ||
|
|
93f08be653 | ||
|
|
79d0399dba | ||
|
|
d1a0039b97 | ||
|
|
19387c9dd5 | ||
|
|
c43b916a96 | ||
|
|
4924e0610a | ||
|
|
24683e2d6a | ||
|
|
e23cdb78e9 | ||
|
|
dfa6735236 | ||
|
|
9836817d82 | ||
|
|
83bd792e36 | ||
|
|
7a3abfec0a | ||
|
|
173dd7c7d6 | ||
|
|
63907e1bfe | ||
|
|
05cc575c65 | ||
|
|
096014a45d | ||
|
|
56070d8903 | ||
|
|
1336c4b6d1 | ||
|
|
7cafeff7bd | ||
|
|
4fa8cfe3f4 | ||
|
|
c29315dda4 | ||
|
|
0f6885405c | ||
|
|
0e0d9feefa | ||
|
|
b42fa26690 | ||
|
|
9080381758 | ||
|
|
afd902e992 | ||
|
|
dd969ed5fe | ||
|
|
25cc5777a1 | ||
|
|
91c3669f21 | ||
|
|
c0e032efe5 | ||
|
|
7274ec1864 | ||
|
|
4c9a3bb62b | ||
|
|
5b909beeec | ||
|
|
6045bf2ade | ||
|
|
fa3f444be1 | ||
|
|
3280a930bf | ||
|
|
dd7a9d29a3 | ||
|
|
3bc8fb3723 | ||
|
|
b1e9b6323a | ||
|
|
aa2e91fd69 | ||
|
|
61720589cb | ||
|
|
7735334a46 | ||
|
|
43a6712a0c | ||
|
|
71feea653b | ||
|
|
91480a4e79 | ||
|
|
760acf30e3 | ||
|
|
2d1cd6ee27 | ||
|
|
3655149a60 | ||
|
|
a2d6ee847e | ||
|
|
96ddde1235 | ||
|
|
bea621c3c3 | ||
|
|
78aa2ba440 | ||
|
|
4086e92d86 | ||
|
|
2e1346de56 | ||
|
|
8f01400b77 | ||
|
|
4556086674 | ||
|
|
e009c3d3dc | ||
|
|
7107c44188 | ||
|
|
4219e7254c | ||
|
|
644a4bea02 | ||
|
|
6c57d607c7 | ||
|
|
2cf9987ce3 | ||
|
|
96f51426e4 | ||
|
|
219af0d535 | ||
|
|
d9335595b4 | ||
|
|
9406a60c78 | ||
|
|
cdbed602b9 | ||
|
|
dd72ed19fe | ||
|
|
d0af91ead3 | ||
|
|
1547c2acc8 | ||
|
|
66d2463610 | ||
|
|
64df55449a | ||
|
|
dfa990f942 | ||
|
|
df4b8edee0 | ||
|
|
5eaa113903 | ||
|
|
72901486ba | ||
|
|
b9d2e1f62f | ||
|
|
5376968f69 | ||
|
|
15460959cb | ||
|
|
fde6af6790 | ||
|
|
b59ae848d1 | ||
|
|
f2f099fb70 | ||
|
|
1b772a9bc4 | ||
|
|
358a3f6e3e | ||
|
|
b3f3819a62 | ||
|
|
3d1dcac4c4 | ||
|
|
7df7853ea0 | ||
|
|
86add13493 | ||
|
|
191ca1f3a9 | ||
|
|
8b521aa43a | ||
|
|
b644b4fbbf | ||
|
|
fe735a6986 | ||
|
|
b1f84bf176 | ||
|
|
49c6185ae7 | ||
|
|
0320f517fd | ||
|
|
a86777edf9 | ||
|
|
548b13dc3c | ||
|
|
3727a90075 | ||
|
|
900c3f9cd5 | ||
|
|
e649993a40 | ||
|
|
59006287cd | ||
|
|
410e5f9e04 | ||
|
|
9d21db9e0a | ||
|
|
6cd3823783 | ||
|
|
28356773cb | ||
|
|
56246cdb94 | ||
|
|
cf942a5d69 | ||
|
|
7041051488 | ||
|
|
6f3f9a9e61 | ||
|
|
8d51dc50eb | ||
|
|
5126f71661 | ||
|
|
8a011b8a38 | ||
|
|
cbca6bc395 | ||
|
|
5e6a533680 | ||
|
|
4224c770a3 | ||
|
|
6386897feb | ||
|
|
bda85449f4 | ||
|
|
4348d4efed | ||
|
|
2a02723b76 | ||
|
|
0027cf4703 | ||
|
|
42ca3da579 | ||
|
|
5176726123 | ||
|
|
fae793c101 | ||
|
|
8ded48c37b | ||
|
|
830fb56728 | ||
|
|
c144d78f82 | ||
|
|
e33c2b24ca | ||
|
|
238e4745c6 | ||
|
|
0498660ea5 | ||
|
|
b53547bf01 | ||
|
|
bf66935e07 | ||
|
|
b85864c647 | ||
|
|
d5ad28dbe1 | ||
|
|
8ccdb9d56d | ||
|
|
80600e56cc | ||
|
|
733f875989 | ||
|
|
a1cc8c5519 | ||
|
|
f079775276 | ||
|
|
5f467ec04d | ||
|
|
c9044ba3dd | ||
|
|
137f67e91f | ||
|
|
3ffa237f0e | ||
|
|
25dcdc7e8b | ||
|
|
7da4a4114a | ||
|
|
af29db7ec2 | ||
|
|
073293463e | ||
|
|
0affd45b62 | ||
|
|
5d6f38c1e2 | ||
|
|
1754febbaa | ||
|
|
9e71237221 | ||
|
|
794da715d4 | ||
|
|
b007c54f29 | ||
|
|
8a422b8398 | ||
|
|
ae5e06dd35 | ||
|
|
ae1b7ad430 | ||
|
|
3c5320bf6f | ||
|
|
132059ba0c | ||
|
|
5c1b42a58d | ||
|
|
ee5e3043ce | ||
|
|
f7621f0191 | ||
|
|
c9461a9b55 | ||
|
|
ea55f1f52c | ||
|
|
0e402173c9 | ||
|
|
06519cedc3 | ||
|
|
504eb98953 | ||
|
|
43efa0a4ef | ||
|
|
d6841c040d | ||
|
|
631f4f9947 | ||
|
|
14aa11db02 | ||
|
|
25ad42aabe | ||
|
|
4517697675 | ||
|
|
2eadda6e00 | ||
|
|
28e1da21d8 | ||
|
|
0b7798b2fb | ||
|
|
f2d71f0be2 | ||
|
|
f45d5865ed | ||
|
|
7eae8de0da | ||
|
|
f64cf6b7b8 | ||
|
|
3d81736c97 | ||
|
|
2ddfdf819d | ||
|
|
100f6fbf5f | ||
|
|
c9643a2e45 | ||
|
|
4e9fe30884 | ||
|
|
4e82924686 | ||
|
|
ca3ffd90f2 | ||
|
|
2d07f12b60 | ||
|
|
aea0874c42 | ||
|
|
1d9f7c5fb2 | ||
|
|
29bc520e5b | ||
|
|
4fc151ae69 | ||
|
|
aea981dd54 | ||
|
|
4adbc9c9b2 | ||
|
|
d03d23a6e5 | ||
|
|
3fc1ab6632 | ||
|
|
f20688737a | ||
|
|
f5b4efef5f | ||
|
|
2377c8d32b | ||
|
|
58b71c9ea2 | ||
|
|
91461509de | ||
|
|
0256210376 | ||
|
|
1b4cf35958 | ||
|
|
6b74da4757 | ||
|
|
d81ae2f0bf | ||
|
|
c58f562fa2 | ||
|
|
71d4e2f742 | ||
|
|
4745746725 | ||
|
|
9a32aee22d | ||
|
|
97a467571a | ||
|
|
054a986a85 | ||
|
|
4c5650f688 | ||
|
|
3ea587050d | ||
|
|
d61d4d8e64 | ||
|
|
1b2606425c | ||
|
|
bb9216085f | ||
|
|
b4d4e6e348 | ||
|
|
e2f3978937 | ||
|
|
3e0e32ba30 | ||
|
|
183a20b40e | ||
|
|
a0dc888bf1 | ||
|
|
035a101b62 | ||
|
|
ca2952c5ef | ||
|
|
6e271e4aea | ||
|
|
dfc3675361 | ||
|
|
1a3e2a265f | ||
|
|
4848324c5f | ||
|
|
1b18723e87 | ||
|
|
25208a60a2 | ||
|
|
9ca071b6e5 | ||
|
|
7f2288476b | ||
|
|
6c8a386513 | ||
|
|
e4ffd4d715 | ||
|
|
79efd968bf | ||
|
|
aa486f165e | ||
|
|
c3792825bf | ||
|
|
d4e084a1cc | ||
|
|
5d1e4af673 | ||
|
|
bf0701daa9 | ||
|
|
51536300a1 | ||
|
|
cbf46d3f27 | ||
|
|
5a93ce1247 | ||
|
|
7cf37a18d1 | ||
|
|
b3062166a1 | ||
|
|
489ef888d9 | ||
|
|
f503588aee | ||
|
|
3c958ac47c | ||
|
|
24898650b1 | ||
|
|
64f19a9fc3 | ||
|
|
16f637fbf4 | ||
|
|
178cfacb24 | ||
|
|
dc7a0779d1 | ||
|
|
b2dda9ed83 | ||
|
|
9e3fb4ea94 | ||
|
|
075810f7a2 | ||
|
|
3b49be074d | ||
|
|
ab36804e42 | ||
|
|
ee1be03b43 | ||
|
|
e4717df71a | ||
|
|
09074c1571 | ||
|
|
319a9d19bc | ||
|
|
0570d97fb6 | ||
|
|
de34ef4e4c | ||
|
|
277e0a0168 | ||
|
|
5b43f14be9 | ||
|
|
861a75ed5d | ||
|
|
a070f33c19 | ||
|
|
40dfd4b775 | ||
|
|
6bfab0becc | ||
|
|
8aa657ee39 | ||
|
|
314adcd40e | ||
|
|
4ea61b9669 | ||
|
|
7ee2683007 | ||
|
|
6202251f09 | ||
|
|
061973710e | ||
|
|
159c9ad23e | ||
|
|
955c7f837e | ||
|
|
ff21b36e1e | ||
|
|
6204633979 | ||
|
|
2f80c2ba71 | ||
|
|
088e6ed9a8 | ||
|
|
0134d73a49 | ||
|
|
8d8b488a8d | ||
|
|
21514e0be7 | ||
|
|
47f819c3ca | ||
|
|
eb7e38dfb4 | ||
|
|
046c4d018e | ||
|
|
0e66bbd5b0 | ||
|
|
b36e55d357 | ||
|
|
aefb45469e | ||
|
|
26f9d55719 | ||
|
|
f91723cb90 | ||
|
|
5b40153003 | ||
|
|
652ec31f9f | ||
|
|
c22ce88775 | ||
|
|
29d2540622 | ||
|
|
97ff0fec11 | ||
|
|
2d924d7a97 | ||
|
|
df43ce9675 | ||
|
|
2f3e2e39cc | ||
|
|
96f4ce02a3 | ||
|
|
ce4895aae8 | ||
|
|
8d6a4f8afe | ||
|
|
56e4b1a515 | ||
|
|
efc6b36cb3 | ||
|
|
a42111b49b | ||
|
|
8d51ffdfab | ||
|
|
43cf52911a | ||
|
|
8306020a3e | ||
|
|
977cffc442 | ||
|
|
4cfd14984f | ||
|
|
f0ff512b75 | ||
|
|
155de14cd8 | ||
|
|
4ec4cd23f4 | ||
|
|
5f97ce4c70 | ||
|
|
b89480e02c | ||
|
|
22e6055c75 | ||
|
|
255323cf09 | ||
|
|
4281d2149c | ||
|
|
1008850435 | ||
|
|
355d57d90d | ||
|
|
f7902802f1 | ||
|
|
7153098229 | ||
|
|
22a2e019c4 | ||
|
|
996328bb8e | ||
|
|
5ef9f63a72 | ||
|
|
1745a405eb | ||
|
|
05e9fa23f7 | ||
|
|
9614d8c1d6 | ||
|
|
263220d2c1 |
@@ -1,43 +0,0 @@
|
||||
---
|
||||
name: Bug report
|
||||
about: Create a report to help us improve
|
||||
title: ''
|
||||
labels: 'bug'
|
||||
assignees: ''
|
||||
---
|
||||
|
||||
**Describe the bug**
|
||||
|
||||
Include a clear and concise description of what the problem is, including what
|
||||
you expected to happen, and what actually happened.
|
||||
|
||||
**Steps to reproduce the bug**
|
||||
|
||||
It's important that we are able to reproduce the problem that you are
|
||||
experiencing. Please provide all code and relevant steps to reproduce the
|
||||
problem, including your `BUILD`/`CMakeLists.txt` file and build commands. Links
|
||||
to a GitHub branch or [godbolt.org](https://godbolt.org/) that demonstrate the
|
||||
problem are also helpful.
|
||||
|
||||
**Does the bug persist in the most recent commit?**
|
||||
|
||||
We recommend using the latest commit in the master branch in your projects.
|
||||
|
||||
**What operating system and version are you using?**
|
||||
|
||||
If you are using a Linux distribution please include the name and version of the
|
||||
distribution as well.
|
||||
|
||||
**What compiler and version are you using?**
|
||||
|
||||
Please include the output of `gcc -v` or `clang -v`, or the equivalent for your
|
||||
compiler.
|
||||
|
||||
**What build system are you using?**
|
||||
|
||||
Please include the output of `bazel --version` or `cmake --version`, or the
|
||||
equivalent for your build system.
|
||||
|
||||
**Additional context**
|
||||
|
||||
Add any other context about the problem here.
|
||||
@@ -0,0 +1,53 @@
|
||||
name: Bug Report
|
||||
description: Let us know that something does not work as expected.
|
||||
title: "[Bug]: Please title this bug report"
|
||||
body:
|
||||
- type: textarea
|
||||
id: what-happened
|
||||
attributes:
|
||||
label: Describe the issue
|
||||
description: What happened, and what did you expect to happen?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: steps
|
||||
attributes:
|
||||
label: Steps to reproduce the problem
|
||||
description: It is important that we are able to reproduce the problem that you are experiencing. Please provide all code and relevant steps to reproduce the problem, including your `BUILD`/`CMakeLists.txt` file and build commands. Links to a GitHub branch or [godbolt.org](https://godbolt.org/) that demonstrate the problem are also helpful.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: version
|
||||
attributes:
|
||||
label: What version of GoogleTest are you using?
|
||||
description: Please include the output of `git rev-parse HEAD` or the GoogleTest release version number that you are using.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: os
|
||||
attributes:
|
||||
label: What operating system and version are you using?
|
||||
description: If you are using a Linux distribution please include the name and version of the distribution as well.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: compiler
|
||||
attributes:
|
||||
label: What compiler and version are you using?
|
||||
description: Please include the output of `gcc -v` or `clang -v`, or the equivalent for your compiler.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: buildsystem
|
||||
attributes:
|
||||
label: What build system are you using?
|
||||
description: Please include the output of `bazel --version` or `cmake --version`, or the equivalent for your build system.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: additional
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add any other context about the problem here.
|
||||
validations:
|
||||
required: false
|
||||
@@ -1,24 +0,0 @@
|
||||
---
|
||||
name: Feature request
|
||||
about: Propose a new feature
|
||||
title: ''
|
||||
labels: 'enhancement'
|
||||
assignees: ''
|
||||
---
|
||||
|
||||
**Does the feature exist in the most recent commit?**
|
||||
|
||||
We recommend using the latest commit from GitHub in your projects.
|
||||
|
||||
**Why do we need this feature?**
|
||||
|
||||
Ideally, explain why a combination of existing features cannot be used instead.
|
||||
|
||||
**Describe the proposal**
|
||||
|
||||
Include a detailed description of the feature, with usage examples.
|
||||
|
||||
**Is the feature specific to an operating system, compiler, or build system version?**
|
||||
|
||||
If it is, please specify which versions.
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
name: Feature request
|
||||
description: Propose a new feature.
|
||||
title: "[FR]: Please title this feature request"
|
||||
labels: "enhancement"
|
||||
body:
|
||||
- type: textarea
|
||||
id: version
|
||||
attributes:
|
||||
label: Does the feature exist in the most recent commit?
|
||||
description: We recommend using the latest commit from GitHub in your projects.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: why
|
||||
attributes:
|
||||
label: Why do we need this feature?
|
||||
description: Ideally, explain why a combination of existing features cannot be used instead.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: proposal
|
||||
attributes:
|
||||
label: Describe the proposal.
|
||||
description: Include a detailed description of the feature, with usage examples.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: platform
|
||||
attributes:
|
||||
label: Is the feature specific to an operating system, compiler, or build system version?
|
||||
description: If it is, please specify which versions.
|
||||
validations:
|
||||
required: true
|
||||
@@ -1 +1,5 @@
|
||||
blank_issues_enabled: false
|
||||
contact_links:
|
||||
- name: Get Help
|
||||
url: https://github.com/google/googletest/discussions
|
||||
about: Please ask and answer questions here.
|
||||
|
||||
@@ -8,6 +8,7 @@ bazel-genfiles
|
||||
bazel-googletest
|
||||
bazel-out
|
||||
bazel-testlogs
|
||||
MODULE.bazel.lock
|
||||
# python
|
||||
*.pyc
|
||||
|
||||
@@ -24,6 +25,10 @@ Win32-Release/
|
||||
x64-Debug/
|
||||
x64-Release/
|
||||
|
||||
# VSCode files
|
||||
.cache/
|
||||
cmake-variants.yaml
|
||||
|
||||
# Ignore autoconf / automake files
|
||||
Makefile.in
|
||||
aclocal.m4
|
||||
|
||||
+66
-7
@@ -38,11 +38,32 @@ licenses(["notice"])
|
||||
|
||||
exports_files(["LICENSE"])
|
||||
|
||||
config_setting(
|
||||
name = "qnx",
|
||||
constraint_values = ["@platforms//os:qnx"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "windows",
|
||||
constraint_values = ["@platforms//os:windows"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "freebsd",
|
||||
constraint_values = ["@platforms//os:freebsd"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "openbsd",
|
||||
constraint_values = ["@platforms//os:openbsd"],
|
||||
)
|
||||
|
||||
# NOTE: Fuchsia is not an officially supported platform.
|
||||
config_setting(
|
||||
name = "fuchsia",
|
||||
constraint_values = ["@platforms//os:fuchsia"],
|
||||
)
|
||||
|
||||
config_setting(
|
||||
name = "msvc_compiler",
|
||||
flag_values = {
|
||||
@@ -64,6 +85,10 @@ cc_library(
|
||||
)
|
||||
|
||||
# Google Test including Google Mock
|
||||
|
||||
# For an actual test, use `gtest` and also `gtest_main` if you depend on gtest's
|
||||
# main(). For a library, use `gtest_for_library` instead if the library can be
|
||||
# testonly.
|
||||
cc_library(
|
||||
name = "gtest",
|
||||
srcs = glob(
|
||||
@@ -86,6 +111,7 @@ cc_library(
|
||||
"googlemock/include/gmock/*.h",
|
||||
]),
|
||||
copts = select({
|
||||
":qnx": [],
|
||||
":windows": [],
|
||||
"//conditions:default": ["-pthread"],
|
||||
}),
|
||||
@@ -104,23 +130,55 @@ cc_library(
|
||||
"googletest/include",
|
||||
],
|
||||
linkopts = select({
|
||||
":qnx": ["-lregex"],
|
||||
":windows": [],
|
||||
":freebsd": [
|
||||
"-lm",
|
||||
"-pthread",
|
||||
],
|
||||
":openbsd": [
|
||||
"-lm",
|
||||
"-pthread",
|
||||
],
|
||||
"//conditions:default": ["-pthread"],
|
||||
}),
|
||||
deps = select({
|
||||
":has_absl": [
|
||||
"@com_google_absl//absl/debugging:failure_signal_handler",
|
||||
"@com_google_absl//absl/debugging:stacktrace",
|
||||
"@com_google_absl//absl/debugging:symbolize",
|
||||
"@com_google_absl//absl/strings",
|
||||
"@com_google_absl//absl/types:any",
|
||||
"@com_google_absl//absl/types:optional",
|
||||
"@com_google_absl//absl/types:variant",
|
||||
"@abseil-cpp//absl/container:flat_hash_set",
|
||||
"@abseil-cpp//absl/debugging:failure_signal_handler",
|
||||
"@abseil-cpp//absl/debugging:stacktrace",
|
||||
"@abseil-cpp//absl/debugging:symbolize",
|
||||
"@abseil-cpp//absl/flags:flag",
|
||||
"@abseil-cpp//absl/flags:parse",
|
||||
"@abseil-cpp//absl/flags:reflection",
|
||||
"@abseil-cpp//absl/flags:usage",
|
||||
"@abseil-cpp//absl/strings",
|
||||
"@re2",
|
||||
],
|
||||
"//conditions:default": [],
|
||||
}) + select({
|
||||
# `gtest-death-test.cc` has `EXPECT_DEATH` that spawns a process,
|
||||
# expects it to crash and inspects its logs with the given matcher,
|
||||
# so that's why these libraries are needed.
|
||||
# Otherwise, builds targeting Fuchsia would fail to compile.
|
||||
":fuchsia": [
|
||||
"@fuchsia_sdk//pkg/fdio",
|
||||
"@fuchsia_sdk//pkg/zx",
|
||||
],
|
||||
"//conditions:default": [],
|
||||
}),
|
||||
)
|
||||
|
||||
# `gtest`, but testonly. See guidance on `gtest` for when to use this.
|
||||
alias(
|
||||
name = "gtest_for_library",
|
||||
testonly = True,
|
||||
actual = ":gtest",
|
||||
)
|
||||
|
||||
# Implements main() for tests using gtest. Prefer to depend on `gtest` as well
|
||||
# to ensure compliance with the layering_check Bazel feature where only the
|
||||
# direct hdrs values are available.
|
||||
cc_library(
|
||||
name = "gtest_main",
|
||||
srcs = ["googlemock/src/gmock_main.cc"],
|
||||
@@ -129,6 +187,7 @@ cc_library(
|
||||
"//conditions:default": [],
|
||||
}),
|
||||
deps = [":gtest"],
|
||||
alwayslink = True,
|
||||
)
|
||||
|
||||
# The following rules build samples of how to use gTest.
|
||||
|
||||
+15
-11
@@ -1,19 +1,13 @@
|
||||
# Note: CMake support is community-based. The maintainers do not use CMake
|
||||
# internally.
|
||||
|
||||
cmake_minimum_required(VERSION 2.8.12)
|
||||
|
||||
if (POLICY CMP0048)
|
||||
cmake_policy(SET CMP0048 NEW)
|
||||
endif (POLICY CMP0048)
|
||||
cmake_minimum_required(VERSION 3.16)
|
||||
|
||||
project(googletest-distribution)
|
||||
set(GOOGLETEST_VERSION 1.11.0)
|
||||
set(GOOGLETEST_VERSION 1.18.0)
|
||||
|
||||
if (CMAKE_VERSION VERSION_GREATER "3.0.2")
|
||||
if(NOT CYGWIN AND NOT MSYS AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL QNX)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
endif()
|
||||
if(NOT CYGWIN AND NOT MSYS AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL QNX)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
endif()
|
||||
|
||||
enable_testing()
|
||||
@@ -21,9 +15,19 @@ enable_testing()
|
||||
include(CMakeDependentOption)
|
||||
include(GNUInstallDirs)
|
||||
|
||||
#Note that googlemock target already builds googletest
|
||||
# Note that googlemock target already builds googletest.
|
||||
option(BUILD_GMOCK "Builds the googlemock subproject" ON)
|
||||
option(INSTALL_GTEST "Enable installation of googletest. (Projects embedding googletest may want to turn this OFF.)" ON)
|
||||
option(GTEST_HAS_ABSL "Use Abseil and RE2. Requires Abseil and RE2 to be separately added to the build." OFF)
|
||||
|
||||
if(GTEST_HAS_ABSL)
|
||||
if(NOT TARGET absl::base)
|
||||
find_package(absl REQUIRED)
|
||||
endif()
|
||||
if(NOT TARGET re2::re2)
|
||||
find_package(re2 REQUIRED)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(BUILD_GMOCK)
|
||||
add_subdirectory( googlemock )
|
||||
|
||||
+29
-18
@@ -21,8 +21,8 @@ accept your pull requests.
|
||||
|
||||
## Are you a Googler?
|
||||
|
||||
If you are a Googler, please make an attempt to submit an internal change rather
|
||||
than a GitHub Pull Request. If you are not able to submit an internal change a
|
||||
If you are a Googler, please make an attempt to submit an internal contribution
|
||||
rather than a GitHub Pull Request. If you are not able to submit internally, a
|
||||
PR is acceptable as an alternative.
|
||||
|
||||
## Contributing A Patch
|
||||
@@ -36,7 +36,8 @@ PR is acceptable as an alternative.
|
||||
This ensures that work isn't being duplicated and communicating your plan
|
||||
early also generally leads to better patches.
|
||||
4. If your proposed change is accepted, and you haven't already done so, sign a
|
||||
Contributor License Agreement (see details above).
|
||||
Contributor License Agreement
|
||||
([see details above](#contributor-license-agreements)).
|
||||
5. Fork the desired repo, develop and test your code changes.
|
||||
6. Ensure that your code adheres to the existing style in the sample to which
|
||||
you are contributing.
|
||||
@@ -46,11 +47,11 @@ PR is acceptable as an alternative.
|
||||
## The Google Test and Google Mock Communities
|
||||
|
||||
The Google Test community exists primarily through the
|
||||
[discussion group](http://groups.google.com/group/googletestframework) and the
|
||||
[discussion group](https://groups.google.com/group/googletestframework) and the
|
||||
GitHub repository. Likewise, the Google Mock community exists primarily through
|
||||
their own [discussion group](http://groups.google.com/group/googlemock). You are
|
||||
definitely encouraged to contribute to the discussion and you can also help us
|
||||
to keep the effectiveness of the group high by following and promoting the
|
||||
their own [discussion group](https://groups.google.com/group/googlemock). You
|
||||
are definitely encouraged to contribute to the discussion and you can also help
|
||||
us to keep the effectiveness of the group high by following and promoting the
|
||||
guidelines listed here.
|
||||
|
||||
### Please Be Friendly
|
||||
@@ -79,15 +80,15 @@ fairly rigid coding style, as defined by the
|
||||
[google-styleguide](https://github.com/google/styleguide) project. All patches
|
||||
will be expected to conform to the style outlined
|
||||
[here](https://google.github.io/styleguide/cppguide.html). Use
|
||||
[.clang-format](https://github.com/google/googletest/blob/master/.clang-format)
|
||||
to check your formatting.
|
||||
[.clang-format](https://github.com/google/googletest/blob/main/.clang-format) to
|
||||
check your formatting.
|
||||
|
||||
## Requirements for Contributors
|
||||
|
||||
If you plan to contribute a patch, you need to build Google Test, Google Mock,
|
||||
and their own tests from a git checkout, which has further requirements:
|
||||
|
||||
* [Python](https://www.python.org/) v2.3 or newer (for running some of the
|
||||
* [Python](https://www.python.org/) v3.6 or newer (for running some of the
|
||||
tests and re-generating certain source files from templates)
|
||||
* [CMake](https://cmake.org/) v2.8.12 or newer
|
||||
|
||||
@@ -101,30 +102,40 @@ To make sure your changes work as intended and don't break existing
|
||||
functionality, you'll want to compile and run Google Test and GoogleMock's own
|
||||
tests. For that you can use CMake:
|
||||
|
||||
mkdir mybuild
|
||||
cd mybuild
|
||||
cmake -Dgtest_build_tests=ON -Dgmock_build_tests=ON ${GTEST_REPO_DIR}
|
||||
```
|
||||
mkdir mybuild
|
||||
cd mybuild
|
||||
cmake -Dgtest_build_tests=ON -Dgmock_build_tests=ON ${GTEST_REPO_DIR}
|
||||
```
|
||||
|
||||
To choose between building only Google Test or Google Mock, you may modify your
|
||||
cmake command to be one of each
|
||||
|
||||
cmake -Dgtest_build_tests=ON ${GTEST_DIR} # sets up Google Test tests
|
||||
cmake -Dgmock_build_tests=ON ${GMOCK_DIR} # sets up Google Mock tests
|
||||
```
|
||||
cmake -Dgtest_build_tests=ON ${GTEST_DIR} # sets up Google Test tests
|
||||
cmake -Dgmock_build_tests=ON ${GMOCK_DIR} # sets up Google Mock tests
|
||||
```
|
||||
|
||||
Make sure you have Python installed, as some of Google Test's tests are written
|
||||
in Python. If the cmake command complains about not being able to find Python
|
||||
(`Could NOT find PythonInterp (missing: PYTHON_EXECUTABLE)`), try telling it
|
||||
explicitly where your Python executable can be found:
|
||||
|
||||
cmake -DPYTHON_EXECUTABLE=path/to/python ...
|
||||
```
|
||||
cmake -DPYTHON_EXECUTABLE=path/to/python ...
|
||||
```
|
||||
|
||||
Next, you can build Google Test and / or Google Mock and all desired tests. On
|
||||
\*nix, this is usually done by
|
||||
|
||||
make
|
||||
```
|
||||
make
|
||||
```
|
||||
|
||||
To run the tests, do
|
||||
|
||||
make test
|
||||
```
|
||||
make test
|
||||
```
|
||||
|
||||
All tests should pass.
|
||||
|
||||
@@ -34,6 +34,7 @@ Manuel Klimek <klimek@google.com>
|
||||
Mario Tanev <radix@google.com>
|
||||
Mark Paskin
|
||||
Markus Heule <markus.heule@gmail.com>
|
||||
Martijn Vels <mvels@google.com>
|
||||
Matthew Simmons <simmonmt@acm.org>
|
||||
Mika Raento <mikie@iki.fi>
|
||||
Mike Bland <mbland@google.com>
|
||||
@@ -54,7 +55,9 @@ Russ Cox <rsc@google.com>
|
||||
Russ Rufer <russ@pentad.com>
|
||||
Sean Mcafee <eefacm@gmail.com>
|
||||
Sigurður Ásgeirsson <siggi@google.com>
|
||||
Soyeon Kim <sxshx818@naver.com>
|
||||
Sverre Sundsdal <sundsdal@gmail.com>
|
||||
Szymon Sobik <sobik.szymon@gmail.com>
|
||||
Takeshi Yoshino <tyoshino@google.com>
|
||||
Tracy Bialik <tracy@pentad.com>
|
||||
Vadim Berman <vadimb@google.com>
|
||||
|
||||
Executable → Regular
+46
-44
@@ -1,7 +1,6 @@
|
||||
#!/usr/bin/env python
|
||||
# Copyright 2024 Google Inc.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Copyright 2009, Google Inc.
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are
|
||||
@@ -29,50 +28,53 @@
|
||||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
"""upload_gtest.py v0.1.0 -- uploads a Google Test patch for review.
|
||||
# https://bazel.build/external/overview#bzlmod
|
||||
|
||||
This simple wrapper passes all command line flags and
|
||||
--cc=googletestframework@googlegroups.com to upload.py.
|
||||
module(
|
||||
name = "googletest",
|
||||
version = "head",
|
||||
compatibility_level = 1,
|
||||
)
|
||||
|
||||
USAGE: upload_gtest.py [options for upload.py]
|
||||
"""
|
||||
# Only direct dependencies need to be listed below.
|
||||
# Please keep the versions in sync with the versions in the WORKSPACE file.
|
||||
|
||||
__author__ = 'wan@google.com (Zhanyong Wan)'
|
||||
bazel_dep(
|
||||
name = "abseil-cpp",
|
||||
version = "20260526.0",
|
||||
)
|
||||
bazel_dep(
|
||||
name = "platforms",
|
||||
version = "1.1.0",
|
||||
)
|
||||
bazel_dep(
|
||||
name = "re2",
|
||||
version = "2025-11-05.bcr.1",
|
||||
)
|
||||
bazel_dep(
|
||||
name = "rules_cc",
|
||||
version = "0.2.22",
|
||||
)
|
||||
|
||||
import os
|
||||
import sys
|
||||
bazel_dep(
|
||||
name = "rules_python",
|
||||
version = "2.2.0",
|
||||
dev_dependency = True,
|
||||
)
|
||||
|
||||
CC_FLAG = '--cc='
|
||||
GTEST_GROUP = 'googletestframework@googlegroups.com'
|
||||
# https://rules-python.readthedocs.io/en/stable/toolchains.html#library-modules-with-dev-only-python-usage
|
||||
python = use_extension(
|
||||
"@rules_python//python/extensions:python.bzl",
|
||||
"python",
|
||||
dev_dependency = True,
|
||||
)
|
||||
python.toolchain(
|
||||
ignore_root_user_error = True,
|
||||
is_default = True,
|
||||
python_version = "3.13",
|
||||
)
|
||||
|
||||
|
||||
def main():
|
||||
# Finds the path to upload.py, assuming it is in the same directory
|
||||
# as this file.
|
||||
my_dir = os.path.dirname(os.path.abspath(__file__))
|
||||
upload_py_path = os.path.join(my_dir, 'upload.py')
|
||||
|
||||
# Adds Google Test discussion group to the cc line if it's not there
|
||||
# already.
|
||||
upload_py_argv = [upload_py_path]
|
||||
found_cc_flag = False
|
||||
for arg in sys.argv[1:]:
|
||||
if arg.startswith(CC_FLAG):
|
||||
found_cc_flag = True
|
||||
cc_line = arg[len(CC_FLAG):]
|
||||
cc_list = [addr for addr in cc_line.split(',') if addr]
|
||||
if GTEST_GROUP not in cc_list:
|
||||
cc_list.append(GTEST_GROUP)
|
||||
upload_py_argv.append(CC_FLAG + ','.join(cc_list))
|
||||
else:
|
||||
upload_py_argv.append(arg)
|
||||
|
||||
if not found_cc_flag:
|
||||
upload_py_argv.append(CC_FLAG + GTEST_GROUP)
|
||||
|
||||
# Invokes upload.py with the modified command line flags.
|
||||
os.execv(upload_py_path, upload_py_argv)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
# See fake_fuchsia_sdk.bzl for instructions on how to override this with a real SDK, if needed.
|
||||
fuchsia_sdk = use_extension("//:fake_fuchsia_sdk.bzl", "fuchsia_sdk")
|
||||
fuchsia_sdk.create_fake()
|
||||
use_repo(fuchsia_sdk, "fuchsia_sdk")
|
||||
@@ -2,28 +2,28 @@
|
||||
|
||||
### Announcements
|
||||
|
||||
#### Live at Head
|
||||
|
||||
GoogleTest now follows the
|
||||
[Abseil Live at Head philosophy](https://abseil.io/about/philosophy#upgrade-support).
|
||||
We recommend using the latest commit in the `master` branch in your projects.
|
||||
|
||||
#### Documentation Updates
|
||||
|
||||
Our documentation is now live on GitHub Pages at
|
||||
https://google.github.io/googletest/. We recommend browsing the documentation on
|
||||
GitHub Pages rather than directly in the repository.
|
||||
|
||||
#### Release 1.10.x
|
||||
#### Release 1.18.0
|
||||
|
||||
[Release 1.10.x](https://github.com/google/googletest/releases/tag/release-1.10.0)
|
||||
is now available.
|
||||
[Release 1.18.0](https://github.com/google/googletest/releases/tag/v1.18.0) is
|
||||
now available.
|
||||
|
||||
The 1.18.x branch
|
||||
[requires at least C++17](https://opensource.google/documentation/policies/cplusplus-support#c_language_standard).
|
||||
|
||||
#### Continuous Integration
|
||||
|
||||
We use Google's internal systems for continuous integration.
|
||||
|
||||
#### Coming Soon
|
||||
|
||||
* We are planning to take a dependency on
|
||||
[Abseil](https://github.com/abseil/abseil-cpp).
|
||||
* More documentation improvements are planned.
|
||||
|
||||
## Welcome to **GoogleTest**, Google's C++ test framework!
|
||||
|
||||
@@ -42,64 +42,58 @@ More information about building GoogleTest can be found at
|
||||
|
||||
## Features
|
||||
|
||||
* An [xUnit](https://en.wikipedia.org/wiki/XUnit) test framework.
|
||||
* Test discovery.
|
||||
* A rich set of assertions.
|
||||
* User-defined assertions.
|
||||
* Death tests.
|
||||
* Fatal and non-fatal failures.
|
||||
* Value-parameterized tests.
|
||||
* Type-parameterized tests.
|
||||
* Various options for running the tests.
|
||||
* XML test report generation.
|
||||
* xUnit test framework: \
|
||||
Googletest is based on the [xUnit](https://en.wikipedia.org/wiki/XUnit)
|
||||
testing framework, a popular architecture for unit testing.
|
||||
* Test discovery: \
|
||||
Googletest automatically discovers and runs your tests, eliminating the need
|
||||
to manually register your tests.
|
||||
* Rich set of assertions: \
|
||||
Googletest provides a variety of assertions, such as equality, inequality,
|
||||
exceptions, and more, making it easy to test your code.
|
||||
* User-defined assertions: \
|
||||
You can define your own assertions with Googletest, making it simple to
|
||||
write tests that are specific to your code.
|
||||
* Death tests: \
|
||||
Googletest supports death tests, which verify that your code exits in a
|
||||
certain way, making it useful for testing error-handling code.
|
||||
* Fatal and non-fatal failures: \
|
||||
You can specify whether a test failure should be treated as fatal or
|
||||
non-fatal with Googletest, allowing tests to continue running even if a
|
||||
failure occurs.
|
||||
* Value-parameterized tests: \
|
||||
Googletest supports value-parameterized tests, which run multiple times with
|
||||
different input values, making it useful for testing functions that take
|
||||
different inputs.
|
||||
* Type-parameterized tests: \
|
||||
Googletest also supports type-parameterized tests, which run with different
|
||||
data types, making it useful for testing functions that work with different
|
||||
data types.
|
||||
* Various options for running tests: \
|
||||
Googletest provides many options for running tests including running
|
||||
individual tests, running tests in a specific order and running tests in
|
||||
parallel.
|
||||
|
||||
## Supported Platforms
|
||||
|
||||
GoogleTest requires a codebase and compiler compliant with the C++11 standard or
|
||||
newer.
|
||||
|
||||
The GoogleTest code is officially supported on the following platforms.
|
||||
Operating systems or tools not listed below are community-supported. For
|
||||
community-supported platforms, patches that do not complicate the code may be
|
||||
considered.
|
||||
|
||||
If you notice any problems on your platform, please file an issue on the
|
||||
[GoogleTest GitHub Issue Tracker](https://github.com/google/googletest/issues).
|
||||
Pull requests containing fixes are welcome!
|
||||
|
||||
### Operating Systems
|
||||
|
||||
* Linux
|
||||
* macOS
|
||||
* Windows
|
||||
|
||||
### Compilers
|
||||
|
||||
* gcc 5.0+
|
||||
* clang 5.0+
|
||||
* MSVC 2015+
|
||||
|
||||
**macOS users:** Xcode 9.3+ provides clang 5.0+.
|
||||
|
||||
### Build Systems
|
||||
|
||||
* [Bazel](https://bazel.build/)
|
||||
* [CMake](https://cmake.org/)
|
||||
|
||||
**Note:** Bazel is the build system used by the team internally and in tests.
|
||||
CMake is supported on a best-effort basis and by the community.
|
||||
GoogleTest follows Google's
|
||||
[Foundational C++ Support Policy](https://opensource.google/documentation/policies/cplusplus-support).
|
||||
See
|
||||
[this table](https://github.com/google/oss-policies-info/blob/main/foundational-cxx-support-matrix.md)
|
||||
for a list of currently supported versions of compilers, platforms, and build
|
||||
tools.
|
||||
|
||||
## Who Is Using GoogleTest?
|
||||
|
||||
In addition to many internal projects at Google, GoogleTest is also used by the
|
||||
following notable projects:
|
||||
|
||||
* The [Chromium projects](http://www.chromium.org/) (behind the Chrome browser
|
||||
and Chrome OS).
|
||||
* The [LLVM](http://llvm.org/) compiler.
|
||||
* The [Chromium projects](https://www.chromium.org/) (behind the Chrome
|
||||
browser and Chrome OS).
|
||||
* The [LLVM](https://llvm.org/) compiler.
|
||||
* [Protocol Buffers](https://github.com/google/protobuf), Google's data
|
||||
interchange format.
|
||||
* The [OpenCV](http://opencv.org/) computer vision library.
|
||||
* The [OpenCV](https://opencv.org/) computer vision library.
|
||||
|
||||
## Related Open Source Projects
|
||||
|
||||
@@ -109,8 +103,8 @@ Windows and Linux platforms.
|
||||
|
||||
[GoogleTest UI](https://github.com/ospector/gtest-gbar) is a test runner that
|
||||
runs your test binary, allows you to track its progress via a progress bar, and
|
||||
displays a list of test failures. Clicking on one shows failure text. Google
|
||||
Test UI is written in C#.
|
||||
displays a list of test failures. Clicking on one shows failure text. GoogleTest
|
||||
UI is written in C#.
|
||||
|
||||
[GTest TAP Listener](https://github.com/kinow/gtest-tap-listener) is an event
|
||||
listener for GoogleTest that implements the
|
||||
@@ -121,11 +115,11 @@ result output. If your test runner understands TAP, you may find it useful.
|
||||
runs tests from your binary in parallel to provide significant speed-up.
|
||||
|
||||
[GoogleTest Adapter](https://marketplace.visualstudio.com/items?itemName=DavidSchuldenfrei.gtest-adapter)
|
||||
is a VS Code extension allowing to view GoogleTest in a tree view, and run/debug
|
||||
is a VS Code extension allowing to view GoogleTest in a tree view and run/debug
|
||||
your tests.
|
||||
|
||||
[C++ TestMate](https://github.com/matepek/vscode-catch2-test-adapter) is a VS
|
||||
Code extension allowing to view GoogleTest in a tree view, and run/debug your
|
||||
Code extension allowing to view GoogleTest in a tree view and run/debug your
|
||||
tests.
|
||||
|
||||
[Cornichon](https://pypi.org/project/cornichon/) is a small Gherkin DSL parser
|
||||
@@ -134,7 +128,7 @@ that generates stub code for GoogleTest.
|
||||
## Contributing Changes
|
||||
|
||||
Please read
|
||||
[`CONTRIBUTING.md`](https://github.com/google/googletest/blob/master/CONTRIBUTING.md)
|
||||
[`CONTRIBUTING.md`](https://github.com/google/googletest/blob/main/CONTRIBUTING.md)
|
||||
for details on how to contribute to this project.
|
||||
|
||||
Happy testing!
|
||||
|
||||
@@ -1,24 +1,66 @@
|
||||
workspace(name = "com_google_googletest")
|
||||
# Copyright 2024 Google Inc.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are
|
||||
# met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright
|
||||
# notice, this list of conditions and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above
|
||||
# copyright notice, this list of conditions and the following disclaimer
|
||||
# in the documentation and/or other materials provided with the
|
||||
# distribution.
|
||||
# * Neither the name of Google Inc. nor the names of its
|
||||
# contributors may be used to endorse or promote products derived from
|
||||
# this software without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
workspace(name = "googletest")
|
||||
|
||||
load("//:googletest_deps.bzl", "googletest_deps")
|
||||
|
||||
googletest_deps()
|
||||
|
||||
load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
|
||||
|
||||
http_archive(
|
||||
name = "com_google_absl",
|
||||
urls = ["https://github.com/abseil/abseil-cpp/archive/7971fb358ae376e016d2d4fc9327aad95659b25e.zip"], # 2021-05-20T02:59:16Z
|
||||
strip_prefix = "abseil-cpp-7971fb358ae376e016d2d4fc9327aad95659b25e",
|
||||
sha256 = "aeba534f7307e36fe084b452299e49b97420667a8d28102cf9a0daeed340b859",
|
||||
name = "rules_python",
|
||||
sha256 = "e11d2e1efce1589e5bdfa93986712c74fc7467a0f093143d489d2ef5ebb1ed2a",
|
||||
strip_prefix = "rules_python-2.2.0",
|
||||
url = "https://github.com/bazelbuild/rules_python/releases/download/2.2.0/rules_python-2.2.0.tar.gz",
|
||||
)
|
||||
|
||||
http_archive(
|
||||
name = "rules_cc",
|
||||
urls = ["https://github.com/bazelbuild/rules_cc/archive/68cb652a71e7e7e2858c50593e5a9e3b94e5b9a9.zip"], # 2021-05-14T14:51:14Z
|
||||
strip_prefix = "rules_cc-68cb652a71e7e7e2858c50593e5a9e3b94e5b9a9",
|
||||
sha256 = "1e19e9a3bc3d4ee91d7fcad00653485ee6c798efbbf9588d40b34cbfbded143d",
|
||||
)
|
||||
# https://github.com/bazelbuild/rules_python/releases/tag/1.1.0
|
||||
load("@rules_python//python:repositories.bzl", "py_repositories")
|
||||
|
||||
py_repositories()
|
||||
|
||||
http_archive(
|
||||
name = "rules_python",
|
||||
urls = ["https://github.com/bazelbuild/rules_python/archive/ed6cc8f2c3692a6a7f013ff8bc185ba77eb9b4d2.zip"], # 2021-05-17T00:24:16Z
|
||||
strip_prefix = "rules_python-ed6cc8f2c3692a6a7f013ff8bc185ba77eb9b4d2",
|
||||
sha256 = "98b3c592faea9636ac8444bfd9de7f3fb4c60590932d6e6ac5946e3f8dbd5ff6",
|
||||
name = "platforms",
|
||||
sha256 = "dbad4a23abcca6171e47b79edc53bd6a41067a3b75f9e8b104656b459ff25046",
|
||||
urls = [
|
||||
"https://mirror.bazel.build/github.com/bazelbuild/platforms/releases/download/1.1.0/platforms-1.1.0.tar.gz",
|
||||
"https://github.com/bazelbuild/platforms/releases/download/1.1.0/platforms-1.1.0.tar.gz",
|
||||
],
|
||||
)
|
||||
|
||||
load("@bazel_features//:deps.bzl", "bazel_features_deps")
|
||||
|
||||
bazel_features_deps()
|
||||
|
||||
load("@rules_cc//cc:extensions.bzl", "compatibility_proxy_repo")
|
||||
|
||||
compatibility_proxy_repo()
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
# Copyright 2013 Google Inc. All Rights Reserved.
|
||||
# Copyright 2024 Google Inc.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are
|
||||
@@ -26,58 +28,8 @@
|
||||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
"""Shared utilities for writing scripts for Google Test/Mock."""
|
||||
|
||||
__author__ = 'wan@google.com (Zhanyong Wan)'
|
||||
|
||||
|
||||
import os
|
||||
import re
|
||||
|
||||
|
||||
# Matches the line from 'svn info .' output that describes what SVN
|
||||
# path the current local directory corresponds to. For example, in
|
||||
# a googletest SVN workspace's trunk/test directory, the output will be:
|
||||
# https://bazel.build/external/migration#workspace.bzlmod
|
||||
#
|
||||
# URL: https://googletest.googlecode.com/svn/trunk/test
|
||||
_SVN_INFO_URL_RE = re.compile(r'^URL: https://(\w+)\.googlecode\.com/svn(.*)')
|
||||
|
||||
|
||||
def GetCommandOutput(command):
|
||||
"""Runs the shell command and returns its stdout as a list of lines."""
|
||||
|
||||
f = os.popen(command, 'r')
|
||||
lines = [line.strip() for line in f.readlines()]
|
||||
f.close()
|
||||
return lines
|
||||
|
||||
|
||||
def GetSvnInfo():
|
||||
"""Returns the project name and the current SVN workspace's root path."""
|
||||
|
||||
for line in GetCommandOutput('svn info .'):
|
||||
m = _SVN_INFO_URL_RE.match(line)
|
||||
if m:
|
||||
project = m.group(1) # googletest or googlemock
|
||||
rel_path = m.group(2)
|
||||
root = os.path.realpath(rel_path.count('/') * '../')
|
||||
return project, root
|
||||
|
||||
return None, None
|
||||
|
||||
|
||||
def GetSvnTrunk():
|
||||
"""Returns the current SVN workspace's trunk root path."""
|
||||
|
||||
_, root = GetSvnInfo()
|
||||
return root + '/trunk' if root else None
|
||||
|
||||
|
||||
def IsInGTestSvn():
|
||||
project, _ = GetSvnInfo()
|
||||
return project == 'googletest'
|
||||
|
||||
|
||||
def IsInGMockSvn():
|
||||
project, _ = GetSvnInfo()
|
||||
return project == 'googlemock'
|
||||
# This file is intentionally empty. When bzlmod is enabled and this
|
||||
# file exists, the content of WORKSPACE is ignored. This prevents
|
||||
# bzlmod builds from unintentionally depending on the WORKSPACE file.
|
||||
+106
-51
@@ -31,39 +31,66 @@
|
||||
|
||||
set -euox pipefail
|
||||
|
||||
readonly LINUX_LATEST_CONTAINER="gcr.io/google.com/absl-177019/linux_hybrid-latest:20210525"
|
||||
readonly LINUX_GCC_FLOOR_CONTAINER="gcr.io/google.com/absl-177019/linux_gcc-floor:20201015"
|
||||
readonly LINUX_LATEST_CONTAINER="gcr.io/google.com/absl-177019/linux_hybrid-latest@sha256:baa99e65a3cc837bab8e5246f1870d25c76d0adf2b1d598ee5a3ec77fd2e19bd"
|
||||
|
||||
if [[ -z ${GTEST_ROOT:-} ]]; then
|
||||
GTEST_ROOT="$(realpath $(dirname ${0})/..)"
|
||||
fi
|
||||
|
||||
if [[ -z ${STD:-} ]]; then
|
||||
STD="c++11 c++14 c++17 c++20"
|
||||
# Use Bazel Vendor mode to reduce reliance on external dependencies.
|
||||
# See https://bazel.build/external/vendor and the Dockerfile for
|
||||
# an explaination of how this works.
|
||||
if [[ ${KOKORO_GFILE_DIR:-} ]] && [[ -f "${KOKORO_GFILE_DIR}/distdir/googletest_vendor.tar.gz" ]]; then
|
||||
DOCKER_EXTRA_ARGS="--mount type=bind,source=${KOKORO_GFILE_DIR}/distdir,target=/distdir,readonly --env=BAZEL_VENDOR_ARCHIVE=/distdir/googletest_vendor.tar.gz ${DOCKER_EXTRA_ARGS:-}"
|
||||
BAZEL_EXTRA_ARGS="--vendor_dir=/googletest_vendor ${BAZEL_EXTRA_ARGS:-}"
|
||||
fi
|
||||
|
||||
# Test the CMake build
|
||||
for cc in /usr/local/bin/gcc /opt/llvm/clang/bin/clang; do
|
||||
for cmake_off_on in OFF ON; do
|
||||
time docker run \
|
||||
--volume="${GTEST_ROOT}:/src:ro" \
|
||||
--tmpfs="/build:exec" \
|
||||
--workdir="/build" \
|
||||
--rm \
|
||||
--env="CC=${cc}" \
|
||||
--env="CXX_FLAGS=\"-Werror -Wdeprecated\"" \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/bin/bash -c "
|
||||
cmake /src \
|
||||
-DCMAKE_CXX_STANDARD=11 \
|
||||
-Dgtest_build_samples=ON \
|
||||
-Dgtest_build_tests=ON \
|
||||
-Dgmock_build_tests=ON \
|
||||
-Dcxx_no_exception=${cmake_off_on} \
|
||||
-Dcxx_no_rtti=${cmake_off_on} && \
|
||||
make -j$(nproc) && \
|
||||
ctest -j$(nproc) --output-on-failure"
|
||||
done
|
||||
if [[ -z ${STD:-} ]]; then
|
||||
STD="c++17 c++20 c++23"
|
||||
fi
|
||||
|
||||
# Test CMake + GCC
|
||||
for cmake_off_on in OFF ON; do
|
||||
time docker run \
|
||||
--volume="${GTEST_ROOT}:/src:ro" \
|
||||
--tmpfs="/build:exec" \
|
||||
--workdir="/build" \
|
||||
--rm \
|
||||
--env="CC=/usr/local/bin/gcc" \
|
||||
--env=CXXFLAGS="-Werror -Wdeprecated" \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/bin/bash -c "
|
||||
cmake /src \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
-Dgtest_build_samples=ON \
|
||||
-Dgtest_build_tests=ON \
|
||||
-Dgmock_build_tests=ON \
|
||||
-Dcxx_no_exception=${cmake_off_on} \
|
||||
-Dcxx_no_rtti=${cmake_off_on} && \
|
||||
make -j$(nproc) && \
|
||||
ctest -j$(nproc) --output-on-failure"
|
||||
done
|
||||
|
||||
# Test CMake + Clang
|
||||
for cmake_off_on in OFF ON; do
|
||||
time docker run \
|
||||
--volume="${GTEST_ROOT}:/src:ro" \
|
||||
--tmpfs="/build:exec" \
|
||||
--workdir="/build" \
|
||||
--rm \
|
||||
--env="CC=/opt/llvm/bin/clang" \
|
||||
--env=CXXFLAGS="-Werror -Wdeprecated --gcc-toolchain=/usr/local" \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/bin/bash -c "
|
||||
cmake /src \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
-Dgtest_build_samples=ON \
|
||||
-Dgtest_build_tests=ON \
|
||||
-Dgmock_build_tests=ON \
|
||||
-Dcxx_no_exception=${cmake_off_on} \
|
||||
-Dcxx_no_rtti=${cmake_off_on} && \
|
||||
make -j$(nproc) && \
|
||||
ctest -j$(nproc) --output-on-failure"
|
||||
done
|
||||
|
||||
# Do one test with an older version of GCC
|
||||
@@ -71,15 +98,27 @@ time docker run \
|
||||
--volume="${GTEST_ROOT}:/src:ro" \
|
||||
--workdir="/src" \
|
||||
--rm \
|
||||
--env="CC=/usr/local/bin/gcc" \
|
||||
${LINUX_GCC_FLOOR_CONTAINER} \
|
||||
--env="CC=/opt/gcc-10/bin/gcc" \
|
||||
--env="BAZEL_CXXOPTS=-std=c++17" \
|
||||
--env="BAZEL_LINKOPTS=-L/opt/gcc-10/lib64:-Wl,-rpath=/opt/gcc-10/lib64" \
|
||||
--env="USE_BAZEL_VERSION=8.5.1" \
|
||||
${DOCKER_EXTRA_ARGS:-} \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/bin/bash --login -c "
|
||||
/usr/local/bin/bazel test ... \
|
||||
--copt="-Wall" \
|
||||
--copt="-Werror" \
|
||||
--copt="-Wno-error=pragmas" \
|
||||
--copt=\"-Wall\" \
|
||||
--copt=\"-Werror\" \
|
||||
--copt=\"-Wuninitialized\" \
|
||||
--copt=\"-Wundef\" \
|
||||
--copt=\"-Wno-error=pragmas\" \
|
||||
--enable_bzlmod=false \
|
||||
--enable_workspace=true \
|
||||
--features=external_include_paths \
|
||||
--keep_going \
|
||||
--per_file_copt=\"external/.*@-w\" \
|
||||
--show_timestamps \
|
||||
--test_output=errors
|
||||
--test_output=errors \
|
||||
${BAZEL_EXTRA_ARGS:-}"
|
||||
|
||||
# Test GCC
|
||||
for std in ${STD}; do
|
||||
@@ -90,15 +129,23 @@ for std in ${STD}; do
|
||||
--rm \
|
||||
--env="CC=/usr/local/bin/gcc" \
|
||||
--env="BAZEL_CXXOPTS=-std=${std}" \
|
||||
--env="USE_BAZEL_VERSION=9.1.0" \
|
||||
${DOCKER_EXTRA_ARGS:-} \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/usr/local/bin/bazel test ... \
|
||||
--copt="-Wall" \
|
||||
--copt="-Werror" \
|
||||
--define="absl=${absl}" \
|
||||
--distdir="/bazel-distdir" \
|
||||
--keep_going \
|
||||
--show_timestamps \
|
||||
--test_output=errors
|
||||
/bin/bash --login -c "
|
||||
/usr/local/bin/bazel test ... \
|
||||
--copt=\"-Wall\" \
|
||||
--copt=\"-Werror\" \
|
||||
--copt=\"-Wuninitialized\" \
|
||||
--copt=\"-Wundef\" \
|
||||
--define=\"absl=${absl}\" \
|
||||
--enable_bzlmod=true \
|
||||
--features=external_include_paths \
|
||||
--keep_going \
|
||||
--per_file_copt=\"external/.*@-w\" \
|
||||
--show_timestamps \
|
||||
--test_output=errors \
|
||||
${BAZEL_EXTRA_ARGS:-}"
|
||||
done
|
||||
done
|
||||
|
||||
@@ -109,18 +156,26 @@ for std in ${STD}; do
|
||||
--volume="${GTEST_ROOT}:/src:ro" \
|
||||
--workdir="/src" \
|
||||
--rm \
|
||||
--env="CC=/opt/llvm/clang/bin/clang" \
|
||||
--env="CC=/opt/llvm/bin/clang" \
|
||||
--env="BAZEL_CXXOPTS=-std=${std}" \
|
||||
--env="USE_BAZEL_VERSION=9.1.0" \
|
||||
${DOCKER_EXTRA_ARGS:-} \
|
||||
${LINUX_LATEST_CONTAINER} \
|
||||
/usr/local/bin/bazel test ... \
|
||||
--copt="--gcc-toolchain=/usr/local" \
|
||||
--copt="-Wall" \
|
||||
--copt="-Werror" \
|
||||
--define="absl=${absl}" \
|
||||
--distdir="/bazel-distdir" \
|
||||
--keep_going \
|
||||
--linkopt="--gcc-toolchain=/usr/local" \
|
||||
--show_timestamps \
|
||||
--test_output=errors
|
||||
/bin/bash --login -c "
|
||||
/usr/local/bin/bazel test ... \
|
||||
--copt=\"--gcc-toolchain=/usr/local\" \
|
||||
--copt=\"-Wall\" \
|
||||
--copt=\"-Werror\" \
|
||||
--copt=\"-Wuninitialized\" \
|
||||
--copt=\"-Wundef\" \
|
||||
--define=\"absl=${absl}\" \
|
||||
--enable_bzlmod=true \
|
||||
--features=external_include_paths \
|
||||
--keep_going \
|
||||
--linkopt=\"--gcc-toolchain=/usr/local\" \
|
||||
--per_file_copt=\"external/.*@-w\" \
|
||||
--show_timestamps \
|
||||
--test_output=errors \
|
||||
${BAZEL_EXTRA_ARGS:-}"
|
||||
done
|
||||
done
|
||||
|
||||
+24
-4
@@ -31,6 +31,14 @@
|
||||
|
||||
set -euox pipefail
|
||||
|
||||
# Use Xcode 26.2
|
||||
sudo xcode-select -s /Applications/Xcode_26.2.app/Contents/Developer
|
||||
|
||||
brew install cmake
|
||||
|
||||
export CMAKE_BUILD_PARALLEL_LEVEL=$(sysctl -n hw.ncpu)
|
||||
export CTEST_PARALLEL_LEVEL=$(sysctl -n hw.ncpu)
|
||||
|
||||
if [[ -z ${GTEST_ROOT:-} ]]; then
|
||||
GTEST_ROOT="$(realpath $(dirname ${0})/..)"
|
||||
fi
|
||||
@@ -40,20 +48,20 @@ for cmake_off_on in OFF ON; do
|
||||
BUILD_DIR=$(mktemp -d build_dir.XXXXXXXX)
|
||||
cd ${BUILD_DIR}
|
||||
time cmake ${GTEST_ROOT} \
|
||||
-DCMAKE_CXX_STANDARD=11 \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
-Dgtest_build_samples=ON \
|
||||
-Dgtest_build_tests=ON \
|
||||
-Dgmock_build_tests=ON \
|
||||
-Dcxx_no_exception=${cmake_off_on} \
|
||||
-Dcxx_no_rtti=${cmake_off_on}
|
||||
time make
|
||||
time make -j$(nproc)
|
||||
time ctest -j$(nproc) --output-on-failure
|
||||
done
|
||||
|
||||
# Test the Bazel build
|
||||
|
||||
# If we are running on Kokoro, check for a versioned Bazel binary.
|
||||
KOKORO_GFILE_BAZEL_BIN="bazel-3.7.0-darwin-x86_64"
|
||||
KOKORO_GFILE_BAZEL_BIN="bazel-9.1.0-darwin-x86_64"
|
||||
if [[ ${KOKORO_GFILE_DIR:-} ]] && [[ -f ${KOKORO_GFILE_DIR}/${KOKORO_GFILE_BAZEL_BIN} ]]; then
|
||||
BAZEL_BIN="${KOKORO_GFILE_DIR}/${KOKORO_GFILE_BAZEL_BIN}"
|
||||
chmod +x ${BAZEL_BIN}
|
||||
@@ -61,13 +69,25 @@ else
|
||||
BAZEL_BIN="bazel"
|
||||
fi
|
||||
|
||||
# Use Bazel Vendor mode to reduce reliance on external dependencies.
|
||||
if [[ ${KOKORO_GFILE_DIR:-} ]] && [[ -f "${KOKORO_GFILE_DIR}/distdir/googletest_vendor.tar.gz" ]]; then
|
||||
tar -xf "${KOKORO_GFILE_DIR}/distdir/googletest_vendor.tar.gz" -C "${HOME}/"
|
||||
BAZEL_EXTRA_ARGS="--vendor_dir=${HOME}/googletest_vendor ${BAZEL_EXTRA_ARGS:-}"
|
||||
fi
|
||||
|
||||
cd ${GTEST_ROOT}
|
||||
for absl in 0 1; do
|
||||
${BAZEL_BIN} test ... \
|
||||
--copt="-Wall" \
|
||||
--copt="-Werror" \
|
||||
--copt="-Wundef" \
|
||||
--cxxopt="-std=c++17" \
|
||||
--define="absl=${absl}" \
|
||||
--enable_bzlmod=true \
|
||||
--features=external_include_paths \
|
||||
--keep_going \
|
||||
--per_file_copt="external/.*@-w" \
|
||||
--show_timestamps \
|
||||
--test_output=errors
|
||||
--test_output=errors \
|
||||
${BAZEL_EXTRA_ARGS:-}
|
||||
done
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
SETLOCAL ENABLEDELAYEDEXPANSION
|
||||
|
||||
SET BAZEL_EXE=%KOKORO_GFILE_DIR%\bazel-9.1.0-windows-x86_64.exe
|
||||
|
||||
SET PATH=C:\Python34;%PATH%
|
||||
SET BAZEL_PYTHON=C:\python34\python.exe
|
||||
SET BAZEL_SH=C:\tools\msys64\usr\bin\bash.exe
|
||||
SET CMAKE_BIN="cmake.exe"
|
||||
SET CTEST_BIN="ctest.exe"
|
||||
SET CTEST_OUTPUT_ON_FAILURE=1
|
||||
SET CMAKE_BUILD_PARALLEL_LEVEL=16
|
||||
SET CTEST_PARALLEL_LEVEL=16
|
||||
|
||||
SET GTEST_ROOT=%~dp0\..
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
|
||||
:: ----------------------------------------------------------------------------
|
||||
:: CMake
|
||||
SET CMAKE_BUILD_PATH=cmake_msvc2022
|
||||
MKDIR %CMAKE_BUILD_PATH%
|
||||
CD %CMAKE_BUILD_PATH%
|
||||
SET CXXFLAGS="/WX"
|
||||
|
||||
%CMAKE_BIN% %GTEST_ROOT% ^
|
||||
-G "Visual Studio 17 2022" ^
|
||||
-DCMAKE_CXX_STANDARD=17 ^
|
||||
-DPYTHON_EXECUTABLE:FILEPATH=c:\python37\python.exe ^
|
||||
-DPYTHON_INCLUDE_DIR:PATH=c:\python37\include ^
|
||||
-DPYTHON_LIBRARY:FILEPATH=c:\python37\lib\site-packages\pip ^
|
||||
-Dgtest_build_samples=ON ^
|
||||
-Dgtest_build_tests=ON ^
|
||||
-Dgmock_build_tests=ON
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
|
||||
%CMAKE_BIN% --build . --target ALL_BUILD --config Debug -- -maxcpucount
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
|
||||
%CTEST_BIN% -C Debug --timeout 600
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
|
||||
SET "CXXFLAGS="
|
||||
CD %GTEST_ROOT%
|
||||
RMDIR /S /Q %CMAKE_BUILD_PATH%
|
||||
|
||||
:: ----------------------------------------------------------------------------
|
||||
:: Bazel
|
||||
|
||||
:: The default home directory on Kokoro is a long path which causes errors
|
||||
:: because of Windows limitations on path length.
|
||||
:: --output_user_root=C:\tmp causes Bazel to use a shorter path.
|
||||
SET BAZEL_VS=C:\Program Files\Microsoft Visual Studio\2022\Community
|
||||
|
||||
:: Use Bazel Vendor mode to reduce reliance on external dependencies.
|
||||
IF EXIST "%KOKORO_GFILE_DIR%\distdir\googletest_vendor.tar.gz" (
|
||||
tar --force-local -xf "%KOKORO_GFILE_DIR%\distdir\googletest_vendor.tar.gz" -C c:
|
||||
SET VENDOR_FLAG=--vendor_dir=c:\googletest_vendor
|
||||
) ELSE (
|
||||
SET VENDOR_FLAG=
|
||||
)
|
||||
|
||||
:: C++17
|
||||
%BAZEL_EXE% ^
|
||||
--output_user_root=C:\tmp ^
|
||||
test ... ^
|
||||
--compilation_mode=dbg ^
|
||||
--copt=/std:c++17 ^
|
||||
--copt=/WX ^
|
||||
--enable_bzlmod=true ^
|
||||
--keep_going ^
|
||||
--per_file_copt=external/.*@/w ^
|
||||
--test_output=errors ^
|
||||
--test_tag_filters=-no_test_msvc2017 ^
|
||||
%VENDOR_FLAG%
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
|
||||
:: C++20
|
||||
%BAZEL_EXE% ^
|
||||
--output_user_root=C:\tmp ^
|
||||
test ... ^
|
||||
--compilation_mode=dbg ^
|
||||
--copt=/std:c++20 ^
|
||||
--copt=/WX ^
|
||||
--enable_bzlmod=true ^
|
||||
--keep_going ^
|
||||
--per_file_copt=external/.*@/w ^
|
||||
--test_output=errors ^
|
||||
--test_tag_filters=-no_test_msvc2017 ^
|
||||
%VENDOR_FLAG%
|
||||
IF %errorlevel% neq 0 EXIT /B 1
|
||||
@@ -7,15 +7,15 @@
|
||||
|
||||
{% seo %}
|
||||
<link rel="stylesheet" href="{{ "/assets/css/style.css?v=" | append: site.github.build_revision | relative_url }}">
|
||||
<!-- Google tag (gtag.js) -->
|
||||
<script async src="https://www.googletagmanager.com/gtag/js?id=G-9PTP6FW1M5"></script>
|
||||
<script>
|
||||
window.ga=window.ga||function(){(ga.q=ga.q||[]).push(arguments)};ga.l=+new Date;
|
||||
ga('create', 'UA-197576187-1', { 'storage': 'none' });
|
||||
ga('set', 'referrer', document.referrer.split('?')[0]);
|
||||
ga('set', 'location', window.location.href.split('?')[0]);
|
||||
ga('set', 'anonymizeIp', true);
|
||||
ga('send', 'pageview');
|
||||
window.dataLayer = window.dataLayer || [];
|
||||
function gtag(){dataLayer.push(arguments);}
|
||||
gtag('js', new Date());
|
||||
|
||||
gtag('config', 'G-9PTP6FW1M5');
|
||||
</script>
|
||||
<script async src='https://www.google-analytics.com/analytics.js'></script>
|
||||
</head>
|
||||
<body>
|
||||
<div class="sidebar">
|
||||
@@ -48,7 +48,7 @@
|
||||
<div class="footer">
|
||||
GoogleTest ·
|
||||
<a href="https://github.com/google/googletest">GitHub Repository</a> ·
|
||||
<a href="https://github.com/google/googletest/blob/master/LICENSE">License</a> ·
|
||||
<a href="https://github.com/google/googletest/blob/main/LICENSE">License</a> ·
|
||||
<a href="https://policies.google.com/privacy">Privacy Policy</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+364
-200
File diff suppressed because it is too large
Load Diff
+46
-81
@@ -1,9 +1,9 @@
|
||||
# Googletest FAQ
|
||||
# GoogleTest FAQ
|
||||
|
||||
## Why should test suite names and test names not contain underscore?
|
||||
|
||||
{: .callout .note}
|
||||
Note: Googletest reserves underscore (`_`) for special purpose keywords, such as
|
||||
Note: GoogleTest reserves underscore (`_`) for special-purpose keywords, such as
|
||||
[the `DISABLED_` prefix](advanced.md#temporarily-disabling-tests), in addition
|
||||
to the following rationale.
|
||||
|
||||
@@ -33,9 +33,9 @@ contains `_`?
|
||||
`TestSuiteName_Bar__Test`, which is invalid.
|
||||
|
||||
So clearly `TestSuiteName` and `TestName` cannot start or end with `_`
|
||||
(Actually, `TestSuiteName` can start with `_` -- as long as the `_` isn't
|
||||
followed by an upper-case letter. But that's getting complicated. So for
|
||||
simplicity we just say that it cannot start with `_`.).
|
||||
(Actually, `TestSuiteName` can start with `_`—as long as the `_` isn't followed
|
||||
by an upper-case letter. But that's getting complicated. So for simplicity we
|
||||
just say that it cannot start with `_`.).
|
||||
|
||||
It may seem fine for `TestSuiteName` and `TestName` to contain `_` in the
|
||||
middle. However, consider this:
|
||||
@@ -50,15 +50,15 @@ Now, the two `TEST`s will both generate the same class
|
||||
|
||||
So for simplicity, we just ask the users to avoid `_` in `TestSuiteName` and
|
||||
`TestName`. The rule is more constraining than necessary, but it's simple and
|
||||
easy to remember. It also gives googletest some wiggle room in case its
|
||||
easy to remember. It also gives GoogleTest some wiggle room in case its
|
||||
implementation needs to change in the future.
|
||||
|
||||
If you violate the rule, there may not be immediate consequences, but your test
|
||||
may (just may) break with a new compiler (or a new version of the compiler you
|
||||
are using) or with a new version of googletest. Therefore it's best to follow
|
||||
are using) or with a new version of GoogleTest. Therefore it's best to follow
|
||||
the rule.
|
||||
|
||||
## Why does googletest support `EXPECT_EQ(NULL, ptr)` and `ASSERT_EQ(NULL, ptr)` but not `EXPECT_NE(NULL, ptr)` and `ASSERT_NE(NULL, ptr)`?
|
||||
## Why does GoogleTest support `EXPECT_EQ(NULL, ptr)` and `ASSERT_EQ(NULL, ptr)` but not `EXPECT_NE(NULL, ptr)` and `ASSERT_NE(NULL, ptr)`?
|
||||
|
||||
First of all, you can use `nullptr` with each of these macros, e.g.
|
||||
`EXPECT_EQ(ptr, nullptr)`, `EXPECT_NE(ptr, nullptr)`, `ASSERT_EQ(ptr, nullptr)`,
|
||||
@@ -68,7 +68,7 @@ because `nullptr` does not have the type problems that `NULL` does.
|
||||
Due to some peculiarity of C++, it requires some non-trivial template meta
|
||||
programming tricks to support using `NULL` as an argument of the `EXPECT_XX()`
|
||||
and `ASSERT_XX()` macros. Therefore we only do it where it's most needed
|
||||
(otherwise we make the implementation of googletest harder to maintain and more
|
||||
(otherwise we make the implementation of GoogleTest harder to maintain and more
|
||||
error-prone than necessary).
|
||||
|
||||
Historically, the `EXPECT_EQ()` macro took the *expected* value as its first
|
||||
@@ -128,30 +128,9 @@ both approaches a try. Practice is a much better way to grasp the subtle
|
||||
differences between the two tools. Once you have some concrete experience, you
|
||||
can much more easily decide which one to use the next time.
|
||||
|
||||
## I got some run-time errors about invalid proto descriptors when using `ProtocolMessageEquals`. Help!
|
||||
|
||||
{: .callout .note}
|
||||
**Note:** `ProtocolMessageEquals` and `ProtocolMessageEquiv` are *deprecated*
|
||||
now. Please use `EqualsProto`, etc instead.
|
||||
|
||||
`ProtocolMessageEquals` and `ProtocolMessageEquiv` were redefined recently and
|
||||
are now less tolerant of invalid protocol buffer definitions. In particular, if
|
||||
you have a `foo.proto` that doesn't fully qualify the type of a protocol message
|
||||
it references (e.g. `message<Bar>` where it should be `message<blah.Bar>`), you
|
||||
will now get run-time errors like:
|
||||
|
||||
```
|
||||
... descriptor.cc:...] Invalid proto descriptor for file "path/to/foo.proto":
|
||||
... descriptor.cc:...] blah.MyMessage.my_field: ".Bar" is not defined.
|
||||
```
|
||||
|
||||
If you see this, your `.proto` file is broken and needs to be fixed by making
|
||||
the types fully qualified. The new definition of `ProtocolMessageEquals` and
|
||||
`ProtocolMessageEquiv` just happen to reveal your bug.
|
||||
|
||||
## My death test modifies some state, but the change seems lost after the death test finishes. Why?
|
||||
|
||||
Death tests (`EXPECT_DEATH`, etc) are executed in a sub-process s.t. the
|
||||
Death tests (`EXPECT_DEATH`, etc.) are executed in a sub-process s.t. the
|
||||
expected crash won't kill the test program (i.e. the parent process). As a
|
||||
result, any in-memory side effects they incur are observable in their respective
|
||||
sub-processes, but not in the parent process. You can think of them as running
|
||||
@@ -162,7 +141,7 @@ methods, the parent process will think the calls have never occurred. Therefore,
|
||||
you may want to move your `EXPECT_CALL` statements inside the `EXPECT_DEATH`
|
||||
macro.
|
||||
|
||||
## EXPECT_EQ(htonl(blah), blah_blah) generates weird compiler errors in opt mode. Is this a googletest bug?
|
||||
## EXPECT_EQ(htonl(blah), blah_blah) generates weird compiler errors in opt mode. Is this a GoogleTest bug?
|
||||
|
||||
Actually, the bug is in `htonl()`.
|
||||
|
||||
@@ -192,16 +171,16 @@ class Foo {
|
||||
};
|
||||
```
|
||||
|
||||
You also need to define it *outside* of the class body in `foo.cc`:
|
||||
you also need to define it *outside* of the class body in `foo.cc`:
|
||||
|
||||
```c++
|
||||
const int Foo::kBar; // No initializer here.
|
||||
```
|
||||
|
||||
Otherwise your code is **invalid C++**, and may break in unexpected ways. In
|
||||
particular, using it in googletest comparison assertions (`EXPECT_EQ`, etc) will
|
||||
generate an "undefined reference" linker error. The fact that "it used to work"
|
||||
doesn't mean it's valid. It just means that you were lucky. :-)
|
||||
particular, using it in GoogleTest comparison assertions (`EXPECT_EQ`, etc.)
|
||||
will generate an "undefined reference" linker error. The fact that "it used to
|
||||
work" doesn't mean it's valid. It just means that you were lucky. :-)
|
||||
|
||||
If the declaration of the static data member is `constexpr` then it is
|
||||
implicitly an `inline` definition, and a separate definition in `foo.cc` is not
|
||||
@@ -225,7 +204,7 @@ cases may want to use the same or slightly different fixtures. For example, you
|
||||
may want to make sure that all of a GUI library's test suites don't leak
|
||||
important system resources like fonts and brushes.
|
||||
|
||||
In googletest, you share a fixture among test suites by putting the shared logic
|
||||
In GoogleTest, you share a fixture among test suites by putting the shared logic
|
||||
in a base test fixture, then deriving from that base a separate fixture for each
|
||||
test suite that wants to use this common logic. You then use `TEST_F()` to write
|
||||
tests using each derived fixture.
|
||||
@@ -264,10 +243,10 @@ TEST_F(FooTest, Baz) { ... }
|
||||
```
|
||||
|
||||
If necessary, you can continue to derive test fixtures from a derived fixture.
|
||||
googletest has no limit on how deep the hierarchy can be.
|
||||
GoogleTest has no limit on how deep the hierarchy can be.
|
||||
|
||||
For a complete example using derived test fixtures, see
|
||||
[sample5_unittest.cc](https://github.com/google/googletest/blob/master/googletest/samples/sample5_unittest.cc).
|
||||
[sample5_unittest.cc](https://github.com/google/googletest/blob/main/googletest/samples/sample5_unittest.cc).
|
||||
|
||||
## My compiler complains "void value not ignored as it ought to be." What does this mean?
|
||||
|
||||
@@ -278,7 +257,7 @@ disabled by our build system. Please see more details
|
||||
|
||||
## My death test hangs (or seg-faults). How do I fix it?
|
||||
|
||||
In googletest, death tests are run in a child process and the way they work is
|
||||
In GoogleTest, death tests are run in a child process and the way they work is
|
||||
delicate. To write death tests you really need to understand how they work—see
|
||||
the details at [Death Assertions](reference/assertions.md#death) in the
|
||||
Assertions Reference.
|
||||
@@ -305,13 +284,13 @@ bullet - sorry!
|
||||
|
||||
## Should I use the constructor/destructor of the test fixture or SetUp()/TearDown()? {#CtorVsSetUp}
|
||||
|
||||
The first thing to remember is that googletest does **not** reuse the same test
|
||||
fixture object across multiple tests. For each `TEST_F`, googletest will create
|
||||
The first thing to remember is that GoogleTest does **not** reuse the same test
|
||||
fixture object across multiple tests. For each `TEST_F`, GoogleTest will create
|
||||
a **fresh** test fixture object, immediately call `SetUp()`, run the test body,
|
||||
call `TearDown()`, and then delete the test fixture object.
|
||||
|
||||
When you need to write per-test set-up and tear-down logic, you have the choice
|
||||
between using the test fixture constructor/destructor or `SetUp()/TearDown()`.
|
||||
between using the test fixture constructor/destructor or `SetUp()`/`TearDown()`.
|
||||
The former is usually preferred, as it has the following benefits:
|
||||
|
||||
* By initializing a member variable in the constructor, we have the option to
|
||||
@@ -328,7 +307,7 @@ You may still want to use `SetUp()/TearDown()` in the following cases:
|
||||
|
||||
* C++ does not allow virtual function calls in constructors and destructors.
|
||||
You can call a method declared as virtual, but it will not use dynamic
|
||||
dispatch, it will use the definition from the class the constructor of which
|
||||
dispatch. It will use the definition from the class the constructor of which
|
||||
is currently executing. This is because calling a virtual method before the
|
||||
derived class constructor has a chance to run is very dangerous - the
|
||||
virtual method might operate on uninitialized data. Therefore, if you need
|
||||
@@ -345,14 +324,14 @@ You may still want to use `SetUp()/TearDown()` in the following cases:
|
||||
that many standard libraries (like STL) may throw when exceptions are
|
||||
enabled in the compiler. Therefore you should prefer `TearDown()` if you
|
||||
want to write portable tests that work with or without exceptions.
|
||||
* The googletest team is considering making the assertion macros throw on
|
||||
* The GoogleTest team is considering making the assertion macros throw on
|
||||
platforms where exceptions are enabled (e.g. Windows, Mac OS, and Linux
|
||||
client-side), which will eliminate the need for the user to propagate
|
||||
failures from a subroutine to its caller. Therefore, you shouldn't use
|
||||
googletest assertions in a destructor if your code could run on such a
|
||||
GoogleTest assertions in a destructor if your code could run on such a
|
||||
platform.
|
||||
|
||||
## The compiler complains "no matching function to call" when I use ASSERT_PRED*. How do I fix it?
|
||||
## The compiler complains "no matching function to call" when I use `ASSERT_PRED*`. How do I fix it?
|
||||
|
||||
See details for [`EXPECT_PRED*`](reference/assertions.md#EXPECT_PRED) in the
|
||||
Assertions Reference.
|
||||
@@ -375,7 +354,7 @@ they write
|
||||
This is **wrong and dangerous**. The testing services needs to see the return
|
||||
value of `RUN_ALL_TESTS()` in order to determine if a test has passed. If your
|
||||
`main()` function ignores it, your test will be considered successful even if it
|
||||
has a googletest assertion failure. Very bad.
|
||||
has a GoogleTest assertion failure. Very bad.
|
||||
|
||||
We have decided to fix this (thanks to Michael Chastain for the idea). Now, your
|
||||
code will no longer be able to ignore `RUN_ALL_TESTS()` when compiled with
|
||||
@@ -410,8 +389,7 @@ C++ is case-sensitive. Did you spell it as `Setup()`?
|
||||
Similarly, sometimes people spell `SetUpTestSuite()` as `SetupTestSuite()` and
|
||||
wonder why it's never called.
|
||||
|
||||
|
||||
## I have several test suites which share the same test fixture logic, do I have to define a new test fixture class for each of them? This seems pretty tedious.
|
||||
## I have several test suites which share the same test fixture logic; do I have to define a new test fixture class for each of them? This seems pretty tedious.
|
||||
|
||||
You don't have to. Instead of
|
||||
|
||||
@@ -441,14 +419,14 @@ TEST_F(BarTest, Abc) { ... }
|
||||
TEST_F(BarTest, Def) { ... }
|
||||
```
|
||||
|
||||
## googletest output is buried in a whole bunch of LOG messages. What do I do?
|
||||
## GoogleTest output is buried in a whole bunch of LOG messages. What do I do?
|
||||
|
||||
The googletest output is meant to be a concise and human-friendly report. If
|
||||
your test generates textual output itself, it will mix with the googletest
|
||||
The GoogleTest output is meant to be a concise and human-friendly report. If
|
||||
your test generates textual output itself, it will mix with the GoogleTest
|
||||
output, making it hard to read. However, there is an easy solution to this
|
||||
problem.
|
||||
|
||||
Since `LOG` messages go to stderr, we decided to let googletest output go to
|
||||
Since `LOG` messages go to stderr, we decided to let GoogleTest output go to
|
||||
stdout. This way, you can easily separate the two using redirection. For
|
||||
example:
|
||||
|
||||
@@ -521,7 +499,7 @@ TEST(MyDeathTest, CompoundStatement) {
|
||||
|
||||
## I have a fixture class `FooTest`, but `TEST_F(FooTest, Bar)` gives me error ``"no matching function for call to `FooTest::FooTest()'"``. Why?
|
||||
|
||||
Googletest needs to be able to create objects of your test fixture class, so it
|
||||
GoogleTest needs to be able to create objects of your test fixture class, so it
|
||||
must have a default constructor. Normally the compiler will define one for you.
|
||||
However, there are cases where you have to define your own:
|
||||
|
||||
@@ -533,24 +511,11 @@ However, there are cases where you have to define your own:
|
||||
list of the constructor. (Early versions of `gcc` doesn't force you to
|
||||
initialize the const member. It's a bug that has been fixed in `gcc 4`.)
|
||||
|
||||
## Why does ASSERT_DEATH complain about previous threads that were already joined?
|
||||
## Why does GoogleTest require the entire test suite, instead of individual tests, to be named `*DeathTest` when it uses `ASSERT_DEATH`?
|
||||
|
||||
With the Linux pthread library, there is no turning back once you cross the line
|
||||
from a single thread to multiple threads. The first time you create a thread, a
|
||||
manager thread is created in addition, so you get 3, not 2, threads. Later when
|
||||
the thread you create joins the main thread, the thread count decrements by 1,
|
||||
but the manager thread will never be killed, so you still have 2 threads, which
|
||||
means you cannot safely run a death test.
|
||||
|
||||
The new NPTL thread library doesn't suffer from this problem, as it doesn't
|
||||
create a manager thread. However, if you don't control which machine your test
|
||||
runs on, you shouldn't depend on this.
|
||||
|
||||
## Why does googletest require the entire test suite, instead of individual tests, to be named *DeathTest when it uses ASSERT_DEATH?
|
||||
|
||||
googletest does not interleave tests from different test suites. That is, it
|
||||
GoogleTest does not interleave tests from different test suites. That is, it
|
||||
runs all tests in one test suite first, and then runs all tests in the next test
|
||||
suite, and so on. googletest does this because it needs to set up a test suite
|
||||
suite, and so on. GoogleTest does this because it needs to set up a test suite
|
||||
before the first test in it is run, and tear it down afterwards. Splitting up
|
||||
the test case would require multiple set-up and tear-down processes, which is
|
||||
inefficient and makes the semantics unclean.
|
||||
@@ -571,7 +536,7 @@ interleave tests from different test suites, we need to run all tests in the
|
||||
`FooTest` case before running any test in the `BarTest` case. This contradicts
|
||||
with the requirement to run `BarTest.DefDeathTest` before `FooTest.Uvw`.
|
||||
|
||||
## But I don't like calling my entire test suite \*DeathTest when it contains both death tests and non-death tests. What do I do?
|
||||
## But I don't like calling my entire test suite `*DeathTest` when it contains both death tests and non-death tests. What do I do?
|
||||
|
||||
You don't have to, but if you like, you may split up the test suite into
|
||||
`FooTest` and `FooDeathTest`, where the names make it clear that they are
|
||||
@@ -589,11 +554,11 @@ TEST_F(FooDeathTest, Uvw) { ... EXPECT_DEATH(...) ... }
|
||||
TEST_F(FooDeathTest, Xyz) { ... ASSERT_DEATH(...) ... }
|
||||
```
|
||||
|
||||
## googletest prints the LOG messages in a death test's child process only when the test fails. How can I see the LOG messages when the death test succeeds?
|
||||
## GoogleTest prints the LOG messages in a death test's child process only when the test fails. How can I see the LOG messages when the death test succeeds?
|
||||
|
||||
Printing the LOG messages generated by the statement inside `EXPECT_DEATH()`
|
||||
makes it harder to search for real problems in the parent's log. Therefore,
|
||||
googletest only prints them when the death test has failed.
|
||||
GoogleTest only prints them when the death test has failed.
|
||||
|
||||
If you really need to see such LOG messages, a workaround is to temporarily
|
||||
break the death test (e.g. by changing the regex pattern it is expected to
|
||||
@@ -608,11 +573,11 @@ defined such that we can print a value of `FooType`.
|
||||
|
||||
In addition, if `FooType` is declared in a name space, the `<<` operator also
|
||||
needs to be defined in the *same* name space. See
|
||||
[Tip of the Week #49](http://abseil.io/tips/49) for details.
|
||||
[Tip of the Week #49](https://abseil.io/tips/49) for details.
|
||||
|
||||
## How do I suppress the memory leak messages on Windows?
|
||||
|
||||
Since the statically initialized googletest singleton requires allocations on
|
||||
Since the statically initialized GoogleTest singleton requires allocations on
|
||||
the heap, the Visual C++ memory leak detector will report memory leaks at the
|
||||
end of the program run. The easiest way to avoid this is to use the
|
||||
`_CrtMemCheckpoint` and `_CrtMemDumpAllObjectsSince` calls to not report any
|
||||
@@ -626,13 +591,13 @@ things accordingly, you are leaking test-only logic into production code and
|
||||
there is no easy way to ensure that the test-only code paths aren't run by
|
||||
mistake in production. Such cleverness also leads to
|
||||
[Heisenbugs](https://en.wikipedia.org/wiki/Heisenbug). Therefore we strongly
|
||||
advise against the practice, and googletest doesn't provide a way to do it.
|
||||
advise against the practice, and GoogleTest doesn't provide a way to do it.
|
||||
|
||||
In general, the recommended way to cause the code to behave differently under
|
||||
test is [Dependency Injection](http://en.wikipedia.org/wiki/Dependency_injection). You can inject
|
||||
test is [Dependency Injection](https://en.wikipedia.org/wiki/Dependency_injection). You can inject
|
||||
different functionality from the test and from the production code. Since your
|
||||
production code doesn't link in the for-test logic at all (the
|
||||
[`testonly`](http://docs.bazel.build/versions/master/be/common-definitions.html#common.testonly) attribute for BUILD targets helps to ensure
|
||||
[`testonly`](https://docs.bazel.build/versions/master/be/common-definitions.html#common.testonly) attribute for BUILD targets helps to ensure
|
||||
that), there is no danger in accidentally running it.
|
||||
|
||||
However, if you *really*, *really*, *really* have no choice, and if you follow
|
||||
@@ -655,7 +620,7 @@ the `--gtest_also_run_disabled_tests` flag.
|
||||
Yes.
|
||||
|
||||
The rule is **all test methods in the same test suite must use the same fixture
|
||||
class.** This means that the following is **allowed** because both tests use the
|
||||
class**. This means that the following is **allowed** because both tests use the
|
||||
same fixture class (`::testing::Test`).
|
||||
|
||||
```c++
|
||||
@@ -673,7 +638,7 @@ TEST(CoolTest, DoSomething) {
|
||||
```
|
||||
|
||||
However, the following code is **not allowed** and will produce a runtime error
|
||||
from googletest because the test methods are using different test fixture
|
||||
from GoogleTest because the test methods are using different test fixture
|
||||
classes with the same test suite name.
|
||||
|
||||
```c++
|
||||
|
||||
@@ -8,7 +8,7 @@ Given
|
||||
|
||||
```cpp
|
||||
class Foo {
|
||||
...
|
||||
public:
|
||||
virtual ~Foo();
|
||||
virtual int GetSize() const = 0;
|
||||
virtual string Describe(const char* name) = 0;
|
||||
@@ -20,10 +20,10 @@ class Foo {
|
||||
(note that `~Foo()` **must** be virtual) we can define its mock as
|
||||
|
||||
```cpp
|
||||
#include "gmock/gmock.h"
|
||||
#include <gmock/gmock.h>
|
||||
|
||||
class MockFoo : public Foo {
|
||||
...
|
||||
public:
|
||||
MOCK_METHOD(int, GetSize, (), (const, override));
|
||||
MOCK_METHOD(string, Describe, (const char* name), (override));
|
||||
MOCK_METHOD(string, Describe, (int type), (override));
|
||||
@@ -58,7 +58,7 @@ To mock
|
||||
```cpp
|
||||
template <typename Elem>
|
||||
class StackInterface {
|
||||
...
|
||||
public:
|
||||
virtual ~StackInterface();
|
||||
virtual int GetSize() const = 0;
|
||||
virtual void Push(const Elem& x) = 0;
|
||||
@@ -71,7 +71,7 @@ class StackInterface {
|
||||
```cpp
|
||||
template <typename Elem>
|
||||
class MockStack : public StackInterface<Elem> {
|
||||
...
|
||||
public:
|
||||
MOCK_METHOD(int, GetSize, (), (const, override));
|
||||
MOCK_METHOD(void, Push, (const Elem& x), (override));
|
||||
};
|
||||
@@ -130,7 +130,7 @@ TEST(BarTest, DoesThis) {
|
||||
## Setting Default Actions {#OnCall}
|
||||
|
||||
gMock has a **built-in default action** for any function that returns `void`,
|
||||
`bool`, a numeric value, or a pointer. In C++11, it will additionally returns
|
||||
`bool`, a numeric value, or a pointer. In C++11, it additionally returns
|
||||
the default-constructed value, if one exists for the given type.
|
||||
|
||||
To customize the default action for functions with return type `T`, use
|
||||
@@ -140,7 +140,7 @@ To customize the default action for functions with return type `T`, use
|
||||
// Sets the default action for return type std::unique_ptr<Buzz> to
|
||||
// creating a new Buzz every time.
|
||||
DefaultValue<std::unique_ptr<Buzz>>::SetFactory(
|
||||
[] { return MakeUnique<Buzz>(AccessLevel::kInternal); });
|
||||
[] { return std::make_unique<Buzz>(AccessLevel::kInternal); });
|
||||
|
||||
// When this fires, the default action of MakeBuzz() will run, which
|
||||
// will return a new Buzz object.
|
||||
@@ -153,7 +153,7 @@ To customize the default action for functions with return type `T`, use
|
||||
EXPECT_NE(buzz1, buzz2);
|
||||
|
||||
// Resets the default action for return type std::unique_ptr<Buzz>,
|
||||
// to avoid interfere with other tests.
|
||||
// to avoid interfering with other tests.
|
||||
DefaultValue<std::unique_ptr<Buzz>>::Clear();
|
||||
```
|
||||
|
||||
@@ -230,7 +230,7 @@ class MockFunction<R(A1, ..., An)> {
|
||||
};
|
||||
```
|
||||
|
||||
See this [recipe](gmock_cook_book.md#using-check-points) for one application of
|
||||
See this [recipe](gmock_cook_book.md#UsingCheckPoints) for one application of
|
||||
it.
|
||||
|
||||
## Flags
|
||||
|
||||
+262
-114
@@ -177,7 +177,7 @@ class StackInterface {
|
||||
template <typename Elem>
|
||||
class MockStack : public StackInterface<Elem> {
|
||||
...
|
||||
MOCK_METHOD(int, GetSize, (), (override));
|
||||
MOCK_METHOD(int, GetSize, (), (const, override));
|
||||
MOCK_METHOD(void, Push, (const Elem& x), (override));
|
||||
};
|
||||
```
|
||||
@@ -285,6 +285,10 @@ If you are concerned about the performance overhead incurred by virtual
|
||||
functions, and profiling confirms your concern, you can combine this with the
|
||||
recipe for [mocking non-virtual methods](#MockingNonVirtualMethods).
|
||||
|
||||
Alternatively, instead of introducing a new interface, you can rewrite your code
|
||||
to accept a std::function instead of the free function, and then use
|
||||
[MockFunction](#MockFunction) to mock the std::function.
|
||||
|
||||
### Old-Style `MOCK_METHODn` Macros
|
||||
|
||||
Before the generic `MOCK_METHOD` macro
|
||||
@@ -392,8 +396,7 @@ Old macros and their new equivalents:
|
||||
If a mock method has no `EXPECT_CALL` spec but is called, we say that it's an
|
||||
"uninteresting call", and the default action (which can be specified using
|
||||
`ON_CALL()`) of the method will be taken. Currently, an uninteresting call will
|
||||
also by default cause gMock to print a warning. (In the future, we might remove
|
||||
this warning by default.)
|
||||
also by default cause gMock to print a warning.
|
||||
|
||||
However, sometimes you may want to ignore these uninteresting calls, and
|
||||
sometimes you may want to treat them as errors. gMock lets you make the decision
|
||||
@@ -694,9 +697,9 @@ TEST(AbcTest, Xyz) {
|
||||
EXPECT_CALL(foo, DoThat(_, _));
|
||||
|
||||
int n = 0;
|
||||
EXPECT_EQ('+', foo.DoThis(5)); // FakeFoo::DoThis() is invoked.
|
||||
EXPECT_EQ(foo.DoThis(5), '+'); // FakeFoo::DoThis() is invoked.
|
||||
foo.DoThat("Hi", &n); // FakeFoo::DoThat() is invoked.
|
||||
EXPECT_EQ(2, n);
|
||||
EXPECT_EQ(n, 2);
|
||||
}
|
||||
```
|
||||
|
||||
@@ -897,15 +900,16 @@ using ::testing::Not;
|
||||
|
||||
Matchers are function objects, and parametrized matchers can be composed just
|
||||
like any other function. However because their types can be long and rarely
|
||||
provide meaningful information, it can be easier to express them with C++14
|
||||
generic lambdas to avoid specifying types. For example,
|
||||
provide meaningful information, it can be easier to express them with template
|
||||
parameters and `auto`. For example,
|
||||
|
||||
```cpp
|
||||
using ::testing::Contains;
|
||||
using ::testing::Property;
|
||||
|
||||
inline constexpr auto HasFoo = [](const auto& f) {
|
||||
return Property(&MyClass::foo, Contains(f));
|
||||
template <typename SubMatcher>
|
||||
inline constexpr auto HasFoo(const SubMatcher& sub_matcher) {
|
||||
return Property("foo", &MyClass::foo, Contains(sub_matcher));
|
||||
};
|
||||
...
|
||||
EXPECT_THAT(x, HasFoo("blah"));
|
||||
@@ -933,8 +937,8 @@ casts a matcher `m` to type `Matcher<T>`. To ensure safety, gMock checks that
|
||||
floating-point numbers), the conversion from `T` to `U` is not lossy (in
|
||||
other words, any value representable by `T` can also be represented by `U`);
|
||||
and
|
||||
3. When `U` is a reference, `T` must also be a reference (as the underlying
|
||||
matcher may be interested in the address of the `U` value).
|
||||
3. When `U` is a non-const reference, `T` must also be a reference (as the
|
||||
underlying matcher may be interested in the address of the `U` value).
|
||||
|
||||
The code won't compile if any of these conditions isn't met.
|
||||
|
||||
@@ -1084,7 +1088,7 @@ using ::testing::Lt;
|
||||
```
|
||||
|
||||
says that `Blah` will be called with arguments `x`, `y`, and `z` where `x < y <
|
||||
z`. Note that in this example, it wasn't necessary specify the positional
|
||||
z`. Note that in this example, it wasn't necessary to specify the positional
|
||||
matchers.
|
||||
|
||||
As a convenience and example, gMock provides some matchers for 2-tuples,
|
||||
@@ -1126,11 +1130,11 @@ using STL's `<functional>` header is just painful). For example, here's a
|
||||
predicate that's satisfied by any number that is >= 0, <= 100, and != 50:
|
||||
|
||||
```cpp
|
||||
using testing::AllOf;
|
||||
using testing::Ge;
|
||||
using testing::Le;
|
||||
using testing::Matches;
|
||||
using testing::Ne;
|
||||
using ::testing::AllOf;
|
||||
using ::testing::Ge;
|
||||
using ::testing::Le;
|
||||
using ::testing::Matches;
|
||||
using ::testing::Ne;
|
||||
...
|
||||
Matches(AllOf(Ge(0), Le(100), Ne(50)))
|
||||
```
|
||||
@@ -1159,7 +1163,7 @@ int IsEven(int n) { return (n % 2) == 0 ? 1 : 0; }
|
||||
```
|
||||
|
||||
Note that the predicate function / functor doesn't have to return `bool`. It
|
||||
works as long as the return value can be used as the condition in in statement
|
||||
works as long as the return value can be used as the condition in the statement
|
||||
`if (condition) ...`.
|
||||
|
||||
### Matching Arguments that Are Not Copyable
|
||||
@@ -1300,23 +1304,27 @@ What if you have a pointer to pointer? You guessed it - you can use nested
|
||||
`Pointee(Pointee(Lt(3)))` matches a pointer that points to a pointer that points
|
||||
to a number less than 3 (what a mouthful...).
|
||||
|
||||
### Testing a Certain Property of an Object
|
||||
### Defining a Custom Matcher Class {#CustomMatcherClass}
|
||||
|
||||
Sometimes you want to specify that an object argument has a certain property,
|
||||
but there is no existing matcher that does this. If you want good error
|
||||
messages, you should [define a matcher](#NewMatchers). If you want to do it
|
||||
quick and dirty, you could get away with writing an ordinary function.
|
||||
Most matchers can be simply defined using [the MATCHER* macros](#NewMatchers),
|
||||
which are terse and flexible, and produce good error messages. However, these
|
||||
macros are not very explicit about the interfaces they create and are not always
|
||||
suitable, especially for matchers that will be widely reused.
|
||||
|
||||
Let's say you have a mock function that takes an object of type `Foo`, which has
|
||||
an `int bar()` method and an `int baz()` method, and you want to constrain that
|
||||
the argument's `bar()` value plus its `baz()` value is a given number. Here's
|
||||
how you can define a matcher to do it:
|
||||
For more advanced cases, you may need to define your own matcher class. A custom
|
||||
matcher allows you to test a specific invariant property of that object. Let's
|
||||
take a look at how to do so.
|
||||
|
||||
Imagine you have a mock function that takes an object of type `Foo`, which has
|
||||
an `int bar()` method and an `int baz()` method. You want to constrain that the
|
||||
argument's `bar()` value plus its `baz()` value is a given number. (This is an
|
||||
invariant.) Here's how we can write and use a matcher class to do so:
|
||||
|
||||
```cpp
|
||||
using ::testing::Matcher;
|
||||
|
||||
class BarPlusBazEqMatcher {
|
||||
public:
|
||||
using is_gtest_matcher = void;
|
||||
|
||||
explicit BarPlusBazEqMatcher(int expected_sum)
|
||||
: expected_sum_(expected_sum) {}
|
||||
|
||||
@@ -1325,23 +1333,24 @@ class BarPlusBazEqMatcher {
|
||||
return (foo.bar() + foo.baz()) == expected_sum_;
|
||||
}
|
||||
|
||||
void DescribeTo(std::ostream& os) const {
|
||||
os << "bar() + baz() equals " << expected_sum_;
|
||||
void DescribeTo(std::ostream* os) const {
|
||||
*os << "bar() + baz() equals " << expected_sum_;
|
||||
}
|
||||
|
||||
void DescribeNegationTo(std::ostream& os) const {
|
||||
os << "bar() + baz() does not equal " << expected_sum_;
|
||||
void DescribeNegationTo(std::ostream* os) const {
|
||||
*os << "bar() + baz() does not equal " << expected_sum_;
|
||||
}
|
||||
private:
|
||||
const int expected_sum_;
|
||||
};
|
||||
|
||||
Matcher<const Foo&> BarPlusBazEq(int expected_sum) {
|
||||
::testing::Matcher<const Foo&> BarPlusBazEq(int expected_sum) {
|
||||
return BarPlusBazEqMatcher(expected_sum);
|
||||
}
|
||||
|
||||
...
|
||||
EXPECT_CALL(..., DoThis(BarPlusBazEq(5)))...;
|
||||
Foo foo;
|
||||
EXPECT_THAT(foo, BarPlusBazEq(5))...;
|
||||
```
|
||||
|
||||
### Matching Containers
|
||||
@@ -1420,11 +1429,12 @@ Use `Pair` when comparing maps or other associative containers.
|
||||
{% raw %}
|
||||
|
||||
```cpp
|
||||
using testing::ElementsAre;
|
||||
using testing::Pair;
|
||||
using ::testing::UnorderedElementsAre;
|
||||
using ::testing::Pair;
|
||||
...
|
||||
std::map<string, int> m = {{"a", 1}, {"b", 2}, {"c", 3}};
|
||||
EXPECT_THAT(m, ElementsAre(Pair("a", 1), Pair("b", 2), Pair("c", 3)));
|
||||
absl::flat_hash_map<string, int> m = {{"a", 1}, {"b", 2}, {"c", 3}};
|
||||
EXPECT_THAT(m, UnorderedElementsAre(
|
||||
Pair("a", 1), Pair("b", 2), Pair("c", 3)));
|
||||
```
|
||||
|
||||
{% endraw %}
|
||||
@@ -1441,8 +1451,8 @@ using testing::Pair;
|
||||
* If the container is passed by pointer instead of by reference, just write
|
||||
`Pointee(ElementsAre*(...))`.
|
||||
* The order of elements *matters* for `ElementsAre*()`. If you are using it
|
||||
with containers whose element order are undefined (e.g. `hash_map`) you
|
||||
should use `WhenSorted` around `ElementsAre`.
|
||||
with containers whose element order are undefined (such as a
|
||||
`std::unordered_map`) you should use `UnorderedElementsAre`.
|
||||
|
||||
### Sharing Matchers
|
||||
|
||||
@@ -1452,7 +1462,7 @@ the pointer is copied. When the last matcher that references the implementation
|
||||
object dies, the implementation object will be deleted.
|
||||
|
||||
Therefore, if you have some complex matcher that you want to use again and
|
||||
again, there is no need to build it everytime. Just assign it to a matcher
|
||||
again, there is no need to build it every time. Just assign it to a matcher
|
||||
variable and use that variable repeatedly! For example,
|
||||
|
||||
```cpp
|
||||
@@ -1754,7 +1764,7 @@ specifies the following DAG (where `s1` is `A -> B`, and `s2` is `A -> C -> D`):
|
||||
|
|
||||
A ---|
|
||||
|
|
||||
+---> C ---> D
|
||||
+---> C ---> D
|
||||
```
|
||||
|
||||
This means that A must occur before B and C, and C must occur before D. There's
|
||||
@@ -1852,7 +1862,7 @@ error. So, what shall you do?
|
||||
Though you may be tempted, DO NOT use `std::ref()`:
|
||||
|
||||
```cpp
|
||||
using testing::Return;
|
||||
using ::testing::Return;
|
||||
|
||||
class MockFoo : public Foo {
|
||||
public:
|
||||
@@ -1864,7 +1874,7 @@ class MockFoo : public Foo {
|
||||
EXPECT_CALL(foo, GetValue())
|
||||
.WillRepeatedly(Return(std::ref(x))); // Wrong!
|
||||
x = 42;
|
||||
EXPECT_EQ(42, foo.GetValue());
|
||||
EXPECT_EQ(foo.GetValue(), 42);
|
||||
```
|
||||
|
||||
Unfortunately, it doesn't work here. The above code will fail with error:
|
||||
@@ -1886,20 +1896,20 @@ the expectation is set, and `Return(std::ref(x))` will always return 0.
|
||||
returns the value pointed to by `pointer` at the time the action is *executed*:
|
||||
|
||||
```cpp
|
||||
using testing::ReturnPointee;
|
||||
using ::testing::ReturnPointee;
|
||||
...
|
||||
int x = 0;
|
||||
MockFoo foo;
|
||||
EXPECT_CALL(foo, GetValue())
|
||||
.WillRepeatedly(ReturnPointee(&x)); // Note the & here.
|
||||
x = 42;
|
||||
EXPECT_EQ(42, foo.GetValue()); // This will succeed now.
|
||||
EXPECT_EQ(foo.GetValue(), 42); // This will succeed now.
|
||||
```
|
||||
|
||||
### Combining Actions
|
||||
|
||||
Want to do more than one thing when a function is called? That's fine. `DoAll()`
|
||||
allow you to do sequence of actions every time. Only the return value of the
|
||||
allows you to do a sequence of actions every time. Only the return value of the
|
||||
last action in the sequence will be used.
|
||||
|
||||
```cpp
|
||||
@@ -1918,6 +1928,12 @@ class MockFoo : public Foo {
|
||||
action_n));
|
||||
```
|
||||
|
||||
The return value of the last action **must** match the return type of the mocked
|
||||
method. In the example above, `action_n` could be `Return(true)`, or a lambda
|
||||
that returns a `bool`, but not `SaveArg`, which returns `void`. Otherwise the
|
||||
signature of `DoAll` would not match the signature expected by `WillOnce`, which
|
||||
is the signature of the mocked method, and it wouldn't compile.
|
||||
|
||||
### Verifying Complex Arguments {#SaveArgVerify}
|
||||
|
||||
If you want to verify that a method is called with a particular argument but the
|
||||
@@ -1980,6 +1996,7 @@ If the mock method also needs to return a value as well, you can chain
|
||||
|
||||
```cpp
|
||||
using ::testing::_;
|
||||
using ::testing::DoAll;
|
||||
using ::testing::Return;
|
||||
using ::testing::SetArgPointee;
|
||||
|
||||
@@ -2033,10 +2050,7 @@ class MockRolodex : public Rolodex {
|
||||
}
|
||||
...
|
||||
MockRolodex rolodex;
|
||||
vector<string> names;
|
||||
names.push_back("George");
|
||||
names.push_back("John");
|
||||
names.push_back("Thomas");
|
||||
vector<string> names = {"George", "John", "Thomas"};
|
||||
EXPECT_CALL(rolodex, GetNames(_))
|
||||
.WillOnce(SetArrayArgument<0>(names.begin(), names.end()));
|
||||
```
|
||||
@@ -2257,7 +2271,7 @@ TEST_F(FooTest, Test) {
|
||||
|
||||
EXPECT_CALL(foo, DoThis(2))
|
||||
.WillOnce(Invoke(NewPermanentCallback(SignOfSum, 5)));
|
||||
EXPECT_EQ('+', foo.DoThis(2)); // Invokes SignOfSum(5, 2).
|
||||
EXPECT_EQ(foo.DoThis(2), '+'); // Invokes SignOfSum(5, 2).
|
||||
}
|
||||
```
|
||||
|
||||
@@ -2604,7 +2618,7 @@ efficient. When the last action that references the implementation object dies,
|
||||
the implementation object will be deleted.
|
||||
|
||||
If you have some complex action that you want to use again and again, you may
|
||||
not have to build it from scratch everytime. If the action doesn't have an
|
||||
not have to build it from scratch every time. If the action doesn't have an
|
||||
internal state (i.e. if it always does the same thing no matter how many times
|
||||
it has been called), you can assign it to an action variable and use that
|
||||
variable repeatedly. For example:
|
||||
@@ -2633,8 +2647,8 @@ action will exhibit different behaviors. Example:
|
||||
.WillRepeatedly(IncrementCounter(0));
|
||||
foo.DoThis(); // Returns 1.
|
||||
foo.DoThis(); // Returns 2.
|
||||
foo.DoThat(); // Returns 1 - Blah() uses a different
|
||||
// counter than Bar()'s.
|
||||
foo.DoThat(); // Returns 1 - DoThat() uses a different
|
||||
// counter than DoThis()'s.
|
||||
```
|
||||
|
||||
versus
|
||||
@@ -2764,36 +2778,33 @@ returns a null `unique_ptr`, that’s what you’ll get if you don’t specify a
|
||||
action:
|
||||
|
||||
```cpp
|
||||
using ::testing::IsNull;
|
||||
...
|
||||
// Use the default action.
|
||||
EXPECT_CALL(mock_buzzer_, MakeBuzz("hello"));
|
||||
|
||||
// Triggers the previous EXPECT_CALL.
|
||||
EXPECT_EQ(nullptr, mock_buzzer_.MakeBuzz("hello"));
|
||||
EXPECT_THAT(mock_buzzer_.MakeBuzz("hello"), IsNull());
|
||||
```
|
||||
|
||||
If you are not happy with the default action, you can tweak it as usual; see
|
||||
[Setting Default Actions](#OnCall).
|
||||
|
||||
If you just need to return a pre-defined move-only value, you can use the
|
||||
`Return(ByMove(...))` action:
|
||||
If you just need to return a move-only value, you can use it in combination with
|
||||
`WillOnce`. For example:
|
||||
|
||||
```cpp
|
||||
// When this fires, the unique_ptr<> specified by ByMove(...) will
|
||||
// be returned.
|
||||
EXPECT_CALL(mock_buzzer_, MakeBuzz("world"))
|
||||
.WillOnce(Return(ByMove(MakeUnique<Buzz>(AccessLevel::kInternal))));
|
||||
|
||||
EXPECT_NE(nullptr, mock_buzzer_.MakeBuzz("world"));
|
||||
EXPECT_CALL(mock_buzzer_, MakeBuzz("hello"))
|
||||
.WillOnce(Return(std::make_unique<Buzz>(AccessLevel::kInternal)));
|
||||
EXPECT_NE(nullptr, mock_buzzer_.MakeBuzz("hello"));
|
||||
```
|
||||
|
||||
Note that `ByMove()` is essential here - if you drop it, the code won’t compile.
|
||||
|
||||
Quiz time! What do you think will happen if a `Return(ByMove(...))` action is
|
||||
performed more than once (e.g. you write `...
|
||||
.WillRepeatedly(Return(ByMove(...)));`)? Come think of it, after the first time
|
||||
the action runs, the source value will be consumed (since it’s a move-only
|
||||
value), so the next time around, there’s no value to move from -- you’ll get a
|
||||
run-time error that `Return(ByMove(...))` can only be run once.
|
||||
Quiz time! What do you think will happen if a `Return` action is performed more
|
||||
than once (e.g. you write `... .WillRepeatedly(Return(std::move(...)));`)? Come
|
||||
think of it, after the first time the action runs, the source value will be
|
||||
consumed (since it’s a move-only value), so the next time around, there’s no
|
||||
value to move from -- you’ll get a run-time error that `Return(std::move(...))`
|
||||
can only be run once.
|
||||
|
||||
If you need your mock method to do more than just moving a pre-defined value,
|
||||
remember that you can always use a lambda or a callable object, which can do
|
||||
@@ -2802,7 +2813,7 @@ pretty much anything you want:
|
||||
```cpp
|
||||
EXPECT_CALL(mock_buzzer_, MakeBuzz("x"))
|
||||
.WillRepeatedly([](StringPiece text) {
|
||||
return MakeUnique<Buzz>(AccessLevel::kInternal);
|
||||
return std::make_unique<Buzz>(AccessLevel::kInternal);
|
||||
});
|
||||
|
||||
EXPECT_NE(nullptr, mock_buzzer_.MakeBuzz("x"));
|
||||
@@ -2810,7 +2821,7 @@ pretty much anything you want:
|
||||
```
|
||||
|
||||
Every time this `EXPECT_CALL` fires, a new `unique_ptr<Buzz>` will be created
|
||||
and returned. You cannot do this with `Return(ByMove(...))`.
|
||||
and returned. You cannot do this with `Return(std::make_unique<...>(...))`.
|
||||
|
||||
That covers returning move-only values; but how do we work with methods
|
||||
accepting move-only arguments? The answer is that they work normally, although
|
||||
@@ -2821,7 +2832,7 @@ can always use `Return`, or a [lambda or functor](#FunctionsAsActions):
|
||||
using ::testing::Unused;
|
||||
|
||||
EXPECT_CALL(mock_buzzer_, ShareBuzz(NotNull(), _)).WillOnce(Return(true));
|
||||
EXPECT_TRUE(mock_buzzer_.ShareBuzz(MakeUnique<Buzz>(AccessLevel::kInternal)),
|
||||
EXPECT_TRUE(mock_buzzer_.ShareBuzz(std::make_unique<Buzz>(AccessLevel::kInternal)),
|
||||
0);
|
||||
|
||||
EXPECT_CALL(mock_buzzer_, ShareBuzz(_, _)).WillOnce(
|
||||
@@ -2865,7 +2876,7 @@ method:
|
||||
// When one calls ShareBuzz() on the MockBuzzer like this, the call is
|
||||
// forwarded to DoShareBuzz(), which is mocked. Therefore this statement
|
||||
// will trigger the above EXPECT_CALL.
|
||||
mock_buzzer_.ShareBuzz(MakeUnique<Buzz>(AccessLevel::kInternal), 0);
|
||||
mock_buzzer_.ShareBuzz(std::make_unique<Buzz>(AccessLevel::kInternal), 0);
|
||||
```
|
||||
|
||||
### Making the Compilation Faster
|
||||
@@ -3190,11 +3201,11 @@ You can unlock this power by running your test with the `--gmock_verbose=info`
|
||||
flag. For example, given the test program:
|
||||
|
||||
```cpp
|
||||
#include "gmock/gmock.h"
|
||||
#include <gmock/gmock.h>
|
||||
|
||||
using testing::_;
|
||||
using testing::HasSubstr;
|
||||
using testing::Return;
|
||||
using ::testing::_;
|
||||
using ::testing::HasSubstr;
|
||||
using ::testing::Return;
|
||||
|
||||
class MockFoo {
|
||||
public:
|
||||
@@ -3302,7 +3313,7 @@ For convenience, we allow the description string to be empty (`""`), in which
|
||||
case gMock will use the sequence of words in the matcher name as the
|
||||
description.
|
||||
|
||||
For example:
|
||||
#### Basic Example
|
||||
|
||||
```cpp
|
||||
MATCHER(IsDivisibleBy7, "") { return (arg % 7) == 0; }
|
||||
@@ -3340,6 +3351,8 @@ If the above assertions fail, they will print something like:
|
||||
where the descriptions `"is divisible by 7"` and `"not (is divisible by 7)"` are
|
||||
automatically calculated from the matcher name `IsDivisibleBy7`.
|
||||
|
||||
#### Adding Custom Failure Messages
|
||||
|
||||
As you may have noticed, the auto-generated descriptions (especially those for
|
||||
the negation) may not be so great. You can always override them with a `string`
|
||||
expression of your own:
|
||||
@@ -3373,21 +3386,84 @@ With this definition, the above assertion will give a better message:
|
||||
Actual: 27 (the remainder is 6)
|
||||
```
|
||||
|
||||
#### `MatchAndExplain`
|
||||
|
||||
You should let `MatchAndExplain()` print *any additional information* that can
|
||||
help a user understand the match result. Note that it should explain why the
|
||||
match succeeds in case of a success (unless it's obvious) - this is useful when
|
||||
the matcher is used inside `Not()`. There is no need to print the argument value
|
||||
itself, as gMock already prints it for you.
|
||||
|
||||
{: .callout .note}
|
||||
NOTE: The type of the value being matched (`arg_type`) is determined by the
|
||||
context in which you use the matcher and is supplied to you by the compiler, so
|
||||
you don't need to worry about declaring it (nor can you). This allows the
|
||||
matcher to be polymorphic. For example, `IsDivisibleBy7()` can be used to match
|
||||
any type where the value of `(arg % 7) == 0` can be implicitly converted to a
|
||||
`bool`. In the `Bar(IsDivisibleBy7())` example above, if method `Bar()` takes an
|
||||
`int`, `arg_type` will be `int`; if it takes an `unsigned long`, `arg_type` will
|
||||
be `unsigned long`; and so on.
|
||||
#### Argument Types
|
||||
|
||||
The type of the value being matched (`arg_type`) is determined by the context in
|
||||
which you use the matcher and is supplied to you by the compiler, so you don't
|
||||
need to worry about declaring it (nor can you). This allows the matcher to be
|
||||
polymorphic. For example, `IsDivisibleBy7()` can be used to match any type where
|
||||
the value of `(arg % 7) == 0` can be implicitly converted to a `bool`. In the
|
||||
`Bar(IsDivisibleBy7())` example above, if method `Bar()` takes an `int`,
|
||||
`arg_type` will be `int`; if it takes an `unsigned long`, `arg_type` will be
|
||||
`unsigned long`; and so on.
|
||||
|
||||
#### Anti-pattern: Using EXPECT_ Statements in Matchers
|
||||
|
||||
Using `EXPECT_...` statements inside custom matcher definitions is an
|
||||
**anti-pattern** and should be avoided.
|
||||
|
||||
While it might appear to write matchers more concisely and generate informative
|
||||
messages, this pattern has critical issues:
|
||||
|
||||
1. **Negation Breakage (`Not`):** If wrapped in `Not(IsDivisibleBy7())`,
|
||||
evaluating it still triggers the internal `EXPECT_EQ`, registering a test
|
||||
failure on the runner even when the overall assertion is expected to
|
||||
succeed.
|
||||
2. **Composition / Container Breakage (`AnyOf`, `AllOf`, `Contains`):** When
|
||||
composed or used inside container matchers, elements that are expected
|
||||
mismatches will trigger the internal `EXPECT_` and register spurious
|
||||
failures.
|
||||
3. **ASSERT_* compilation errors:** `ASSERT_*` macros use `return;` to abort
|
||||
from a void function. Since matchers return `bool`, using `ASSERT_` inside
|
||||
them triggers a compilation error.
|
||||
4. **Purity Violations:** Matchers must be functionally pure (side-effect
|
||||
free), whereas registering global failures is a major side effect.
|
||||
5. **Line Number Confusion:** Failure reports point to the matcher's definition
|
||||
line rather than the calling `EXPECT_THAT`
|
||||
line.
|
||||
|
||||
##### The Anti-Pattern
|
||||
|
||||
```cpp
|
||||
// Anti-pattern: Do not do this!
|
||||
MATCHER(IsDivisibleBy7, "") {
|
||||
const auto remainder = arg % 7;
|
||||
EXPECT_EQ(remainder, 0); // Spurious failures if negated/composed!
|
||||
return true;
|
||||
}
|
||||
```
|
||||
|
||||
##### The Correct Solution
|
||||
|
||||
To write concise matchers that delegate to other matchers and safely propagate
|
||||
the mismatch explanation, use **`::testing::ExplainMatchResult`** instead,
|
||||
passing it the sub-matcher, the value to check, and the `result_listener`:
|
||||
|
||||
```cpp
|
||||
MATCHER(IsDivisibleBy7, "") {
|
||||
const auto remainder = arg % 7;
|
||||
return ::testing::ExplainMatchResult(::testing::Eq(0), remainder,
|
||||
result_listener);
|
||||
}
|
||||
```
|
||||
|
||||
If you write a test that includes the line:
|
||||
|
||||
```cpp
|
||||
EXPECT_THAT(28, Not(IsDivisibleBy7()));
|
||||
```
|
||||
|
||||
it will correctly report the mismatch, properly point to the `EXPECT_THAT` line
|
||||
number, and support negation (`Not`) and composition (`AllOf`, `AnyOf`, etc.)
|
||||
without registering spurious failures.
|
||||
|
||||
### Writing New Parameterized Matchers Quickly
|
||||
|
||||
@@ -3526,12 +3602,17 @@ general leads to better compiler error messages that pay off in the long run.
|
||||
They also allow overloading matchers based on parameter types (as opposed to
|
||||
just based on the number of parameters).
|
||||
|
||||
### Writing New Monomorphic Matchers
|
||||
### Writing New Monomorphic Matchers {#MonomorphicMatchers}
|
||||
|
||||
A matcher of argument type `T` implements the matcher interface for `T` and does
|
||||
two things: it tests whether a value of type `T` matches the matcher, and can
|
||||
describe what kind of values it matches. The latter ability is used for
|
||||
generating readable error messages when expectations are violated.
|
||||
A matcher of type `testing::Matcher<T>` implements the matcher interface for `T`
|
||||
and does two things: it tests whether a value of type `T` matches the matcher,
|
||||
and can describe what kind of values it matches. The latter ability is used for
|
||||
generating readable error messages when expectations are violated. Some matchers
|
||||
can even explain why it matches or doesn't match a certain value, which can be
|
||||
helpful when the reason isn't obvious.
|
||||
|
||||
Because a matcher of type `testing::Matcher<T>` for a particular type `T` can
|
||||
only be used to match a value of type `T`, we call it "monomorphic."
|
||||
|
||||
A matcher of `T` must declare a typedef like:
|
||||
|
||||
@@ -3546,7 +3627,7 @@ and supports the following operations:
|
||||
bool matched = matcher.MatchAndExplain(value, maybe_os);
|
||||
// where `value` is of type `T` and
|
||||
// `maybe_os` is of type `std::ostream*`, where it can be null if the caller
|
||||
// is not interested in there textual explanation.
|
||||
// is not interested in the textual explanation.
|
||||
|
||||
matcher.DescribeTo(os);
|
||||
matcher.DescribeNegationTo(os);
|
||||
@@ -3621,10 +3702,18 @@ Expected: is divisible by 7
|
||||
Tip: for convenience, `MatchAndExplain()` can take a `MatchResultListener*`
|
||||
instead of `std::ostream*`.
|
||||
|
||||
### Writing New Polymorphic Matchers
|
||||
### Writing New Polymorphic Matchers {#PolymorphicMatchers}
|
||||
|
||||
Expanding what we learned above to *polymorphic* matchers is now just as simple
|
||||
as adding templates in the right place.
|
||||
Unlike a monomorphic matcher, which can only be used to match a value of a
|
||||
particular type, a *polymorphic* matcher is one that can be used to match values
|
||||
of multiple types. For example, `Eq(5)` is a polymorphic matcher as it can be
|
||||
used to match an `int`, a `double`, a `float`, and so on. You should think of a
|
||||
polymorphic matcher as a *matcher factory* as opposed to a
|
||||
`testing::Matcher<SomeType>` - itself is not an actual matcher, but can be
|
||||
implicitly converted to a `testing::Matcher<SomeType>` depending on the context.
|
||||
|
||||
Expanding what we learned above to polymorphic matchers is now as simple as
|
||||
adding templates in the right place.
|
||||
|
||||
```cpp
|
||||
|
||||
@@ -3750,6 +3839,26 @@ virtual.
|
||||
Like in a monomorphic matcher, you may explain the match result by streaming
|
||||
additional information to the `listener` argument in `MatchAndExplain()`.
|
||||
|
||||
### Implementing Composite Matchers {#CompositeMatchers}
|
||||
|
||||
Sometimes we want to define a matcher that takes other matchers as parameters.
|
||||
For example, `DistanceFrom(target, m)` is a polymorphic matcher that takes a
|
||||
matcher `m` as a parameter. It tests that the distance from `target` to the
|
||||
value being matched satisfies sub-matcher `m`.
|
||||
|
||||
If you are implementing such a composite matcher, you'll need to generate the
|
||||
description of the matcher based on the description(s) of its sub-matcher(s).
|
||||
You can see the implementation of `DistanceFrom()` in
|
||||
`googlemock/include/gmock/gmock-matchers.h` for an example. In particular, pay
|
||||
attention to `DistanceFromMatcherImpl`. Notice that it stores the sub-matcher as
|
||||
a `const Matcher<const Distance&> distance_matcher_` instead of a polymorphic
|
||||
matcher - this allows it to call `distance_matcher_.DescribeTo(os)` to describe
|
||||
the sub-matcher. If the sub-matcher is stored as a polymorphic matcher instead,
|
||||
it would not be possible to get its description as in general polymorphic
|
||||
matchers don't know how to describe themselves - they are matcher factories
|
||||
instead of actual matchers; only after being converted to `Matcher<SomeType>`
|
||||
can they be described.
|
||||
|
||||
### Writing New Cardinalities
|
||||
|
||||
A cardinality is used in `Times()` to tell gMock how many times you expect a
|
||||
@@ -3809,35 +3918,74 @@ Cardinality EvenNumber() {
|
||||
.Times(EvenNumber());
|
||||
```
|
||||
|
||||
### Writing New Actions Quickly {#QuickNewActions}
|
||||
### Writing New Actions {#QuickNewActions}
|
||||
|
||||
If the built-in actions don't work for you, you can easily define your own one.
|
||||
Just define a functor class with a (possibly templated) call operator, matching
|
||||
the signature of your action.
|
||||
All you need is a call operator with a signature compatible with the mocked
|
||||
function. So you can use a lambda:
|
||||
|
||||
```cpp
|
||||
struct Increment {
|
||||
template <typename T>
|
||||
T operator()(T* arg) {
|
||||
return ++(*arg);
|
||||
}
|
||||
}
|
||||
MockFunction<int(int)> mock;
|
||||
EXPECT_CALL(mock, Call).WillOnce([](const int input) { return input * 7; });
|
||||
EXPECT_EQ(mock.AsStdFunction()(2), 14);
|
||||
```
|
||||
|
||||
The same approach works with stateful functors (or any callable, really):
|
||||
Or a struct with a call operator (even a templated one):
|
||||
|
||||
```
|
||||
```cpp
|
||||
struct MultiplyBy {
|
||||
template <typename T>
|
||||
T operator()(T arg) { return arg * multiplier; }
|
||||
|
||||
int multiplier;
|
||||
}
|
||||
};
|
||||
|
||||
// Then use:
|
||||
// EXPECT_CALL(...).WillOnce(MultiplyBy{7});
|
||||
```
|
||||
|
||||
It's also fine for the callable to take no arguments, ignoring the arguments
|
||||
supplied to the mock function:
|
||||
|
||||
```cpp
|
||||
MockFunction<int(int)> mock;
|
||||
EXPECT_CALL(mock, Call).WillOnce([] { return 17; });
|
||||
EXPECT_EQ(mock.AsStdFunction()(0), 17);
|
||||
```
|
||||
|
||||
When used with `WillOnce`, the callable can assume it will be called at most
|
||||
once and is allowed to be a move-only type:
|
||||
|
||||
```cpp
|
||||
// An action that contains move-only types and has an &&-qualified operator,
|
||||
// demanding in the type system that it be called at most once. This can be
|
||||
// used with WillOnce, but the compiler will reject it if handed to
|
||||
// WillRepeatedly.
|
||||
struct MoveOnlyAction {
|
||||
std::unique_ptr<int> move_only_state;
|
||||
std::unique_ptr<int> operator()() && { return std::move(move_only_state); }
|
||||
};
|
||||
|
||||
MockFunction<std::unique_ptr<int>()> mock;
|
||||
EXPECT_CALL(mock, Call).WillOnce(MoveOnlyAction{std::make_unique<int>(17)});
|
||||
EXPECT_THAT(mock.AsStdFunction()(), Pointee(Eq(17)));
|
||||
```
|
||||
|
||||
More generally, to use with a mock function whose signature is `R(Args...)` the
|
||||
object can be anything convertible to `OnceAction<R(Args...)>` or
|
||||
`Action<R(Args...)`>. The difference between the two is that `OnceAction` has
|
||||
weaker requirements (`Action` requires a copy-constructible input that can be
|
||||
called repeatedly whereas `OnceAction` requires only move-constructible and
|
||||
supports `&&`-qualified call operators), but can be used only with `WillOnce`.
|
||||
`OnceAction` is typically relevant only when supporting move-only types or
|
||||
actions that want a type-system guarantee that they will be called at most once.
|
||||
|
||||
Typically the `OnceAction` and `Action` templates need not be referenced
|
||||
directly in your actions: a struct or class with a call operator is sufficient,
|
||||
as in the examples above. But fancier polymorphic actions that need to know the
|
||||
specific return type of the mock function can define templated conversion
|
||||
operators to make that possible. See `gmock-actions.h` for examples.
|
||||
|
||||
#### Legacy macro-based Actions
|
||||
|
||||
Before C++11, the functor-based actions were not supported; the old way of
|
||||
@@ -4191,7 +4339,7 @@ This implementation class does *not* need to inherit from any particular class.
|
||||
What matters is that it must have a `Perform()` method template. This method
|
||||
template takes the mock function's arguments as a tuple in a **single**
|
||||
argument, and returns the result of the action. It can be either `const` or not,
|
||||
but must be invokable with exactly one template argument, which is the result
|
||||
but must be invocable with exactly one template argument, which is the result
|
||||
type. In other words, you must be able to call `Perform<R>(args)` where `R` is
|
||||
the mock function's return type and `args` is its arguments in a tuple.
|
||||
|
||||
@@ -4252,7 +4400,7 @@ particular type than to dump the bytes.
|
||||
### Mock std::function {#MockFunction}
|
||||
|
||||
`std::function` is a general function type introduced in C++11. It is a
|
||||
preferred way of passing callbacks to new interfaces. Functions are copiable,
|
||||
preferred way of passing callbacks to new interfaces. Functions are copyable,
|
||||
and are not usually passed around by pointer, which makes them tricky to mock.
|
||||
But fear not - `MockFunction` can help you with that.
|
||||
|
||||
|
||||
+2
-2
@@ -369,8 +369,8 @@ Usually, if your action is for a particular function type, defining it using
|
||||
different types (e.g. if you are defining `Return(*value*)`),
|
||||
`MakePolymorphicAction()` is easiest. Sometimes you want precise control on what
|
||||
types of functions the action can be used in, and implementing `ActionInterface`
|
||||
is the way to go here. See the implementation of `Return()` in
|
||||
`testing/base/public/gmock-actions.h` for an example.
|
||||
is the way to go here. See the implementation of `Return()` in `gmock-actions.h`
|
||||
for an example.
|
||||
|
||||
### I use SetArgPointee() in WillOnce(), but gcc complains about "conflicting return type specified". What does it mean?
|
||||
|
||||
|
||||
+13
-11
@@ -90,14 +90,14 @@ gMock is bundled with googletest.
|
||||
## A Case for Mock Turtles
|
||||
|
||||
Let's look at an example. Suppose you are developing a graphics program that
|
||||
relies on a [LOGO](http://en.wikipedia.org/wiki/Logo_programming_language)-like
|
||||
relies on a [LOGO](https://en.wikipedia.org/wiki/Logo_programming_language)-like
|
||||
API for drawing. How would you test that it does the right thing? Well, you can
|
||||
run it and compare the screen with a golden screen snapshot, but let's admit it:
|
||||
tests like this are expensive to run and fragile (What if you just upgraded to a
|
||||
shiny new graphics card that has better anti-aliasing? Suddenly you have to
|
||||
update all your golden images.). It would be too painful if all your tests are
|
||||
like this. Fortunately, you learned about
|
||||
[Dependency Injection](http://en.wikipedia.org/wiki/Dependency_injection) and know the right thing
|
||||
[Dependency Injection](https://en.wikipedia.org/wiki/Dependency_injection) and know the right thing
|
||||
to do: instead of having your application talk to the system API directly, wrap
|
||||
the API in an interface (say, `Turtle`) and code to that interface:
|
||||
|
||||
@@ -164,7 +164,7 @@ follow:
|
||||
After the process, you should have something like:
|
||||
|
||||
```cpp
|
||||
#include "gmock/gmock.h" // Brings in gMock.
|
||||
#include <gmock/gmock.h> // Brings in gMock.
|
||||
|
||||
class MockTurtle : public Turtle {
|
||||
public:
|
||||
@@ -190,10 +190,10 @@ Some people put it in a `_test.cc`. This is fine when the interface being mocked
|
||||
`Foo` changes it, your test could break. (You can't really expect `Foo`'s
|
||||
maintainer to fix every test that uses `Foo`, can you?)
|
||||
|
||||
So, the rule of thumb is: if you need to mock `Foo` and it's owned by others,
|
||||
define the mock class in `Foo`'s package (better, in a `testing` sub-package
|
||||
such that you can clearly separate production code and testing utilities), put
|
||||
it in a `.h` and a `cc_library`. Then everyone can reference them from their
|
||||
Generally, you should not mock classes you don't own. If you must mock such a
|
||||
class owned by others, define the mock class in `Foo`'s Bazel package (usually
|
||||
the same directory or a `testing` sub-directory), and put it in a `.h` and a
|
||||
`cc_library` with `testonly=True`. Then everyone can reference them from their
|
||||
tests. If `Foo` ever changes, there is only one copy of `MockFoo` to change, and
|
||||
only tests that depend on the changed methods need to be fixed.
|
||||
|
||||
@@ -224,8 +224,8 @@ Here's an example:
|
||||
|
||||
```cpp
|
||||
#include "path/to/mock-turtle.h"
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
#include <gmock/gmock.h>
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
using ::testing::AtLeast; // #1
|
||||
|
||||
@@ -261,6 +261,8 @@ happen. Therefore it's a good idea to turn on the heap checker in your tests
|
||||
when you allocate mocks on the heap. You get that automatically if you use the
|
||||
`gtest_main` library already.
|
||||
|
||||
###### Expectation Ordering
|
||||
|
||||
**Important note:** gMock requires expectations to be set **before** the mock
|
||||
functions are called, otherwise the behavior is **undefined**. Do not alternate
|
||||
between calls to `EXPECT_CALL()` and calls to the mock functions, and do not set
|
||||
@@ -480,8 +482,8 @@ the *default* action for the function every time (unless, of course, you have a
|
||||
`WillRepeatedly()`.).
|
||||
|
||||
What can we do inside `WillOnce()` besides `Return()`? You can return a
|
||||
reference using `ReturnRef(*variable*)`, or invoke a pre-defined function, among
|
||||
[others](gmock_cook_book.md#using-actions).
|
||||
reference using `ReturnRef(`*`variable`*`)`, or invoke a pre-defined function,
|
||||
among [others](gmock_cook_book.md#using-actions).
|
||||
|
||||
**Important note:** The `EXPECT_CALL()` statement evaluates the action clause
|
||||
only once, even though the action may be performed many times. Therefore you
|
||||
|
||||
+6
-10
@@ -19,19 +19,15 @@ examples here we assume you want to compile the sample
|
||||
Using `pkg-config` in CMake is fairly easy:
|
||||
|
||||
```cmake
|
||||
cmake_minimum_required(VERSION 3.0)
|
||||
|
||||
cmake_policy(SET CMP0048 NEW)
|
||||
project(my_gtest_pkgconfig VERSION 0.0.1 LANGUAGES CXX)
|
||||
|
||||
find_package(PkgConfig)
|
||||
pkg_search_module(GTEST REQUIRED gtest_main)
|
||||
|
||||
add_executable(testapp samples/sample3_unittest.cc)
|
||||
target_link_libraries(testapp ${GTEST_LDFLAGS})
|
||||
target_compile_options(testapp PUBLIC ${GTEST_CFLAGS})
|
||||
add_executable(testapp)
|
||||
target_sources(testapp PRIVATE samples/sample3_unittest.cc)
|
||||
target_link_libraries(testapp PRIVATE ${GTEST_LDFLAGS})
|
||||
target_compile_options(testapp PRIVATE ${GTEST_CFLAGS})
|
||||
|
||||
include(CTest)
|
||||
enable_testing()
|
||||
add_test(first_and_only_test testapp)
|
||||
```
|
||||
|
||||
@@ -105,7 +101,7 @@ includedir=/usr/include
|
||||
|
||||
Name: gtest
|
||||
Description: GoogleTest (without main() function)
|
||||
Version: 1.10.0
|
||||
Version: 1.11.0
|
||||
URL: https://github.com/google/googletest
|
||||
Libs: -L${libdir} -lgtest -lpthread
|
||||
Cflags: -I${includedir} -DGTEST_HAS_PTHREAD=1 -lpthread
|
||||
|
||||
+6
-33
@@ -1,35 +1,8 @@
|
||||
# Supported Platforms
|
||||
|
||||
GoogleTest requires a codebase and compiler compliant with the C++11 standard or
|
||||
newer.
|
||||
|
||||
The GoogleTest code is officially supported on the following platforms.
|
||||
Operating systems or tools not listed below are community-supported. For
|
||||
community-supported platforms, patches that do not complicate the code may be
|
||||
considered.
|
||||
|
||||
If you notice any problems on your platform, please file an issue on the
|
||||
[GoogleTest GitHub Issue Tracker](https://github.com/google/googletest/issues).
|
||||
Pull requests containing fixes are welcome!
|
||||
|
||||
### Operating systems
|
||||
|
||||
* Linux
|
||||
* macOS
|
||||
* Windows
|
||||
|
||||
### Compilers
|
||||
|
||||
* gcc 5.0+
|
||||
* clang 5.0+
|
||||
* MSVC 2015+
|
||||
|
||||
**macOS users:** Xcode 9.3+ provides clang 5.0+.
|
||||
|
||||
### Build systems
|
||||
|
||||
* [Bazel](https://bazel.build/)
|
||||
* [CMake](https://cmake.org/)
|
||||
|
||||
Bazel is the build system used by the team internally and in tests. CMake is
|
||||
supported on a best-effort basis and by the community.
|
||||
GoogleTest follows Google's
|
||||
[Foundational C++ Support Policy](https://opensource.google/documentation/policies/cplusplus-support).
|
||||
See
|
||||
[this table](https://github.com/google/oss-policies-info/blob/main/foundational-cxx-support-matrix.md)
|
||||
for a list of currently supported versions compilers, platforms, and build
|
||||
tools.
|
||||
|
||||
+74
-74
@@ -1,84 +1,84 @@
|
||||
# Googletest Primer
|
||||
# GoogleTest Primer
|
||||
|
||||
## Introduction: Why googletest?
|
||||
## Introduction: Why GoogleTest?
|
||||
|
||||
*googletest* helps you write better C++ tests.
|
||||
*GoogleTest* helps you write better C++ tests.
|
||||
|
||||
googletest is a testing framework developed by the Testing Technology team with
|
||||
GoogleTest is a testing framework developed by the Testing Technology team with
|
||||
Google's specific requirements and constraints in mind. Whether you work on
|
||||
Linux, Windows, or a Mac, if you write C++ code, googletest can help you. And it
|
||||
Linux, Windows, or a Mac, if you write C++ code, GoogleTest can help you. And it
|
||||
supports *any* kind of tests, not just unit tests.
|
||||
|
||||
So what makes a good test, and how does googletest fit in? We believe:
|
||||
So what makes a good test, and how does GoogleTest fit in? We believe:
|
||||
|
||||
1. Tests should be *independent* and *repeatable*. It's a pain to debug a test
|
||||
that succeeds or fails as a result of other tests. googletest isolates the
|
||||
that succeeds or fails as a result of other tests. GoogleTest isolates the
|
||||
tests by running each of them on a different object. When a test fails,
|
||||
googletest allows you to run it in isolation for quick debugging.
|
||||
GoogleTest allows you to run it in isolation for quick debugging.
|
||||
2. Tests should be well *organized* and reflect the structure of the tested
|
||||
code. googletest groups related tests into test suites that can share data
|
||||
code. GoogleTest groups related tests into test suites that can share data
|
||||
and subroutines. This common pattern is easy to recognize and makes tests
|
||||
easy to maintain. Such consistency is especially helpful when people switch
|
||||
projects and start to work on a new code base.
|
||||
3. Tests should be *portable* and *reusable*. Google has a lot of code that is
|
||||
platform-neutral; its tests should also be platform-neutral. googletest
|
||||
platform-neutral; its tests should also be platform-neutral. GoogleTest
|
||||
works on different OSes, with different compilers, with or without
|
||||
exceptions, so googletest tests can work with a variety of configurations.
|
||||
exceptions, so GoogleTest tests can work with a variety of configurations.
|
||||
4. When tests fail, they should provide as much *information* about the problem
|
||||
as possible. googletest doesn't stop at the first test failure. Instead, it
|
||||
as possible. GoogleTest doesn't stop at the first test failure. Instead, it
|
||||
only stops the current test and continues with the next. You can also set up
|
||||
tests that report non-fatal failures after which the current test continues.
|
||||
Thus, you can detect and fix multiple bugs in a single run-edit-compile
|
||||
cycle.
|
||||
5. The testing framework should liberate test writers from housekeeping chores
|
||||
and let them focus on the test *content*. googletest automatically keeps
|
||||
and let them focus on the test *content*. GoogleTest automatically keeps
|
||||
track of all tests defined, and doesn't require the user to enumerate them
|
||||
in order to run them.
|
||||
6. Tests should be *fast*. With googletest, you can reuse shared resources
|
||||
6. Tests should be *fast*. With GoogleTest, you can reuse shared resources
|
||||
across tests and pay for the set-up/tear-down only once, without making
|
||||
tests depend on each other.
|
||||
|
||||
Since googletest is based on the popular xUnit architecture, you'll feel right
|
||||
Since GoogleTest is based on the popular xUnit architecture, you'll feel right
|
||||
at home if you've used JUnit or PyUnit before. If not, it will take you about 10
|
||||
minutes to learn the basics and get started. So let's go!
|
||||
|
||||
## Beware of the nomenclature
|
||||
## Beware of the Nomenclature
|
||||
|
||||
{: .callout .note}
|
||||
_Note:_ There might be some confusion arising from different definitions of the
|
||||
terms _Test_, _Test Case_ and _Test Suite_, so beware of misunderstanding these.
|
||||
*Note:* There might be some confusion arising from different definitions of the
|
||||
terms *Test*, *Test Case* and *Test Suite*, so beware of misunderstanding these.
|
||||
|
||||
Historically, googletest started to use the term _Test Case_ for grouping
|
||||
Historically, GoogleTest started to use the term *Test Case* for grouping
|
||||
related tests, whereas current publications, including International Software
|
||||
Testing Qualifications Board ([ISTQB](http://www.istqb.org/)) materials and
|
||||
Testing Qualifications Board ([ISTQB](https://www.istqb.org/)) materials and
|
||||
various textbooks on software quality, use the term
|
||||
_[Test Suite][istqb test suite]_ for this.
|
||||
*[Test Suite][istqb test suite]* for this.
|
||||
|
||||
The related term _Test_, as it is used in googletest, corresponds to the term
|
||||
_[Test Case][istqb test case]_ of ISTQB and others.
|
||||
The related term *Test*, as it is used in GoogleTest, corresponds to the term
|
||||
*[Test Case][istqb test case]* of ISTQB and others.
|
||||
|
||||
The term _Test_ is commonly of broad enough sense, including ISTQB's definition
|
||||
of _Test Case_, so it's not much of a problem here. But the term _Test Case_ as
|
||||
The term *Test* is commonly of broad enough sense, including ISTQB's definition
|
||||
of *Test Case*, so it's not much of a problem here. But the term *Test Case* as
|
||||
was used in Google Test is of contradictory sense and thus confusing.
|
||||
|
||||
googletest recently started replacing the term _Test Case_ with _Test Suite_.
|
||||
GoogleTest recently started replacing the term *Test Case* with *Test Suite*.
|
||||
The preferred API is *TestSuite*. The older TestCase API is being slowly
|
||||
deprecated and refactored away.
|
||||
|
||||
So please be aware of the different definitions of the terms:
|
||||
|
||||
|
||||
Meaning | googletest Term | [ISTQB](http://www.istqb.org/) Term
|
||||
Meaning | GoogleTest Term | [ISTQB](https://www.istqb.org/) Term
|
||||
:----------------------------------------------------------------------------------- | :---------------------- | :----------------------------------
|
||||
Exercise a particular program path with specific input values and verify the results | [TEST()](#simple-tests) | [Test Case][istqb test case]
|
||||
|
||||
|
||||
[istqb test case]: http://glossary.istqb.org/en/search/test%20case
|
||||
[istqb test suite]: http://glossary.istqb.org/en/search/test%20suite
|
||||
[istqb test case]: https://glossary.istqb.org/en_US/term/test-case
|
||||
[istqb test suite]: https://glossary.istqb.org/en_US/term/test-suite
|
||||
|
||||
## Basic Concepts
|
||||
|
||||
When using googletest, you start by writing *assertions*, which are statements
|
||||
When using GoogleTest, you start by writing *assertions*, which are statements
|
||||
that check whether a condition is true. An assertion's result can be *success*,
|
||||
*nonfatal failure*, or *fatal failure*. If a fatal failure occurs, it aborts the
|
||||
current function; otherwise the program continues normally.
|
||||
@@ -98,11 +98,11 @@ assertion level and building up to tests and test suites.
|
||||
|
||||
## Assertions
|
||||
|
||||
googletest assertions are macros that resemble function calls. You test a class
|
||||
GoogleTest assertions are macros that resemble function calls. You test a class
|
||||
or function by making assertions about its behavior. When an assertion fails,
|
||||
googletest prints the assertion's source file and line number location, along
|
||||
GoogleTest prints the assertion's source file and line number location, along
|
||||
with a failure message. You may also supply a custom failure message which will
|
||||
be appended to googletest's message.
|
||||
be appended to GoogleTest's message.
|
||||
|
||||
The assertions come in pairs that test the same thing but have different effects
|
||||
on the current function. `ASSERT_*` versions generate fatal failures when they
|
||||
@@ -149,7 +149,7 @@ To create a test:
|
||||
1. Use the `TEST()` macro to define and name a test function. These are
|
||||
ordinary C++ functions that don't return a value.
|
||||
2. In this function, along with any valid C++ statements you want to include,
|
||||
use the various googletest assertions to check values.
|
||||
use the various GoogleTest assertions to check values.
|
||||
3. The test's result is determined by the assertions; if any assertion in the
|
||||
test fails (either fatally or non-fatally), or if the test crashes, the
|
||||
entire test fails. Otherwise, it succeeds.
|
||||
@@ -162,9 +162,9 @@ TEST(TestSuiteName, TestName) {
|
||||
|
||||
`TEST()` arguments go from general to specific. The *first* argument is the name
|
||||
of the test suite, and the *second* argument is the test's name within the test
|
||||
suite. Both names must be valid C++ identifiers, and they should not contain
|
||||
any underscores (`_`). A test's *full name* consists of its containing test suite and
|
||||
its individual name. Tests from different test suites can have the same
|
||||
suite. Both names must be valid C++ identifiers, and they should not contain any
|
||||
underscores (`_`). A test's *full name* consists of its containing test suite
|
||||
and its individual name. Tests from different test suites can have the same
|
||||
individual name.
|
||||
|
||||
For example, let's take a simple integer function:
|
||||
@@ -190,7 +190,7 @@ TEST(FactorialTest, HandlesPositiveInput) {
|
||||
}
|
||||
```
|
||||
|
||||
googletest groups the test results by test suites, so logically related tests
|
||||
GoogleTest groups the test results by test suites, so logically related tests
|
||||
should be in the same test suite; in other words, the first argument to their
|
||||
`TEST()` should be the same. In the above example, we have two tests,
|
||||
`HandlesZeroInput` and `HandlesPositiveInput`, that belong to the same test
|
||||
@@ -210,7 +210,7 @@ objects for several different tests.
|
||||
|
||||
To create a fixture:
|
||||
|
||||
1. Derive a class from `::testing::Test` . Start its body with `protected:`, as
|
||||
1. Derive a class from `testing::Test` . Start its body with `protected:`, as
|
||||
we'll want to access fixture members from sub-classes.
|
||||
2. Inside the class, declare any objects you plan to use.
|
||||
3. If necessary, write a default constructor or `SetUp()` function to prepare
|
||||
@@ -227,14 +227,14 @@ When using a fixture, use `TEST_F()` instead of `TEST()` as it allows you to
|
||||
access objects and subroutines in the test fixture:
|
||||
|
||||
```c++
|
||||
TEST_F(TestFixtureName, TestName) {
|
||||
TEST_F(TestFixtureClassName, TestName) {
|
||||
... test body ...
|
||||
}
|
||||
```
|
||||
|
||||
Like `TEST()`, the first argument is the test suite name, but for `TEST_F()`
|
||||
this must be the name of the test fixture class. You've probably guessed: `_F`
|
||||
is for fixture.
|
||||
Unlike `TEST()`, in `TEST_F()` the first argument must be the name of the test
|
||||
fixture class. (`_F` stands for "Fixture"). No test suite name is specified for
|
||||
this macro.
|
||||
|
||||
Unfortunately, the C++ macro system does not allow us to create a single macro
|
||||
that can handle both types of tests. Using the wrong macro causes a compiler
|
||||
@@ -244,12 +244,12 @@ Also, you must first define a test fixture class before using it in a
|
||||
`TEST_F()`, or you'll get the compiler error "`virtual outside class
|
||||
declaration`".
|
||||
|
||||
For each test defined with `TEST_F()`, googletest will create a *fresh* test
|
||||
fixture at runtime, immediately initialize it via `SetUp()`, run the test,
|
||||
clean up by calling `TearDown()`, and then delete the test fixture. Note that
|
||||
For each test defined with `TEST_F()`, GoogleTest will create a *fresh* test
|
||||
fixture at runtime, immediately initialize it via `SetUp()`, run the test, clean
|
||||
up by calling `TearDown()`, and then delete the test fixture. Note that
|
||||
different tests in the same test suite have different test fixture objects, and
|
||||
googletest always deletes a test fixture before it creates the next one.
|
||||
googletest does **not** reuse the same test fixture for multiple tests. Any
|
||||
GoogleTest always deletes a test fixture before it creates the next one.
|
||||
GoogleTest does **not** reuse the same test fixture for multiple tests. Any
|
||||
changes one test makes to the fixture do not affect other tests.
|
||||
|
||||
As an example, let's write tests for a FIFO queue class named `Queue`, which has
|
||||
@@ -271,15 +271,16 @@ First, define a fixture class. By convention, you should give it the name
|
||||
`FooTest` where `Foo` is the class being tested.
|
||||
|
||||
```c++
|
||||
class QueueTest : public ::testing::Test {
|
||||
class QueueTest : public testing::Test {
|
||||
protected:
|
||||
void SetUp() override {
|
||||
QueueTest() {
|
||||
// q0_ remains empty
|
||||
q1_.Enqueue(1);
|
||||
q2_.Enqueue(2);
|
||||
q2_.Enqueue(3);
|
||||
}
|
||||
|
||||
// void TearDown() override {}
|
||||
// ~QueueTest() override = default;
|
||||
|
||||
Queue<int> q0_;
|
||||
Queue<int> q1_;
|
||||
@@ -287,8 +288,9 @@ class QueueTest : public ::testing::Test {
|
||||
};
|
||||
```
|
||||
|
||||
In this case, `TearDown()` is not needed since we don't have to clean up after
|
||||
each test, other than what's already done by the destructor.
|
||||
In this case, we don't need to define a destructor or a `TearDown()` method,
|
||||
because the implicit destructor generated by the compiler will perform all of
|
||||
the necessary cleanup.
|
||||
|
||||
Now we'll write tests using `TEST_F()` and this fixture.
|
||||
|
||||
@@ -324,30 +326,28 @@ would lead to a segfault when `n` is `NULL`.
|
||||
|
||||
When these tests run, the following happens:
|
||||
|
||||
1. googletest constructs a `QueueTest` object (let's call it `t1`).
|
||||
2. `t1.SetUp()` initializes `t1`.
|
||||
3. The first test (`IsEmptyInitially`) runs on `t1`.
|
||||
4. `t1.TearDown()` cleans up after the test finishes.
|
||||
5. `t1` is destructed.
|
||||
6. The above steps are repeated on another `QueueTest` object, this time
|
||||
1. GoogleTest constructs a `QueueTest` object (let's call it `t1`).
|
||||
2. The first test (`IsEmptyInitially`) runs on `t1`.
|
||||
3. `t1` is destructed.
|
||||
4. The above steps are repeated on another `QueueTest` object, this time
|
||||
running the `DequeueWorks` test.
|
||||
|
||||
**Availability**: Linux, Windows, Mac.
|
||||
|
||||
## Invoking the Tests
|
||||
|
||||
`TEST()` and `TEST_F()` implicitly register their tests with googletest. So,
|
||||
`TEST()` and `TEST_F()` implicitly register their tests with GoogleTest. So,
|
||||
unlike with many other C++ testing frameworks, you don't have to re-list all
|
||||
your defined tests in order to run them.
|
||||
|
||||
After defining your tests, you can run them with `RUN_ALL_TESTS()`, which
|
||||
returns `0` if all the tests are successful, or `1` otherwise. Note that
|
||||
`RUN_ALL_TESTS()` runs *all tests* in your link unit--they can be from
|
||||
different test suites, or even different source files.
|
||||
`RUN_ALL_TESTS()` runs *all tests* in your link unit--they can be from different
|
||||
test suites, or even different source files.
|
||||
|
||||
When invoked, the `RUN_ALL_TESTS()` macro:
|
||||
|
||||
* Saves the state of all googletest flags.
|
||||
* Saves the state of all GoogleTest flags.
|
||||
|
||||
* Creates a test fixture object for the first test.
|
||||
|
||||
@@ -359,7 +359,7 @@ When invoked, the `RUN_ALL_TESTS()` macro:
|
||||
|
||||
* Deletes the fixture.
|
||||
|
||||
* Restores the state of all googletest flags.
|
||||
* Restores the state of all GoogleTest flags.
|
||||
|
||||
* Repeats the above steps for the next test, until all tests have run.
|
||||
|
||||
@@ -373,14 +373,14 @@ If a fatal failure happens the subsequent steps will be skipped.
|
||||
> return the value of `RUN_ALL_TESTS()`.
|
||||
>
|
||||
> Also, you should call `RUN_ALL_TESTS()` only **once**. Calling it more than
|
||||
> once conflicts with some advanced googletest features (e.g., thread-safe
|
||||
> once conflicts with some advanced GoogleTest features (e.g., thread-safe
|
||||
> [death tests](advanced.md#death-tests)) and thus is not supported.
|
||||
|
||||
**Availability**: Linux, Windows, Mac.
|
||||
|
||||
## Writing the main() Function
|
||||
|
||||
Most users should _not_ need to write their own `main` function and instead link
|
||||
Most users should *not* need to write their own `main` function and instead link
|
||||
with `gtest_main` (as opposed to with `gtest`), which defines a suitable entry
|
||||
point. See the end of this section for details. The remainder of this section
|
||||
should only apply when you need to do something custom before the tests run that
|
||||
@@ -394,14 +394,14 @@ You can start from this boilerplate:
|
||||
```c++
|
||||
#include "this/package/foo.h"
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
namespace my {
|
||||
namespace project {
|
||||
namespace {
|
||||
|
||||
// The fixture for testing class Foo.
|
||||
class FooTest : public ::testing::Test {
|
||||
class FooTest : public testing::Test {
|
||||
protected:
|
||||
// You can remove any or all of the following functions if their bodies would
|
||||
// be empty.
|
||||
@@ -449,15 +449,15 @@ TEST_F(FooTest, DoesXyz) {
|
||||
} // namespace my
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
::testing::InitGoogleTest(&argc, argv);
|
||||
testing::InitGoogleTest(&argc, argv);
|
||||
return RUN_ALL_TESTS();
|
||||
}
|
||||
```
|
||||
|
||||
The `::testing::InitGoogleTest()` function parses the command line for
|
||||
googletest flags, and removes all recognized flags. This allows the user to
|
||||
control a test program's behavior via various flags, which we'll cover in
|
||||
the [AdvancedGuide](advanced.md). You **must** call this function before calling
|
||||
The `testing::InitGoogleTest()` function parses the command line for GoogleTest
|
||||
flags, and removes all recognized flags. This allows the user to control a test
|
||||
program's behavior via various flags, which we'll cover in the
|
||||
[AdvancedGuide](advanced.md). You **must** call this function before calling
|
||||
`RUN_ALL_TESTS()`, or the flags won't be properly initialized.
|
||||
|
||||
On Windows, `InitGoogleTest()` also works with wide strings, so it can be used
|
||||
@@ -475,7 +475,7 @@ NOTE: `ParseGUnitFlags()` is deprecated in favor of `InitGoogleTest()`.
|
||||
|
||||
* Google Test is designed to be thread-safe. The implementation is thread-safe
|
||||
on systems where the `pthreads` library is available. It is currently
|
||||
_unsafe_ to use Google Test assertions from two threads concurrently on
|
||||
*unsafe* to use Google Test assertions from two threads concurrently on
|
||||
other systems (e.g. Windows). In most tests this is not an issue as usually
|
||||
the assertions are done in the main thread. If you want to help, you can
|
||||
volunteer to implement the necessary synchronization primitives in
|
||||
|
||||
+36
-51
@@ -9,27 +9,26 @@ we recommend this tutorial as a starting point.
|
||||
To complete this tutorial, you'll need:
|
||||
|
||||
* A compatible operating system (e.g. Linux, macOS, Windows).
|
||||
* A compatible C++ compiler that supports at least C++11.
|
||||
* [Bazel](https://bazel.build/), the preferred build system used by the
|
||||
GoogleTest team.
|
||||
* A compatible C++ compiler that supports at least C++17.
|
||||
* [Bazel](https://bazel.build/) 7.0 or higher, the preferred build system used
|
||||
by the GoogleTest team.
|
||||
|
||||
See [Supported Platforms](platforms.md) for more information about platforms
|
||||
compatible with GoogleTest.
|
||||
|
||||
If you don't already have Bazel installed, see the
|
||||
[Bazel installation guide](https://docs.bazel.build/versions/master/install.html).
|
||||
[Bazel installation guide](https://bazel.build/install).
|
||||
|
||||
{: .callout .note}
|
||||
Note: The terminal commands in this tutorial show a Unix shell prompt, but the
|
||||
commands work on the Windows command line as well.
|
||||
{: .callout .note} Note: The terminal commands in this tutorial show a Unix
|
||||
shell prompt, but the commands work on the Windows command line as well.
|
||||
|
||||
## Set up a Bazel workspace
|
||||
|
||||
A
|
||||
[Bazel workspace](https://docs.bazel.build/versions/master/build-ref.html#workspace)
|
||||
[Bazel workspace](https://docs.bazel.build/versions/main/build-ref.html#workspace)
|
||||
is a directory on your filesystem that you use to manage source files for the
|
||||
software you want to build. Each workspace directory has a text file named
|
||||
`WORKSPACE` which may be empty, or may contain references to external
|
||||
`MODULE.bazel` which may be empty, or may contain references to external
|
||||
dependencies required to build the outputs.
|
||||
|
||||
First, create a directory for your workspace:
|
||||
@@ -38,40 +37,18 @@ First, create a directory for your workspace:
|
||||
$ mkdir my_workspace && cd my_workspace
|
||||
```
|
||||
|
||||
Next, you’ll create the `WORKSPACE` file to specify dependencies. A common and
|
||||
recommended way to depend on GoogleTest is to use a
|
||||
[Bazel external dependency](https://docs.bazel.build/versions/master/external.html)
|
||||
via the
|
||||
[`http_archive` rule](https://docs.bazel.build/versions/master/repo/http.html#http_archive).
|
||||
To do this, in the root directory of your workspace (`my_workspace/`), create a
|
||||
file named `WORKSPACE` with the following contents:
|
||||
Next, you’ll create the `MODULE.bazel` file to specify dependencies. As of Bazel
|
||||
7.0, the recommended way to consume GoogleTest is through the
|
||||
[Bazel Central Registry](https://registry.bazel.build/modules/googletest). To do
|
||||
this, create a `MODULE.bazel` file in the root directory of your Bazel workspace
|
||||
with the following content:
|
||||
|
||||
```
|
||||
load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
|
||||
# MODULE.bazel
|
||||
|
||||
http_archive(
|
||||
name = "com_google_googletest",
|
||||
urls = ["https://github.com/google/googletest/archive/609281088cfefc76f9d0ce82e1ff6c30cc3591e5.zip"],
|
||||
strip_prefix = "googletest-609281088cfefc76f9d0ce82e1ff6c30cc3591e5",
|
||||
)
|
||||
```
|
||||
|
||||
The above configuration declares a dependency on GoogleTest which is downloaded
|
||||
as a ZIP archive from GitHub. In the above example,
|
||||
`609281088cfefc76f9d0ce82e1ff6c30cc3591e5` is the Git commit hash of the
|
||||
GoogleTest version to use; we recommend updating the hash often to point to the
|
||||
latest version.
|
||||
|
||||
Bazel also needs a dependency on the
|
||||
[`rules_cc` repository](https://github.com/bazelbuild/rules_cc) to build C++
|
||||
code, so add the following to the `WORKSPACE` file:
|
||||
|
||||
```
|
||||
http_archive(
|
||||
name = "rules_cc",
|
||||
urls = ["https://github.com/bazelbuild/rules_cc/archive/40548a2974f1aea06215272d9c2b47a14a24e556.zip"],
|
||||
strip_prefix = "rules_cc-40548a2974f1aea06215272d9c2b47a14a24e556",
|
||||
)
|
||||
# Choose the most recent version available at
|
||||
# https://registry.bazel.build/modules/googletest
|
||||
bazel_dep(name = "googletest", version = "1.18.0")
|
||||
```
|
||||
|
||||
Now you're ready to build C++ code that uses GoogleTest.
|
||||
@@ -104,26 +81,34 @@ To build the code, create a file named `BUILD` in the same directory with the
|
||||
following contents:
|
||||
|
||||
```
|
||||
load("@rules_cc//cc:defs.bzl", "cc_test")
|
||||
|
||||
cc_test(
|
||||
name = "hello_test",
|
||||
size = "small",
|
||||
srcs = ["hello_test.cc"],
|
||||
deps = ["@com_google_googletest//:gtest_main"],
|
||||
name = "hello_test",
|
||||
size = "small",
|
||||
srcs = ["hello_test.cc"],
|
||||
deps = [
|
||||
"@googletest//:gtest",
|
||||
"@googletest//:gtest_main",
|
||||
],
|
||||
)
|
||||
```
|
||||
|
||||
This `cc_test` rule declares the C++ test binary you want to build, and links to
|
||||
GoogleTest (`//:gtest_main`) using the prefix you specified in the `WORKSPACE`
|
||||
file (`@com_google_googletest`). For more information about Bazel `BUILD` files,
|
||||
see the
|
||||
[Bazel C++ Tutorial](https://docs.bazel.build/versions/master/tutorial/cpp.html).
|
||||
the GoogleTest library (`@googletest//:gtest"`) and the GoogleTest `main()`
|
||||
function (`@googletest//:gtest_main`). For more information about Bazel `BUILD`
|
||||
files, see the
|
||||
[Bazel C++ Tutorial](https://docs.bazel.build/versions/main/tutorial/cpp.html).
|
||||
|
||||
{: .callout .note}
|
||||
NOTE: In the example below, we assume Clang or GCC and set `--cxxopt=-std=c++17`
|
||||
to ensure that GoogleTest is compiled as C++17 instead of the compiler's default
|
||||
setting. For MSVC, the equivalent would be `--cxxopt=/std:c++17`. See
|
||||
[Supported Platforms](platforms.md) for more details on supported language
|
||||
versions.
|
||||
|
||||
Now you can build and run your test:
|
||||
|
||||
<pre>
|
||||
<strong>my_workspace$ bazel test --test_output=all //:hello_test</strong>
|
||||
<strong>$ bazel test --cxxopt=-std=c++17 --test_output=all //:hello_test</strong>
|
||||
INFO: Analyzed target //:hello_test (26 packages loaded, 362 targets configured).
|
||||
INFO: Found 1 test target...
|
||||
INFO: From Testing //:hello_test:
|
||||
|
||||
@@ -10,7 +10,7 @@ this tutorial as a starting point. If your project uses Bazel, see the
|
||||
To complete this tutorial, you'll need:
|
||||
|
||||
* A compatible operating system (e.g. Linux, macOS, Windows).
|
||||
* A compatible C++ compiler that supports at least C++11.
|
||||
* A compatible C++ compiler that supports at least C++17.
|
||||
* [CMake](https://cmake.org/) and a compatible build tool for building the
|
||||
project.
|
||||
* Compatible build tools include
|
||||
@@ -52,13 +52,14 @@ To do this, in your project directory (`my_project`), create a file named
|
||||
cmake_minimum_required(VERSION 3.14)
|
||||
project(my_project)
|
||||
|
||||
# GoogleTest requires at least C++11
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
# GoogleTest requires at least C++17
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
|
||||
include(FetchContent)
|
||||
FetchContent_Declare(
|
||||
googletest
|
||||
URL https://github.com/google/googletest/archive/609281088cfefc76f9d0ce82e1ff6c30cc3591e5.zip
|
||||
URL https://github.com/google/googletest/archive/03597a01ee50ed33e9dfd640b249b4be3799d395.zip
|
||||
)
|
||||
# For Windows: Prevent overriding the parent project's compiler/linker settings
|
||||
set(gtest_force_shared_crt ON CACHE BOOL "" FORCE)
|
||||
@@ -66,7 +67,7 @@ FetchContent_MakeAvailable(googletest)
|
||||
```
|
||||
|
||||
The above configuration declares a dependency on GoogleTest which is downloaded
|
||||
from GitHub. In the above example, `609281088cfefc76f9d0ce82e1ff6c30cc3591e5` is
|
||||
from GitHub. In the above example, `03597a01ee50ed33e9dfd640b249b4be3799d395` is
|
||||
the Git commit hash of the GoogleTest version to use; we recommend updating the
|
||||
hash often to point to the latest version.
|
||||
|
||||
@@ -108,7 +109,7 @@ add_executable(
|
||||
)
|
||||
target_link_libraries(
|
||||
hello_test
|
||||
gtest_main
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
include(GoogleTest)
|
||||
|
||||
+11
-10
@@ -6,7 +6,7 @@ provided by GoogleTest. All actions are defined in the `::testing` namespace.
|
||||
|
||||
## Returning a Value
|
||||
|
||||
| | |
|
||||
| Action | Description |
|
||||
| :-------------------------------- | :-------------------------------------------- |
|
||||
| `Return()` | Return from a `void` mock function. |
|
||||
| `Return(value)` | Return `value`. If the type of `value` is different to the mock function's return type, `value` is converted to the latter type <i>at the time the expectation is set</i>, not when the action is executed. |
|
||||
@@ -20,11 +20,12 @@ provided by GoogleTest. All actions are defined in the `::testing` namespace.
|
||||
|
||||
## Side Effects
|
||||
|
||||
| | |
|
||||
| Action | Description |
|
||||
| :--------------------------------- | :-------------------------------------- |
|
||||
| `Assign(&variable, value)` | Assign `value` to variable. |
|
||||
| `DeleteArg<N>()` | Delete the `N`-th (0-based) argument, which must be a pointer. |
|
||||
| `SaveArg<N>(pointer)` | Save the `N`-th (0-based) argument to `*pointer`. |
|
||||
| `SaveArg<N>(pointer)` | Save the `N`-th (0-based) argument to `*pointer` by copy-assignment. |
|
||||
| `SaveArgByMove<N>(pointer)` | Save the `N`-th (0-based) argument to `*pointer` by move-assignment. |
|
||||
| `SaveArgPointee<N>(pointer)` | Save the value pointed to by the `N`-th (0-based) argument to `*pointer`. |
|
||||
| `SetArgReferee<N>(value)` | Assign `value` to the variable referenced by the `N`-th (0-based) argument. |
|
||||
| `SetArgPointee<N>(value)` | Assign `value` to the variable pointed by the `N`-th (0-based) argument. |
|
||||
@@ -38,17 +39,17 @@ provided by GoogleTest. All actions are defined in the `::testing` namespace.
|
||||
In the following, by "callable" we mean a free function, `std::function`,
|
||||
functor, or lambda.
|
||||
|
||||
| | |
|
||||
| Action | Description |
|
||||
| :---------------------------------- | :------------------------------------- |
|
||||
| `f` | Invoke f with the arguments passed to the mock function, where f is a callable. |
|
||||
| `f` | Invoke `f` with the arguments passed to the mock function, where `f` is a callable. |
|
||||
| `Invoke(f)` | Invoke `f` with the arguments passed to the mock function, where `f` can be a global/static function or a functor. |
|
||||
| `Invoke(object_pointer, &class::method)` | Invoke the method on the object with the arguments passed to the mock function. |
|
||||
| `InvokeWithoutArgs(f)` | Invoke `f`, which can be a global/static function or a functor. `f` must take no arguments. |
|
||||
| `InvokeWithoutArgs(object_pointer, &class::method)` | Invoke the method on the object, which takes no arguments. |
|
||||
| `InvokeArgument<N>(arg1, arg2, ..., argk)` | Invoke the mock function's `N`-th (0-based) argument, which must be a function or a functor, with the `k` arguments. |
|
||||
|
||||
The return value of the invoked function is used as the return value of the
|
||||
action.
|
||||
The return value of the invoked function (except `InvokeArgument`) is used as
|
||||
the return value of the action.
|
||||
|
||||
When defining a callable to be used with `Invoke*()`, you can declare any unused
|
||||
parameters as `Unused`:
|
||||
@@ -86,7 +87,7 @@ value, and `foo` by reference.
|
||||
|
||||
## Default Action
|
||||
|
||||
| Matcher | Description |
|
||||
| Action | Description |
|
||||
| :------------ | :----------------------------------------------------- |
|
||||
| `DoDefault()` | Do the default action (specified by `ON_CALL()` or the built-in one). |
|
||||
|
||||
@@ -96,7 +97,7 @@ composite action - trying to do so will result in a run-time error.
|
||||
|
||||
## Composite Actions
|
||||
|
||||
| | |
|
||||
| Action | Description |
|
||||
| :----------------------------- | :------------------------------------------ |
|
||||
| `DoAll(a1, a2, ..., an)` | Do all actions `a1` to `an` and return the result of `an` in each invocation. The first `n - 1` sub-actions must return void and will receive a readonly view of the arguments. |
|
||||
| `IgnoreResult(a)` | Perform action `a` and ignore its result. `a` must not return void. |
|
||||
@@ -106,7 +107,7 @@ composite action - trying to do so will result in a run-time error.
|
||||
|
||||
## Defining Actions
|
||||
|
||||
| | |
|
||||
| Macro | Description |
|
||||
| :--------------------------------- | :-------------------------------------- |
|
||||
| `ACTION(Sum) { return arg0 + arg1; }` | Defines an action `Sum()` to return the sum of the mock function's argument #0 and #1. |
|
||||
| `ACTION_P(Plus, n) { return arg0 + n; }` | Defines an action `Plus(n)` to return the sum of the mock function's argument #0 and `n`. |
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
# Assertions Reference
|
||||
|
||||
This page lists the assertion macros provided by GoogleTest for verifying code
|
||||
behavior. To use them, include the header `gtest/gtest.h`.
|
||||
behavior. To use them, add `#include <gtest/gtest.h>`.
|
||||
|
||||
The majority of the macros listed below come as a pair with an `EXPECT_` variant
|
||||
and an `ASSERT_` variant. Upon failure, `EXPECT_` macros generate nonfatal
|
||||
@@ -88,7 +88,7 @@ For example, the following code verifies that the string `value1` starts with
|
||||
10:
|
||||
|
||||
```cpp
|
||||
#include "gmock/gmock.h"
|
||||
#include <gmock/gmock.h>
|
||||
|
||||
using ::testing::AllOf;
|
||||
using ::testing::Gt;
|
||||
@@ -276,7 +276,8 @@ Units in the Last Place (ULPs). To learn more about ULPs, see the article
|
||||
`ASSERT_FLOAT_EQ(`*`val1`*`,`*`val2`*`)`
|
||||
|
||||
Verifies that the two `float` values *`val1`* and *`val2`* are approximately
|
||||
equal, to within 4 ULPs from each other.
|
||||
equal, to within 4 ULPs from each other. Infinity and the largest finite float
|
||||
value are considered to be one ULP apart.
|
||||
|
||||
### EXPECT_DOUBLE_EQ {#EXPECT_DOUBLE_EQ}
|
||||
|
||||
@@ -284,7 +285,8 @@ equal, to within 4 ULPs from each other.
|
||||
`ASSERT_DOUBLE_EQ(`*`val1`*`,`*`val2`*`)`
|
||||
|
||||
Verifies that the two `double` values *`val1`* and *`val2`* are approximately
|
||||
equal, to within 4 ULPs from each other.
|
||||
equal, to within 4 ULPs from each other. Infinity and the largest finite double
|
||||
value are considered to be one ULP apart.
|
||||
|
||||
### EXPECT_NEAR {#EXPECT_NEAR}
|
||||
|
||||
@@ -294,6 +296,11 @@ equal, to within 4 ULPs from each other.
|
||||
Verifies that the difference between *`val1`* and *`val2`* does not exceed the
|
||||
absolute error bound *`abs_error`*.
|
||||
|
||||
If *`val`* and *`val2`* are both infinity of the same sign, the difference is
|
||||
considered to be 0. Otherwise, if either value is infinity, the difference is
|
||||
considered to be infinity. All non-NaN values (including infinity) are
|
||||
considered to not exceed an *`abs_error`* of infinity.
|
||||
|
||||
## Exception Assertions {#exceptions}
|
||||
|
||||
The following assertions verify that a piece of code throws, or does not throw,
|
||||
@@ -515,7 +522,7 @@ Verifies that *`expression`* is a success `HRESULT`.
|
||||
### EXPECT_HRESULT_FAILED {#EXPECT_HRESULT_FAILED}
|
||||
|
||||
`EXPECT_HRESULT_FAILED(`*`expression`*`)` \
|
||||
`EXPECT_HRESULT_FAILED(`*`expression`*`)`
|
||||
`ASSERT_HRESULT_FAILED(`*`expression`*`)`
|
||||
|
||||
Verifies that *`expression`* is a failure `HRESULT`.
|
||||
|
||||
|
||||
+87
-20
@@ -1,5 +1,7 @@
|
||||
# Matchers Reference
|
||||
|
||||
<!-- disableFinding(LINK_RELATIVE_G3DOC) -->
|
||||
|
||||
A **matcher** matches a *single* argument. You can use it inside `ON_CALL()` or
|
||||
`EXPECT_CALL()`, or use it to validate a value directly using two macros:
|
||||
|
||||
@@ -8,9 +10,13 @@ A **matcher** matches a *single* argument. You can use it inside `ON_CALL()` or
|
||||
| `EXPECT_THAT(actual_value, matcher)` | Asserts that `actual_value` matches `matcher`. |
|
||||
| `ASSERT_THAT(actual_value, matcher)` | The same as `EXPECT_THAT(actual_value, matcher)`, except that it generates a **fatal** failure. |
|
||||
|
||||
{: .callout .note}
|
||||
**Note:** Although equality matching via `EXPECT_THAT(actual_value,
|
||||
expected_value)` is supported, prefer to make the comparison explicit via
|
||||
{: .callout .warning}
|
||||
**WARNING:** Equality matching via `EXPECT_THAT(actual_value, expected_value)`
|
||||
is supported, however note that implicit conversions can cause surprising
|
||||
results. For example, `EXPECT_THAT(some_bool, "some string")` will compile and
|
||||
may pass unintentionally.
|
||||
|
||||
**BEST PRACTICE:** Prefer to make the comparison explicit via
|
||||
`EXPECT_THAT(actual_value, Eq(expected_value))` or `EXPECT_EQ(actual_value,
|
||||
expected_value)`.
|
||||
|
||||
@@ -38,11 +44,14 @@ Matcher | Description
|
||||
| `Lt(value)` | `argument < value` |
|
||||
| `Ne(value)` | `argument != value` |
|
||||
| `IsFalse()` | `argument` evaluates to `false` in a Boolean context. |
|
||||
| `DistanceFrom(target, m)` | The distance between `argument` and `target` (computed by `abs(argument - target)`) matches `m`. |
|
||||
| `DistanceFrom(target, get_distance, m)` | The distance between `argument` and `target` (computed by `get_distance(argument, target)`) matches `m`. |
|
||||
| `IsTrue()` | `argument` evaluates to `true` in a Boolean context. |
|
||||
| `IsNull()` | `argument` is a `NULL` pointer (raw or smart). |
|
||||
| `NotNull()` | `argument` is a non-null pointer (raw or smart). |
|
||||
| `Optional(m)` | `argument` is `optional<>` that contains a value matching `m`. (For testing whether an `optional<>` is set, check for equality with `nullopt`. You may need to use `Eq(nullopt)` if the inner type doesn't have `==`.)|
|
||||
| `Optional(m)` | `argument` is `optional<>` that contains a value matching `m`. (For testing whether an `optional<>` is unset, check for equality with `nullopt`. You may need to use `Eq(nullopt)` if the inner type doesn't have `==`.)|
|
||||
| `VariantWith<T>(m)` | `argument` is `variant<>` that holds the alternative of type T with a value matching `m`. |
|
||||
| `AnyWith<T>(m)` | `argument` is `any<>` that holds a value of type T with a value matching `m`. |
|
||||
| `Ref(variable)` | `argument` is a reference to `variable`. |
|
||||
| `TypedEq<type>(value)` | `argument` has type `type` and is equal to `value`. You may need to use this instead of `Eq(value)` when the mock function is overloaded. |
|
||||
|
||||
@@ -88,22 +97,50 @@ The `argument` can be either a C string or a C++ string object:
|
||||
|
||||
| Matcher | Description |
|
||||
| :---------------------- | :------------------------------------------------- |
|
||||
| `ContainsRegex(string)` | `argument` matches the given regular expression. |
|
||||
| `EndsWith(suffix)` | `argument` ends with string `suffix`. |
|
||||
| `HasSubstr(string)` | `argument` contains `string` as a sub-string. |
|
||||
| `IsEmpty()` | `argument` is an empty string. |
|
||||
| `MatchesRegex(string)` | `argument` matches the given regular expression with the match starting at the first character and ending at the last character. |
|
||||
| `StartsWith(prefix)` | `argument` starts with string `prefix`. |
|
||||
| `StrCaseEq(string)` | `argument` is equal to `string`, ignoring case. |
|
||||
| `StrCaseNe(string)` | `argument` is not equal to `string`, ignoring case. |
|
||||
| `StrEq(string)` | `argument` is equal to `string`. |
|
||||
| `StrNe(string)` | `argument` is not equal to `string`. |
|
||||
| `ContainsRegex(string)` | `argument` matches the given regular expression. |
|
||||
| `EndsWith(suffix)` | `argument` ends with string `suffix`. |
|
||||
| `HasSubstr(string)` | `argument` contains `string` as a sub-string. |
|
||||
| `IsEmpty()` | `argument` is an empty string. |
|
||||
| `MatchesRegex(string)` | `argument` matches the given regular expression with the match starting at the first character and ending at the last character. |
|
||||
| `StartsWith(prefix)` | `argument` starts with string `prefix`. |
|
||||
| `StrCaseEq(string)` | `argument` is equal to `string`, ignoring case. |
|
||||
| `StrCaseNe(string)` | `argument` is not equal to `string`, ignoring case. |
|
||||
| `StrEq(string)` | `argument` is equal to `string`. |
|
||||
| `StrNe(string)` | `argument` is not equal to `string`. |
|
||||
| `WhenBase64Unescaped(m)` | `argument` is a base-64 escaped string whose unescaped string matches `m`. The web-safe format from [RFC 4648](https://www.rfc-editor.org/rfc/rfc4648#section-5) is supported. |
|
||||
|
||||
`ContainsRegex()` and `MatchesRegex()` take ownership of the `RE` object. They
|
||||
use the regular expression syntax defined
|
||||
[here](../advanced.md#regular-expression-syntax). All of these matchers, except
|
||||
`ContainsRegex()` and `MatchesRegex()` work for wide strings as well.
|
||||
|
||||
## Exception Matchers
|
||||
|
||||
| Matcher | Description |
|
||||
| :---------------------------------------- | :------------------------------- |
|
||||
| `Throws<E>()` | The `argument` is a callable object that, when called, throws an exception of the expected type `E`. |
|
||||
| `Throws<E>(m)` | The `argument` is a callable object that, when called, throws an exception of type `E` that satisfies the matcher `m`. |
|
||||
| `ThrowsMessage<E>(m)` | The `argument` is a callable object that, when called, throws an exception of type `E` with a message that satisfies the matcher `m`. |
|
||||
|
||||
Examples:
|
||||
|
||||
```cpp
|
||||
auto argument = [] { throw std::runtime_error("error msg"); };
|
||||
|
||||
// Checks if the lambda throws a `std::runtime_error`.
|
||||
EXPECT_THAT(argument, Throws<std::runtime_error>());
|
||||
|
||||
// Checks if the lambda throws a `std::runtime_error` with a specific message
|
||||
// that matches "error msg".
|
||||
EXPECT_THAT(argument,
|
||||
Throws<std::runtime_error>(Property(&std::runtime_error::what,
|
||||
Eq("error msg"))));
|
||||
|
||||
// Checks if the lambda throws a `std::runtime_error` with a message that
|
||||
// contains "msg".
|
||||
EXPECT_THAT(argument, ThrowsMessage<std::runtime_error>(HasSubstr("msg")));
|
||||
```
|
||||
|
||||
## Container Matchers
|
||||
|
||||
Most STL-style containers support `==`, so you can use `Eq(expected_container)`
|
||||
@@ -116,6 +153,7 @@ messages, you can use:
|
||||
| `BeginEndDistanceIs(m)` | `argument` is a container whose `begin()` and `end()` iterators are separated by a number of increments matching `m`. E.g. `BeginEndDistanceIs(2)` or `BeginEndDistanceIs(Lt(2))`. For containers that define a `size()` method, `SizeIs(m)` may be more efficient. |
|
||||
| `ContainerEq(container)` | The same as `Eq(container)` except that the failure message also includes which elements are in one container but not the other. |
|
||||
| `Contains(e)` | `argument` contains an element that matches `e`, which can be either a value or a matcher. |
|
||||
| `Contains(e).Times(n)` | `argument` contains elements that match `e`, which can be either a value or a matcher, and the number of matches is `n`, which can be either a value or a matcher. Unlike the plain `Contains` and `Each` this allows to check for arbitrary occurrences including testing for absence with `Contains(e).Times(0)`. |
|
||||
| `Each(e)` | `argument` is a container where *every* element matches `e`, which can be either a value or a matcher. |
|
||||
| `ElementsAre(e0, e1, ..., en)` | `argument` has `n + 1` elements, where the *i*-th element matches `ei`, which can be a value or a matcher. |
|
||||
| `ElementsAreArray({e0, e1, ..., en})`, `ElementsAreArray(a_container)`, `ElementsAreArray(begin, end)`, `ElementsAreArray(array)`, or `ElementsAreArray(array, count)` | The same as `ElementsAre()` except that the expected element values/matchers come from an initializer list, STL-style container, iterator range, or C-style array. |
|
||||
@@ -146,7 +184,6 @@ messages, you can use:
|
||||
one might write:
|
||||
|
||||
```cpp
|
||||
using ::std::get;
|
||||
MATCHER(FooEq, "") {
|
||||
return std::get<0>(arg).Equals(std::get<1>(arg));
|
||||
}
|
||||
@@ -166,6 +203,11 @@ messages, you can use:
|
||||
| `Property(&class::property, m)` | `argument.property()` (or `argument->property()` when `argument` is a plain pointer) matches matcher `m`, where `argument` is an object of type _class_. The method `property()` must take no argument and be declared as `const`. |
|
||||
| `Property(property_name, &class::property, m)` | The same as the two-parameter version, but provides a better error message.
|
||||
|
||||
{: .callout .warning}
|
||||
Warning: Don't use `Property()` against member functions that you do not own,
|
||||
because taking addresses of functions is fragile and generally not part of the
|
||||
contract of the function.
|
||||
|
||||
**Notes:**
|
||||
|
||||
* You can use `FieldsAre()` to match any type that supports structured
|
||||
@@ -184,15 +226,12 @@ messages, you can use:
|
||||
EXPECT_THAT(s, FieldsAre(42, "aloha"));
|
||||
```
|
||||
|
||||
* Don't use `Property()` against member functions that you do not own, because
|
||||
taking addresses of functions is fragile and generally not part of the
|
||||
contract of the function.
|
||||
|
||||
## Matching the Result of a Function, Functor, or Callback
|
||||
|
||||
| Matcher | Description |
|
||||
| :--------------- | :------------------------------------------------ |
|
||||
| `ResultOf(f, m)` | `f(argument)` matches matcher `m`, where `f` is a function or functor. |
|
||||
| `ResultOf(result_description, f, m)` | The same as the two-parameter version, but provides a better error message.
|
||||
|
||||
## Pointer Matchers
|
||||
|
||||
@@ -217,6 +256,14 @@ Matcher | Description
|
||||
`Le()` | `x <= y`
|
||||
`Lt()` | `x < y`
|
||||
`Ne()` | `x != y`
|
||||
`FloatEq()` | `x` approximately equals `y`
|
||||
`DoubleEq()` | `x` approximately equals `y`
|
||||
`NanSensitiveFloatEq()` | Same as `FloatEq()`, but treats two NaNs as equal
|
||||
`NanSensitiveDoubleEq()` | Same as `DoubleEq()`, but treats two NaNs as equal
|
||||
`FloatNear(max_abs_error)` | `x` is within `max_abs_error` of `y`
|
||||
`DoubleNear(max_abs_error)` | `x` is within `max_abs_error` of `y`
|
||||
`NanSensitiveFloatNear(max_abs_error)` | Same as `FloatNear(max_abs_error)`, but treats two NaNs as near
|
||||
`NanSensitiveDoubleNear(max_abs_error)` | Same as `DoubleNear(max_abs_error)`, but treats two NaNs as near
|
||||
|
||||
You can use the following selectors to pick a subset of the arguments (or
|
||||
reorder them) to participate in the matching:
|
||||
@@ -237,6 +284,7 @@ You can make a matcher from one or more other matchers:
|
||||
| `AnyOf(m1, m2, ..., mn)` | `argument` matches at least one of the matchers `m1` to `mn`. |
|
||||
| `AnyOfArray({m0, m1, ..., mn})`, `AnyOfArray(a_container)`, `AnyOfArray(begin, end)`, `AnyOfArray(array)`, or `AnyOfArray(array, count)` | The same as `AnyOf()` except that the matchers come from an initializer list, STL-style container, iterator range, or C-style array. |
|
||||
| `Not(m)` | `argument` doesn't match matcher `m`. |
|
||||
| `Conditional(cond, m1, m2)` | Matches matcher `m1` if `cond` evaluates to true, else matches `m2`.|
|
||||
|
||||
## Adapters for Matchers
|
||||
|
||||
@@ -259,7 +307,14 @@ which must be a permanent callback.
|
||||
|
||||
## Defining Matchers
|
||||
|
||||
| Matcher | Description |
|
||||
{: .callout .note}
|
||||
Note: full details about defining new matchers are in the
|
||||
[cookbook](../gmock_cook_book.md#NewMatchers). In particular, if `MATCHER`
|
||||
macros are not sufficient, you can directly implement
|
||||
[monomorphic](../gmock_cook_book.md#MonomorphicMatchers) or
|
||||
[polymorphic](../gmock_cook_book.md#PolymorphicMatchers) matchers.
|
||||
|
||||
| Macro | Description |
|
||||
| :----------------------------------- | :------------------------------------ |
|
||||
| `MATCHER(IsEven, "") { return (arg % 2) == 0; }` | Defines a matcher `IsEven()` to match an even number. |
|
||||
| `MATCHER_P(IsDivisibleBy, n, "") { *result_listener << "where the remainder is " << (arg % n); return (arg % n) == 0; }` | Defines a matcher `IsDivisibleBy(n)` to match a number divisible by `n`. |
|
||||
@@ -281,3 +336,15 @@ which must be a permanent callback.
|
||||
return ExplainMatchResult(matcher, arg.nested().property(), result_listener);
|
||||
}
|
||||
```
|
||||
|
||||
5. You can use `DescribeMatcher<>` to describe another matcher. For example:
|
||||
|
||||
```cpp
|
||||
MATCHER_P(XAndYThat, matcher,
|
||||
"X that " + DescribeMatcher<int>(matcher, negation) +
|
||||
(negation ? " or" : " and") + " Y that " +
|
||||
DescribeMatcher<double>(matcher, negation)) {
|
||||
return ExplainMatchResult(matcher, arg.x(), result_listener) &&
|
||||
ExplainMatchResult(matcher, arg.y(), result_listener);
|
||||
}
|
||||
```
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
# Mocking Reference
|
||||
|
||||
This page lists the facilities provided by GoogleTest for creating and working
|
||||
with mock objects. To use them, include the header
|
||||
`gmock/gmock.h`.
|
||||
with mock objects. To use them, add `#include <gmock/gmock.h>`.
|
||||
|
||||
## Macros {#macros}
|
||||
|
||||
@@ -248,7 +247,9 @@ EXPECT_CALL(my_mock, GetNumber())
|
||||
.WillOnce(Return(3));
|
||||
```
|
||||
|
||||
The `WillOnce` clause can be used any number of times on an expectation.
|
||||
The `WillOnce` clause can be used any number of times on an expectation. Unlike
|
||||
`WillRepeatedly`, the action fed to each `WillOnce` call will be called at most
|
||||
once, so may be a move-only type and/or have an `&&`-qualified call operator.
|
||||
|
||||
#### WillRepeatedly {#EXPECT_CALL.WillRepeatedly}
|
||||
|
||||
|
||||
+160
-41
@@ -3,7 +3,7 @@
|
||||
<!--* toc_depth: 3 *-->
|
||||
|
||||
This page lists the facilities provided by GoogleTest for writing test programs.
|
||||
To use them, include the header `gtest/gtest.h`.
|
||||
To use them, add `#include <gtest/gtest.h>`.
|
||||
|
||||
## Macros
|
||||
|
||||
@@ -94,7 +94,8 @@ Instantiates the value-parameterized test suite *`TestSuiteName`* (defined with
|
||||
The argument *`InstantiationName`* is a unique name for the instantiation of the
|
||||
test suite, to distinguish between multiple instantiations. In test output, the
|
||||
instantiation name is added as a prefix to the test suite name
|
||||
*`TestSuiteName`*.
|
||||
*`TestSuiteName`*. If *`InstantiationName`* is empty
|
||||
(`INSTANTIATE_TEST_SUITE_P(, ...)`), no prefix is added.
|
||||
|
||||
The argument *`param_generator`* is one of the following GoogleTest-provided
|
||||
functions that generate the test parameters, all defined in the `::testing`
|
||||
@@ -109,6 +110,7 @@ namespace:
|
||||
| `ValuesIn(container)` or `ValuesIn(begin,end)` | Yields values from a C-style array, an STL-style container, or an iterator range `[begin, end)`. |
|
||||
| `Bool()` | Yields sequence `{false, true}`. |
|
||||
| `Combine(g1, g2, ..., gN)` | Yields as `std::tuple` *n*-tuples all combinations (Cartesian product) of the values generated by the given *n* generators `g1`, `g2`, ..., `gN`. |
|
||||
| `ConvertGenerator<T>(g)` or `ConvertGenerator(g, func)` | Yields values generated by generator `g`, `static_cast` from `T`. (Note: `T` might not be what you expect. See [*Using ConvertGenerator*](#using-convertgenerator) below.) The second overload uses `func` to perform the conversion. |
|
||||
|
||||
The optional last argument *`name_generator`* is a function or functor that
|
||||
generates custom test name suffixes based on the test parameters. The function
|
||||
@@ -121,8 +123,8 @@ custom function can be used for more control:
|
||||
```cpp
|
||||
INSTANTIATE_TEST_SUITE_P(
|
||||
MyInstantiation, MyTestSuite,
|
||||
::testing::Values(...),
|
||||
[](const ::testing::TestParamInfo<MyTestSuite::ParamType>& info) {
|
||||
testing::Values(...),
|
||||
[](const testing::TestParamInfo<MyTestSuite::ParamType>& info) {
|
||||
// Can use info.param here to generate the test suffix
|
||||
std::string name = ...
|
||||
return name;
|
||||
@@ -135,9 +137,107 @@ For more information, see
|
||||
See also
|
||||
[`GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST`](#GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST).
|
||||
|
||||
###### Using `ConvertGenerator`
|
||||
|
||||
The functions listed in the table above appear to return generators that create
|
||||
values of the desired types, but this is not generally the case. Rather, they
|
||||
typically return factory objects that convert to the the desired generators.
|
||||
This affords some flexibility in allowing you to specify values of types that
|
||||
are different from, yet implicitly convertible to, the actual parameter type
|
||||
required by your fixture class.
|
||||
|
||||
For example, you can do the following with a fixture that requires an `int`
|
||||
parameter:
|
||||
|
||||
```cpp
|
||||
INSTANTIATE_TEST_SUITE_P(MyInstantiation, MyTestSuite,
|
||||
testing::Values(1, 1.2)); // Yes, Values() supports heterogeneous argument types.
|
||||
```
|
||||
|
||||
It might seem obvious that `1.2` — a `double` — will be converted to
|
||||
an `int` but in actuality it requires some template gymnastics involving the
|
||||
indirection described in the previous paragraph.
|
||||
|
||||
What if your parameter type is not implicitly convertible from the generated
|
||||
type but is *explicitly* convertible? There will be no automatic conversion, but
|
||||
you can force it by applying `ConvertGenerator<T>`. The compiler can
|
||||
automatically deduce the target type (your fixture's parameter type), but
|
||||
because of the aforementioned indirection it cannot decide what the generated
|
||||
type should be. You need to tell it, by providing the type `T` explicitly. Thus
|
||||
`T` should not be your fixture's parameter type, but rather an intermediate type
|
||||
that is supported by the factory object, and which can be `static_cast` to the
|
||||
fixture's parameter type:
|
||||
|
||||
```cpp
|
||||
// The fixture's parameter type.
|
||||
class MyParam {
|
||||
public:
|
||||
// Explicit converting ctor.
|
||||
explicit MyParam(const std::tuple<int, bool>& t);
|
||||
...
|
||||
};
|
||||
|
||||
INSTANTIATE_TEST_SUITE_P(MyInstantiation, MyTestSuite,
|
||||
ConvertGenerator<std::tuple<int, bool>>(Combine(Values(0.1, 1.2), Bool())));
|
||||
```
|
||||
|
||||
In this example `Combine` supports the generation of `std::tuple<int, bool>>`
|
||||
objects (even though the provided values for the first tuple element are
|
||||
`double`s) and those `tuple`s get converted into `MyParam` objects by virtue of
|
||||
the call to `ConvertGenerator`.
|
||||
|
||||
For parameter types that are not convertible from the generated types you can
|
||||
provide a callable that does the conversion. The callable accepts an object of
|
||||
the generated type and returns an object of the fixture's parameter type. The
|
||||
generated type can often be deduced by the compiler from the callable's call
|
||||
signature so you do not usually need specify it explicitly (but see a caveat
|
||||
below).
|
||||
|
||||
```cpp
|
||||
// The fixture's parameter type.
|
||||
class MyParam {
|
||||
public:
|
||||
MyParam(int, bool);
|
||||
...
|
||||
};
|
||||
|
||||
INSTANTIATE_TEST_SUITE_P(MyInstantiation, MyTestSuite,
|
||||
ConvertGenerator(Combine(Values(1, 1.2), Bool()),
|
||||
[](const std::tuple<int, bool>& t){
|
||||
const auto [i, b] = t;
|
||||
return MyParam(i, b);
|
||||
}));
|
||||
```
|
||||
|
||||
The callable may be anything that can be used to initialize a `std::function`
|
||||
with the appropriate call signature. Note the callable's return object gets
|
||||
`static_cast` to the fixture's parameter type, so it does not have to be of that
|
||||
exact type, only convertible to it.
|
||||
|
||||
**Caveat:** Consider the following example.
|
||||
|
||||
```cpp
|
||||
INSTANTIATE_TEST_SUITE_P(MyInstantiation, MyTestSuite,
|
||||
ConvertGenerator(Values(std::string("s")), [](std::string_view s) { ... }));
|
||||
```
|
||||
|
||||
The `string` argument gets copied into the factory object returned by `Values`.
|
||||
Then, because the generated type deduced from the lambda is `string_view`, the
|
||||
factory object spawns a generator that holds a `string_view` referencing that
|
||||
`string`. Unfortunately, by the time this generator gets invoked, the factory
|
||||
object is gone and the `string_view` is dangling.
|
||||
|
||||
To overcome this problem you can specify the generated type explicitly:
|
||||
`ConvertGenerator<std::string>(Values(std::string("s")), [](std::string_view s)
|
||||
{ ... })`. Alternatively, you can change the lambda's signature to take a
|
||||
`std::string` or a `const std::string&` (the latter will not leave you with a
|
||||
dangling reference because the type deduction strips off the reference and the
|
||||
`const`).
|
||||
|
||||
### TYPED_TEST_SUITE {#TYPED_TEST_SUITE}
|
||||
|
||||
`TYPED_TEST_SUITE(`*`TestFixtureName`*`,`*`Types`*`)`
|
||||
`TYPED_TEST_SUITE(`*`TestFixtureName`*`,`*`Types`*`,`*`NameGenerator`*`)`
|
||||
|
||||
Defines a typed test suite based on the test fixture *`TestFixtureName`*. The
|
||||
test suite name is *`TestFixtureName`*.
|
||||
@@ -147,7 +247,7 @@ type, for example:
|
||||
|
||||
```cpp
|
||||
template <typename T>
|
||||
class MyFixture : public ::testing::Test {
|
||||
class MyFixture : public testing::Test {
|
||||
public:
|
||||
...
|
||||
using List = std::list<T>;
|
||||
@@ -167,6 +267,22 @@ TYPED_TEST_SUITE(MyFixture, MyTypes);
|
||||
The type alias (`using` or `typedef`) is necessary for the `TYPED_TEST_SUITE`
|
||||
macro to parse correctly.
|
||||
|
||||
The optional third argument *`NameGenerator`* allows specifying a class that
|
||||
exposes a templated static function `GetName(int)`. For example:
|
||||
|
||||
```cpp
|
||||
class NameGenerator {
|
||||
public:
|
||||
template <typename T>
|
||||
static std::string GetName(int) {
|
||||
if constexpr (std::is_same_v<T, char>) return "char";
|
||||
if constexpr (std::is_same_v<T, int>) return "int";
|
||||
if constexpr (std::is_same_v<T, unsigned int>) return "unsignedInt";
|
||||
}
|
||||
};
|
||||
TYPED_TEST_SUITE(MyFixture, MyTypes, NameGenerator);
|
||||
```
|
||||
|
||||
See also [`TYPED_TEST`](#TYPED_TEST) and
|
||||
[Typed Tests](../advanced.md#typed-tests) for more information.
|
||||
|
||||
@@ -276,7 +392,8 @@ must be registered with
|
||||
The argument *`InstantiationName`* is a unique name for the instantiation of the
|
||||
test suite, to distinguish between multiple instantiations. In test output, the
|
||||
instantiation name is added as a prefix to the test suite name
|
||||
*`TestSuiteName`*.
|
||||
*`TestSuiteName`*. If *`InstantiationName`* is empty
|
||||
(`INSTANTIATE_TYPED_TEST_SUITE_P(, ...)`), no prefix is added.
|
||||
|
||||
The argument *`Types`* is a [`Types`](#Types) object representing the list of
|
||||
types to run the tests on, for example:
|
||||
@@ -323,7 +440,7 @@ Then the test code should look like:
|
||||
```cpp
|
||||
namespace my_namespace {
|
||||
|
||||
class MyClassTest : public ::testing::Test {
|
||||
class MyClassTest : public testing::Test {
|
||||
...
|
||||
};
|
||||
|
||||
@@ -386,7 +503,7 @@ GoogleTest defines the following classes and types to help with writing tests.
|
||||
|
||||
### AssertionResult {#AssertionResult}
|
||||
|
||||
`::testing::AssertionResult`
|
||||
`testing::AssertionResult`
|
||||
|
||||
A class for indicating whether an assertion was successful.
|
||||
|
||||
@@ -400,14 +517,14 @@ To create an instance of this class, use one of the factory functions
|
||||
|
||||
### AssertionException {#AssertionException}
|
||||
|
||||
`::testing::AssertionException`
|
||||
`testing::AssertionException`
|
||||
|
||||
Exception which can be thrown from
|
||||
[`TestEventListener::OnTestPartResult`](#TestEventListener::OnTestPartResult).
|
||||
|
||||
### EmptyTestEventListener {#EmptyTestEventListener}
|
||||
|
||||
`::testing::EmptyTestEventListener`
|
||||
`testing::EmptyTestEventListener`
|
||||
|
||||
Provides an empty implementation of all methods in the
|
||||
[`TestEventListener`](#TestEventListener) interface, such that a subclass only
|
||||
@@ -415,7 +532,7 @@ needs to override the methods it cares about.
|
||||
|
||||
### Environment {#Environment}
|
||||
|
||||
`::testing::Environment`
|
||||
`testing::Environment`
|
||||
|
||||
Represents a global test environment. See
|
||||
[Global Set-Up and Tear-Down](../advanced.md#global-set-up-and-tear-down).
|
||||
@@ -436,7 +553,7 @@ Override this to define how to tear down the environment.
|
||||
|
||||
### ScopedTrace {#ScopedTrace}
|
||||
|
||||
`::testing::ScopedTrace`
|
||||
`testing::ScopedTrace`
|
||||
|
||||
An instance of this class causes a trace to be included in every test failure
|
||||
message generated by code in the scope of the lifetime of the `ScopedTrace`
|
||||
@@ -452,7 +569,7 @@ ScopedTrace(const char* file, int line, const T& message)
|
||||
Example usage:
|
||||
|
||||
```cpp
|
||||
::testing::ScopedTrace trace("file.cc", 123, "message");
|
||||
testing::ScopedTrace trace("file.cc", 123, "message");
|
||||
```
|
||||
|
||||
The resulting trace includes the given source file path and line number, and the
|
||||
@@ -463,7 +580,7 @@ See also [`SCOPED_TRACE`](#SCOPED_TRACE).
|
||||
|
||||
### Test {#Test}
|
||||
|
||||
`::testing::Test`
|
||||
`testing::Test`
|
||||
|
||||
The abstract class that all tests inherit from. `Test` is not copyable.
|
||||
|
||||
@@ -518,8 +635,8 @@ Logs a property for the current test, test suite, or entire invocation of the
|
||||
test program. Only the last value for a given key is logged.
|
||||
|
||||
The key must be a valid XML attribute name, and cannot conflict with the ones
|
||||
already used by GoogleTest (`name`, `status`, `time`, `classname`, `type_param`,
|
||||
and `value_param`).
|
||||
already used by GoogleTest (`name`, `file`, `line`, `status`, `time`,
|
||||
`classname`, `type_param`, and `value_param`).
|
||||
|
||||
`RecordProperty` is `public static` so it can be called from utility functions
|
||||
that are not members of the test fixture.
|
||||
@@ -551,7 +668,7 @@ after running each individual test.
|
||||
|
||||
### TestWithParam {#TestWithParam}
|
||||
|
||||
`::testing::TestWithParam<T>`
|
||||
`testing::TestWithParam<T>`
|
||||
|
||||
A convenience class which inherits from both [`Test`](#Test) and
|
||||
[`WithParamInterface<T>`](#WithParamInterface).
|
||||
@@ -671,7 +788,7 @@ during execution of `SetUpTestSuite` and `TearDownTestSuite`.
|
||||
|
||||
### TestInfo {#TestInfo}
|
||||
|
||||
`::testing::TestInfo`
|
||||
`testing::TestInfo`
|
||||
|
||||
Stores information about a test.
|
||||
|
||||
@@ -750,7 +867,7 @@ Returns the result of the test. See [`TestResult`](#TestResult).
|
||||
|
||||
### TestParamInfo {#TestParamInfo}
|
||||
|
||||
`::testing::TestParamInfo<T>`
|
||||
`testing::TestParamInfo<T>`
|
||||
|
||||
Describes a parameter to a value-parameterized test. The type `T` is the type of
|
||||
the parameter.
|
||||
@@ -760,7 +877,7 @@ and its integer index respectively.
|
||||
|
||||
### UnitTest {#UnitTest}
|
||||
|
||||
`::testing::UnitTest`
|
||||
`testing::UnitTest`
|
||||
|
||||
This class contains information about the test program.
|
||||
|
||||
@@ -928,7 +1045,7 @@ GoogleTest. See [`TestEventListeners`](#TestEventListeners).
|
||||
|
||||
### TestEventListener {#TestEventListener}
|
||||
|
||||
`::testing::TestEventListener`
|
||||
`testing::TestEventListener`
|
||||
|
||||
The interface for tracing execution of tests. The methods below are listed in
|
||||
the order the corresponding events are fired.
|
||||
@@ -1026,7 +1143,7 @@ Fired after all test activities have ended.
|
||||
|
||||
### TestEventListeners {#TestEventListeners}
|
||||
|
||||
`::testing::TestEventListeners`
|
||||
`testing::TestEventListeners`
|
||||
|
||||
Lets users add listeners to track events in GoogleTest.
|
||||
|
||||
@@ -1071,7 +1188,7 @@ the caller and makes this function return `NULL` the next time.
|
||||
|
||||
### TestPartResult {#TestPartResult}
|
||||
|
||||
`::testing::TestPartResult`
|
||||
`testing::TestPartResult`
|
||||
|
||||
A copyable object representing the result of a test part (i.e. an assertion or
|
||||
an explicit `FAIL()`, `ADD_FAILURE()`, or `SUCCESS()`).
|
||||
@@ -1153,7 +1270,7 @@ Returns true if and only if the test part failed.
|
||||
|
||||
### TestProperty {#TestProperty}
|
||||
|
||||
`::testing::TestProperty`
|
||||
`testing::TestProperty`
|
||||
|
||||
A copyable object representing a user-specified test property which can be
|
||||
output as a key/value string pair.
|
||||
@@ -1180,7 +1297,7 @@ Sets a new value, overriding the previous one.
|
||||
|
||||
### TestResult {#TestResult}
|
||||
|
||||
`::testing::TestResult`
|
||||
`testing::TestResult`
|
||||
|
||||
Contains information about the result of a single test.
|
||||
|
||||
@@ -1261,20 +1378,20 @@ range, aborts the program.
|
||||
|
||||
### TimeInMillis {#TimeInMillis}
|
||||
|
||||
`::testing::TimeInMillis`
|
||||
`testing::TimeInMillis`
|
||||
|
||||
An integer type representing time in milliseconds.
|
||||
|
||||
### Types {#Types}
|
||||
|
||||
`::testing::Types<T...>`
|
||||
`testing::Types<T...>`
|
||||
|
||||
Represents a list of types for use in typed tests and type-parameterized tests.
|
||||
|
||||
The template argument `T...` can be any number of types, for example:
|
||||
|
||||
```
|
||||
::testing::Types<char, int, unsigned int>
|
||||
testing::Types<char, int, unsigned int>
|
||||
```
|
||||
|
||||
See [Typed Tests](../advanced.md#typed-tests) and
|
||||
@@ -1283,7 +1400,7 @@ information.
|
||||
|
||||
### WithParamInterface {#WithParamInterface}
|
||||
|
||||
`::testing::WithParamInterface<T>`
|
||||
`testing::WithParamInterface<T>`
|
||||
|
||||
The pure interface class that all value-parameterized tests inherit from.
|
||||
|
||||
@@ -1309,14 +1426,16 @@ tests.
|
||||
|
||||
### InitGoogleTest {#InitGoogleTest}
|
||||
|
||||
`void ::testing::InitGoogleTest(int* argc, char** argv)` \
|
||||
`void ::testing::InitGoogleTest(int* argc, wchar_t** argv)` \
|
||||
`void ::testing::InitGoogleTest()`
|
||||
`void testing::InitGoogleTest(int* argc, char** argv)` \
|
||||
`void testing::InitGoogleTest(int* argc, wchar_t** argv)` \
|
||||
`void testing::InitGoogleTest()`
|
||||
|
||||
Initializes GoogleTest. This must be called before calling
|
||||
[`RUN_ALL_TESTS()`](#RUN_ALL_TESTS). In particular, it parses the command line
|
||||
for the flags that GoogleTest recognizes. Whenever a GoogleTest flag is seen, it
|
||||
is removed from `argv`, and `*argc` is decremented.
|
||||
is removed from `argv`, and `*argc` is decremented. Keep in mind that `argv`
|
||||
must terminate with a `NULL` pointer (i.e. `argv[argc]` is `NULL`), which is
|
||||
already the case with the default `argv` passed to `main`.
|
||||
|
||||
No value is returned. Instead, the GoogleTest flag variables are updated.
|
||||
|
||||
@@ -1328,7 +1447,7 @@ platforms where there is no `argc`/`argv`.
|
||||
|
||||
### AddGlobalTestEnvironment {#AddGlobalTestEnvironment}
|
||||
|
||||
`Environment* ::testing::AddGlobalTestEnvironment(Environment* env)`
|
||||
`Environment* testing::AddGlobalTestEnvironment(Environment* env)`
|
||||
|
||||
Adds a test environment to the test program. Must be called before
|
||||
[`RUN_ALL_TESTS()`](#RUN_ALL_TESTS) is called. See
|
||||
@@ -1341,7 +1460,7 @@ See also [`Environment`](#Environment).
|
||||
|
||||
```cpp
|
||||
template <typename Factory>
|
||||
TestInfo* ::testing::RegisterTest(const char* test_suite_name, const char* test_name,
|
||||
TestInfo* testing::RegisterTest(const char* test_suite_name, const char* test_name,
|
||||
const char* type_param, const char* value_param,
|
||||
const char* file, int line, Factory factory)
|
||||
```
|
||||
@@ -1380,27 +1499,27 @@ an all-caps name.
|
||||
|
||||
### AssertionSuccess {#AssertionSuccess}
|
||||
|
||||
`AssertionResult ::testing::AssertionSuccess()`
|
||||
`AssertionResult testing::AssertionSuccess()`
|
||||
|
||||
Creates a successful assertion result. See
|
||||
[`AssertionResult`](#AssertionResult).
|
||||
|
||||
### AssertionFailure {#AssertionFailure}
|
||||
|
||||
`AssertionResult ::testing::AssertionFailure()`
|
||||
`AssertionResult testing::AssertionFailure()`
|
||||
|
||||
Creates a failed assertion result. Use the `<<` operator to store a failure
|
||||
message:
|
||||
|
||||
```cpp
|
||||
::testing::AssertionFailure() << "My failure message";
|
||||
testing::AssertionFailure() << "My failure message";
|
||||
```
|
||||
|
||||
See [`AssertionResult`](#AssertionResult).
|
||||
|
||||
### StaticAssertTypeEq {#StaticAssertTypeEq}
|
||||
|
||||
`::testing::StaticAssertTypeEq<T1, T2>()`
|
||||
`testing::StaticAssertTypeEq<T1, T2>()`
|
||||
|
||||
Compile-time assertion for type equality. Compiles if and only if `T1` and `T2`
|
||||
are the same type. The value it returns is irrelevant.
|
||||
@@ -1409,7 +1528,7 @@ See [Type Assertions](../advanced.md#type-assertions) for more information.
|
||||
|
||||
### PrintToString {#PrintToString}
|
||||
|
||||
`std::string ::testing::PrintToString(x)`
|
||||
`std::string testing::PrintToString(x)`
|
||||
|
||||
Prints any value `x` using GoogleTest's value printer.
|
||||
|
||||
@@ -1419,7 +1538,7 @@ for more information.
|
||||
|
||||
### PrintToStringParamName {#PrintToStringParamName}
|
||||
|
||||
`std::string ::testing::PrintToStringParamName(TestParamInfo<T>& info)`
|
||||
`std::string testing::PrintToStringParamName(TestParamInfo<T>& info)`
|
||||
|
||||
A built-in parameterized test name generator which returns the result of
|
||||
[`PrintToString`](#PrintToString) called on `info.param`. Does not work when the
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
# Googletest Samples
|
||||
|
||||
If you're like us, you'd like to look at
|
||||
[googletest samples.](https://github.com/google/googletest/tree/master/googletest/samples)
|
||||
[googletest samples.](https://github.com/google/googletest/blob/main/googletest/samples)
|
||||
The sample directory has a number of well-commented samples showing how to use a
|
||||
variety of googletest features.
|
||||
|
||||
|
||||
@@ -0,0 +1,61 @@
|
||||
"""Provides a fake @fuchsia_sdk implementation that's used when the real one isn't available.
|
||||
|
||||
GoogleTest can be used with the [Fuchsia](https://fuchsia.dev/) SDK. However,
|
||||
because the Fuchsia SDK does not yet support bzlmod, GoogleTest's `MODULE.bazel`
|
||||
file by default provides a "fake" Fuchsia SDK.
|
||||
|
||||
To override this and use the real Fuchsia SDK, you can add the following to your
|
||||
project's `MODULE.bazel` file:
|
||||
|
||||
fake_fuchsia_sdk_extension =
|
||||
use_extension("@com_google_googletest//:fake_fuchsia_sdk.bzl", "fuchsia_sdk")
|
||||
override_repo(fake_fuchsia_sdk_extension, "fuchsia_sdk")
|
||||
|
||||
NOTE: The `override_repo` built-in is only available in Bazel 8.0 and higher.
|
||||
|
||||
See https://github.com/google/googletest/issues/4472 for more details of why the
|
||||
fake Fuchsia SDK is needed.
|
||||
"""
|
||||
|
||||
def _fake_fuchsia_sdk_impl(repo_ctx):
|
||||
for stub_target in repo_ctx.attr._stub_build_targets:
|
||||
stub_package = stub_target
|
||||
stub_target_name = stub_target.split("/")[-1]
|
||||
repo_ctx.file("%s/BUILD.bazel" % stub_package, """
|
||||
filegroup(
|
||||
name = "%s",
|
||||
)
|
||||
""" % stub_target_name)
|
||||
|
||||
fake_fuchsia_sdk = repository_rule(
|
||||
doc = "Used to create a fake @fuchsia_sdk repository with stub build targets.",
|
||||
implementation = _fake_fuchsia_sdk_impl,
|
||||
attrs = {
|
||||
"_stub_build_targets": attr.string_list(
|
||||
doc = "The stub build targets to initialize.",
|
||||
default = [
|
||||
"pkg/fdio",
|
||||
"pkg/syslog",
|
||||
"pkg/zx",
|
||||
],
|
||||
),
|
||||
},
|
||||
)
|
||||
|
||||
_create_fake = tag_class()
|
||||
|
||||
def _fuchsia_sdk_impl(module_ctx):
|
||||
create_fake_sdk = False
|
||||
for mod in module_ctx.modules:
|
||||
for _ in mod.tags.create_fake:
|
||||
create_fake_sdk = True
|
||||
|
||||
if create_fake_sdk:
|
||||
fake_fuchsia_sdk(name = "fuchsia_sdk")
|
||||
|
||||
return module_ctx.extension_metadata(reproducible = True)
|
||||
|
||||
fuchsia_sdk = module_extension(
|
||||
implementation = _fuchsia_sdk_impl,
|
||||
tag_classes = {"create_fake": _create_fake},
|
||||
)
|
||||
+29
-37
@@ -5,7 +5,7 @@
|
||||
# CMake build script for Google Mock.
|
||||
#
|
||||
# To run the tests for Google Mock itself on Linux, use 'make test' or
|
||||
# ctest. You can select which tests to run using 'ctest -R regex'.
|
||||
# ctest. You can select which tests to run using 'ctest -R regex'.
|
||||
# For more options, run 'ctest --help'.
|
||||
|
||||
option(gmock_build_tests "Build all of Google Mock's own tests." OFF)
|
||||
@@ -36,20 +36,15 @@ endif()
|
||||
# as ${gmock_SOURCE_DIR} and to the root binary directory as
|
||||
# ${gmock_BINARY_DIR}.
|
||||
# Language "C" is required for find_package(Threads).
|
||||
if (CMAKE_VERSION VERSION_LESS 3.0)
|
||||
project(gmock CXX C)
|
||||
else()
|
||||
cmake_policy(SET CMP0048 NEW)
|
||||
project(gmock VERSION ${GOOGLETEST_VERSION} LANGUAGES CXX C)
|
||||
endif()
|
||||
cmake_minimum_required(VERSION 2.8.12)
|
||||
cmake_minimum_required(VERSION 3.13)
|
||||
project(gmock VERSION ${GOOGLETEST_VERSION} LANGUAGES CXX C)
|
||||
|
||||
if (COMMAND set_up_hermetic_build)
|
||||
set_up_hermetic_build()
|
||||
endif()
|
||||
|
||||
# Instructs CMake to process Google Test's CMakeLists.txt and add its
|
||||
# targets to the current scope. We are placing Google Test's binary
|
||||
# targets to the current scope. We are placing Google Test's binary
|
||||
# directory in a subdirectory of our own as VC compilation may break
|
||||
# if they are the same (the default).
|
||||
add_subdirectory("${gtest_dir}" "${gmock_BINARY_DIR}/${gtest_dir}")
|
||||
@@ -65,25 +60,26 @@ else()
|
||||
endif()
|
||||
|
||||
# Although Google Test's CMakeLists.txt calls this function, the
|
||||
# changes there don't affect the current scope. Therefore we have to
|
||||
# changes there don't affect the current scope. Therefore we have to
|
||||
# call it again here.
|
||||
config_compiler_and_linker() # from ${gtest_dir}/cmake/internal_utils.cmake
|
||||
config_compiler_and_linker() # from ${gtest_dir}/cmake/internal_utils.cmake
|
||||
|
||||
# Adds Google Mock's and Google Test's header directories to the search path.
|
||||
# Get Google Test's include dirs from the target, gtest_SOURCE_DIR is broken
|
||||
# when using fetch-content with the name "GTest".
|
||||
get_target_property(gtest_include_dirs gtest INCLUDE_DIRECTORIES)
|
||||
set(gmock_build_include_dirs
|
||||
"${gmock_SOURCE_DIR}/include"
|
||||
"${gmock_SOURCE_DIR}"
|
||||
"${gtest_SOURCE_DIR}/include"
|
||||
# This directory is needed to build directly from Google Test sources.
|
||||
"${gtest_SOURCE_DIR}")
|
||||
"${gtest_include_dirs}")
|
||||
include_directories(${gmock_build_include_dirs})
|
||||
|
||||
########################################################################
|
||||
#
|
||||
# Defines the gmock & gmock_main libraries. User tests should link
|
||||
# Defines the gmock & gmock_main libraries. User tests should link
|
||||
# with one of them.
|
||||
|
||||
# Google Mock libraries. We build them using more strict warnings than what
|
||||
# Google Mock libraries. We build them using more strict warnings than what
|
||||
# are used for other targets, to ensure that Google Mock can be compiled by
|
||||
# a user aggressive about warnings.
|
||||
if (MSVC)
|
||||
@@ -105,21 +101,18 @@ else()
|
||||
target_link_libraries(gmock_main PUBLIC gmock)
|
||||
set_target_properties(gmock_main PROPERTIES VERSION ${GOOGLETEST_VERSION})
|
||||
endif()
|
||||
# If the CMake version supports it, attach header directory information
|
||||
# to the targets for when we are part of a parent build (ie being pulled
|
||||
# in via add_subdirectory() rather than being a standalone build).
|
||||
if (DEFINED CMAKE_VERSION AND NOT "${CMAKE_VERSION}" VERSION_LESS "2.8.11")
|
||||
target_include_directories(gmock SYSTEM INTERFACE
|
||||
"$<BUILD_INTERFACE:${gmock_build_include_dirs}>"
|
||||
"$<INSTALL_INTERFACE:$<INSTALL_PREFIX>/${CMAKE_INSTALL_INCLUDEDIR}>")
|
||||
target_include_directories(gmock_main SYSTEM INTERFACE
|
||||
"$<BUILD_INTERFACE:${gmock_build_include_dirs}>"
|
||||
"$<INSTALL_INTERFACE:$<INSTALL_PREFIX>/${CMAKE_INSTALL_INCLUDEDIR}>")
|
||||
endif()
|
||||
|
||||
string(REPLACE ";" "$<SEMICOLON>" dirs "${gmock_build_include_dirs}")
|
||||
target_include_directories(gmock SYSTEM INTERFACE
|
||||
"$<BUILD_INTERFACE:${dirs}>"
|
||||
"$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>")
|
||||
target_include_directories(gmock_main SYSTEM INTERFACE
|
||||
"$<BUILD_INTERFACE:${dirs}>"
|
||||
"$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>")
|
||||
|
||||
########################################################################
|
||||
#
|
||||
# Install rules
|
||||
# Install rules.
|
||||
install_project(gmock gmock_main)
|
||||
|
||||
########################################################################
|
||||
@@ -129,8 +122,8 @@ install_project(gmock gmock_main)
|
||||
# You can skip this section if you aren't interested in testing
|
||||
# Google Mock itself.
|
||||
#
|
||||
# The tests are not built by default. To build them, set the
|
||||
# gmock_build_tests option to ON. You can do it by running ccmake
|
||||
# The tests are not built by default. To build them, set the
|
||||
# gmock_build_tests option to ON. You can do it by running ccmake
|
||||
# or specifying the -Dgmock_build_tests=ON flag when running cmake.
|
||||
|
||||
if (gmock_build_tests)
|
||||
@@ -139,11 +132,7 @@ if (gmock_build_tests)
|
||||
enable_testing()
|
||||
|
||||
if (MINGW OR CYGWIN)
|
||||
if (CMAKE_VERSION VERSION_LESS "2.8.12")
|
||||
add_compile_options("-Wa,-mbig-obj")
|
||||
else()
|
||||
add_definitions("-Wa,-mbig-obj")
|
||||
endif()
|
||||
add_compile_options("-Wa,-mbig-obj")
|
||||
endif()
|
||||
|
||||
############################################################
|
||||
@@ -154,7 +143,10 @@ if (gmock_build_tests)
|
||||
cxx_test(gmock_ex_test gmock_main)
|
||||
cxx_test(gmock-function-mocker_test gmock_main)
|
||||
cxx_test(gmock-internal-utils_test gmock_main)
|
||||
cxx_test(gmock-matchers_test gmock_main)
|
||||
cxx_test(gmock-matchers-arithmetic_test gmock_main)
|
||||
cxx_test(gmock-matchers-comparisons_test gmock_main)
|
||||
cxx_test(gmock-matchers-containers_test gmock_main)
|
||||
cxx_test(gmock-matchers-misc_test gmock_main)
|
||||
cxx_test(gmock-more-actions_test gmock_main)
|
||||
cxx_test(gmock-nice-strict_test gmock_main)
|
||||
cxx_test(gmock-port_test gmock_main)
|
||||
@@ -196,7 +188,7 @@ if (gmock_build_tests)
|
||||
cxx_shared_library(shared_gmock_main "${cxx_default}"
|
||||
"${gtest_dir}/src/gtest-all.cc" src/gmock-all.cc src/gmock_main.cc)
|
||||
|
||||
# Tests that a binary can be built with Google Mock as a shared library. On
|
||||
# Tests that a binary can be built with Google Mock as a shared library. On
|
||||
# some system configurations, it may not possible to run the binary without
|
||||
# knowing more details about the system configurations. We do not try to run
|
||||
# this binary. To get a more robust shared library coverage, configure with
|
||||
|
||||
@@ -8,8 +8,8 @@ derive better designs of your system and write better tests.
|
||||
It is inspired by:
|
||||
|
||||
* [jMock](http://www.jmock.org/)
|
||||
* [EasyMock](http://www.easymock.org/)
|
||||
* [Hamcrest](http://code.google.com/p/hamcrest/)
|
||||
* [EasyMock](https://easymock.org/)
|
||||
* [Hamcrest](https://code.google.com/p/hamcrest/)
|
||||
|
||||
It is designed with C++'s specifics in mind.
|
||||
|
||||
@@ -35,10 +35,6 @@ Details and examples can be found here:
|
||||
* [gMock Cookbook](https://google.github.io/googletest/gmock_cook_book.html)
|
||||
* [gMock Cheat Sheet](https://google.github.io/googletest/gmock_cheat_sheet.html)
|
||||
|
||||
Please note that code under scripts/generator/ is from the
|
||||
[cppclean project](http://code.google.com/p/cppclean/) and under the Apache
|
||||
License, which is different from GoogleMock's license.
|
||||
|
||||
GoogleMock is a part of
|
||||
[GoogleTest C++ testing framework](http://github.com/google/googletest/) and a
|
||||
[GoogleTest C++ testing framework](https://github.com/google/googletest/) and a
|
||||
subject to the same requirements.
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -27,21 +27,23 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements some commonly used cardinalities. More
|
||||
// cardinalities can be defined by the user implementing the
|
||||
// CardinalityInterface interface if necessary.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_CARDINALITIES_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_CARDINALITIES_H_
|
||||
|
||||
#include <limits.h>
|
||||
|
||||
#include <memory>
|
||||
#include <ostream> // NOLINT
|
||||
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
@@ -61,9 +63,9 @@ namespace testing {
|
||||
// management as Cardinality objects can now be copied like plain values.
|
||||
|
||||
// The implementation of a cardinality.
|
||||
class CardinalityInterface {
|
||||
class [[nodiscard]] CardinalityInterface {
|
||||
public:
|
||||
virtual ~CardinalityInterface() {}
|
||||
virtual ~CardinalityInterface() = default;
|
||||
|
||||
// Conservative estimate on the lower/upper bound of the number of
|
||||
// calls allowed.
|
||||
@@ -86,11 +88,11 @@ class CardinalityInterface {
|
||||
// object that specifies how many times a mock function is expected to
|
||||
// be called. The implementation of Cardinality is just a std::shared_ptr
|
||||
// to const CardinalityInterface. Don't inherit from Cardinality!
|
||||
class GTEST_API_ Cardinality {
|
||||
class GTEST_API_ [[nodiscard]] Cardinality {
|
||||
public:
|
||||
// Constructs a null cardinality. Needed for storing Cardinality
|
||||
// objects in STL containers.
|
||||
Cardinality() {}
|
||||
Cardinality() = default;
|
||||
|
||||
// Constructs a Cardinality from its implementation.
|
||||
explicit Cardinality(const CardinalityInterface* impl) : impl_(impl) {}
|
||||
@@ -116,7 +118,7 @@ class GTEST_API_ Cardinality {
|
||||
// cardinality, i.e. exceed the maximum number of allowed calls.
|
||||
bool IsOverSaturatedByCallCount(int call_count) const {
|
||||
return impl_->IsSaturatedByCallCount(call_count) &&
|
||||
!impl_->IsSatisfiedByCallCount(call_count);
|
||||
!impl_->IsSatisfiedByCallCount(call_count);
|
||||
}
|
||||
|
||||
// Describes self to an ostream
|
||||
|
||||
@@ -31,11 +31,13 @@
|
||||
//
|
||||
// This file implements MOCK_METHOD.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_FUNCTION_MOCKER_H_ // NOLINT
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_FUNCTION_MOCKER_H_ // NOLINT
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_FUNCTION_MOCKER_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_FUNCTION_MOCKER_H_
|
||||
|
||||
#include <cstddef>
|
||||
#include <type_traits> // IWYU pragma: keep
|
||||
#include <utility> // IWYU pragma: keep
|
||||
|
||||
@@ -64,6 +66,39 @@ struct ThisRefAdjuster {
|
||||
}
|
||||
};
|
||||
|
||||
constexpr bool PrefixOf(const char* a, const char* b) {
|
||||
return *a == 0 || (*a == *b && internal::PrefixOf(a + 1, b + 1));
|
||||
}
|
||||
|
||||
template <size_t N, size_t M>
|
||||
constexpr bool StartsWith(const char (&prefix)[N], const char (&str)[M]) {
|
||||
return N <= M && internal::PrefixOf(prefix, str);
|
||||
}
|
||||
|
||||
template <size_t N, size_t M>
|
||||
constexpr bool EndsWith(const char (&suffix)[N], const char (&str)[M]) {
|
||||
return N <= M && internal::PrefixOf(suffix, str + M - N);
|
||||
}
|
||||
|
||||
template <size_t N, size_t M>
|
||||
constexpr bool Equals(const char (&a)[N], const char (&b)[M]) {
|
||||
return N == M && internal::PrefixOf(a, b);
|
||||
}
|
||||
|
||||
template <size_t N>
|
||||
constexpr bool ValidateSpec(const char (&spec)[N]) {
|
||||
return internal::Equals("const", spec) ||
|
||||
internal::Equals("override", spec) ||
|
||||
internal::Equals("final", spec) ||
|
||||
internal::Equals("noexcept", spec) ||
|
||||
(internal::StartsWith("noexcept(", spec) &&
|
||||
internal::EndsWith(")", spec)) ||
|
||||
internal::Equals("ref(&)", spec) ||
|
||||
internal::Equals("ref(&&)", spec) ||
|
||||
(internal::StartsWith("Calltype(", spec) &&
|
||||
internal::EndsWith(")", spec));
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
|
||||
// The style guide prohibits "using" statements in a namespace scope
|
||||
@@ -74,8 +109,11 @@ struct ThisRefAdjuster {
|
||||
using internal::FunctionMocker;
|
||||
} // namespace testing
|
||||
|
||||
#define MOCK_METHOD(...) \
|
||||
GMOCK_PP_VARIADIC_CALL(GMOCK_INTERNAL_MOCK_METHOD_ARG_, __VA_ARGS__)
|
||||
#define MOCK_METHOD(...) \
|
||||
GMOCK_INTERNAL_WARNING_PUSH() \
|
||||
GMOCK_INTERNAL_WARNING_CLANG(ignored, "-Wunused-member-function") \
|
||||
GMOCK_PP_VARIADIC_CALL(GMOCK_INTERNAL_MOCK_METHOD_ARG_, __VA_ARGS__) \
|
||||
GMOCK_INTERNAL_WARNING_POP()
|
||||
|
||||
#define GMOCK_INTERNAL_MOCK_METHOD_ARG_1(...) \
|
||||
GMOCK_INTERNAL_WRONG_ARITY(__VA_ARGS__)
|
||||
@@ -86,17 +124,18 @@ using internal::FunctionMocker;
|
||||
#define GMOCK_INTERNAL_MOCK_METHOD_ARG_3(_Ret, _MethodName, _Args) \
|
||||
GMOCK_INTERNAL_MOCK_METHOD_ARG_4(_Ret, _MethodName, _Args, ())
|
||||
|
||||
#define GMOCK_INTERNAL_MOCK_METHOD_ARG_4(_Ret, _MethodName, _Args, _Spec) \
|
||||
GMOCK_INTERNAL_ASSERT_PARENTHESIS(_Args); \
|
||||
GMOCK_INTERNAL_ASSERT_PARENTHESIS(_Spec); \
|
||||
GMOCK_INTERNAL_ASSERT_VALID_SIGNATURE( \
|
||||
GMOCK_PP_NARG0 _Args, GMOCK_INTERNAL_SIGNATURE(_Ret, _Args)); \
|
||||
GMOCK_INTERNAL_ASSERT_VALID_SPEC(_Spec) \
|
||||
GMOCK_INTERNAL_MOCK_METHOD_IMPL( \
|
||||
GMOCK_PP_NARG0 _Args, _MethodName, GMOCK_INTERNAL_HAS_CONST(_Spec), \
|
||||
GMOCK_INTERNAL_HAS_OVERRIDE(_Spec), GMOCK_INTERNAL_HAS_FINAL(_Spec), \
|
||||
GMOCK_INTERNAL_GET_NOEXCEPT_SPEC(_Spec), \
|
||||
GMOCK_INTERNAL_GET_CALLTYPE(_Spec), GMOCK_INTERNAL_GET_REF_SPEC(_Spec), \
|
||||
#define GMOCK_INTERNAL_MOCK_METHOD_ARG_4(_Ret, _MethodName, _Args, _Spec) \
|
||||
GMOCK_INTERNAL_ASSERT_PARENTHESIS(_Args); \
|
||||
GMOCK_INTERNAL_ASSERT_PARENTHESIS(_Spec); \
|
||||
GMOCK_INTERNAL_ASSERT_VALID_SIGNATURE( \
|
||||
GMOCK_PP_NARG0 _Args, GMOCK_INTERNAL_SIGNATURE(_Ret, _Args)); \
|
||||
GMOCK_INTERNAL_ASSERT_VALID_SPEC(_Spec) \
|
||||
GMOCK_INTERNAL_MOCK_METHOD_IMPL( \
|
||||
GMOCK_PP_NARG0 _Args, _MethodName, GMOCK_INTERNAL_HAS_CONST(_Spec), \
|
||||
GMOCK_INTERNAL_HAS_OVERRIDE(_Spec), GMOCK_INTERNAL_HAS_FINAL(_Spec), \
|
||||
GMOCK_INTERNAL_GET_NOEXCEPT_SPEC(_Spec), \
|
||||
GMOCK_INTERNAL_GET_CALLTYPE_SPEC(_Spec), \
|
||||
GMOCK_INTERNAL_GET_REF_SPEC(_Spec), \
|
||||
(GMOCK_INTERNAL_SIGNATURE(_Ret, _Args)))
|
||||
|
||||
#define GMOCK_INTERNAL_MOCK_METHOD_ARG_5(...) \
|
||||
@@ -142,8 +181,9 @@ using internal::FunctionMocker;
|
||||
_Signature)>::Result \
|
||||
GMOCK_INTERNAL_EXPAND(_CallType) \
|
||||
_MethodName(GMOCK_PP_REPEAT(GMOCK_INTERNAL_PARAMETER, _Signature, _N)) \
|
||||
GMOCK_PP_IF(_Constness, const, ) _RefSpec _NoexceptSpec \
|
||||
GMOCK_PP_IF(_Override, override, ) GMOCK_PP_IF(_Final, final, ) { \
|
||||
GMOCK_PP_IF(_Constness, const, ) \
|
||||
_RefSpec _NoexceptSpec GMOCK_PP_IF(_Override, override, ) \
|
||||
GMOCK_PP_IF(_Final, final, ) { \
|
||||
GMOCK_MOCKER_(_N, _Constness, _MethodName) \
|
||||
.SetOwnerAndName(this, #_MethodName); \
|
||||
return GMOCK_MOCKER_(_N, _Constness, _MethodName) \
|
||||
@@ -166,11 +206,11 @@ using internal::FunctionMocker;
|
||||
GMOCK_INTERNAL_A_MATCHER_ARGUMENT, _Signature, _N)); \
|
||||
} \
|
||||
mutable ::testing::FunctionMocker<GMOCK_PP_REMOVE_PARENS(_Signature)> \
|
||||
GMOCK_MOCKER_(_N, _Constness, _MethodName)
|
||||
GMOCK_MOCKER_(_N, _Constness, _MethodName)
|
||||
|
||||
#define GMOCK_INTERNAL_EXPAND(...) __VA_ARGS__
|
||||
|
||||
// Five Valid modifiers.
|
||||
// Valid modifiers.
|
||||
#define GMOCK_INTERNAL_HAS_CONST(_Tuple) \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_DETECT_CONST, ~, _Tuple))
|
||||
|
||||
@@ -189,6 +229,14 @@ using internal::FunctionMocker;
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_NOEXCEPT(_i, _, _elem)), \
|
||||
_elem, )
|
||||
|
||||
#define GMOCK_INTERNAL_GET_CALLTYPE_SPEC(_Tuple) \
|
||||
GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_CALLTYPE_SPEC_IF_CALLTYPE, ~, _Tuple)
|
||||
|
||||
#define GMOCK_INTERNAL_CALLTYPE_SPEC_IF_CALLTYPE(_i, _, _elem) \
|
||||
GMOCK_PP_IF( \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_CALLTYPE(_i, _, _elem)), \
|
||||
GMOCK_PP_CAT(GMOCK_INTERNAL_UNPACK_, _elem), )
|
||||
|
||||
#define GMOCK_INTERNAL_GET_REF_SPEC(_Tuple) \
|
||||
GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_REF_SPEC_IF_REF, ~, _Tuple)
|
||||
|
||||
@@ -196,19 +244,25 @@ using internal::FunctionMocker;
|
||||
GMOCK_PP_IF(GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_REF(_i, _, _elem)), \
|
||||
GMOCK_PP_CAT(GMOCK_INTERNAL_UNPACK_, _elem), )
|
||||
|
||||
#define GMOCK_INTERNAL_GET_CALLTYPE(_Tuple) \
|
||||
GMOCK_PP_FOR_EACH(GMOCK_INTERNAL_GET_CALLTYPE_IMPL, ~, _Tuple)
|
||||
|
||||
#define GMOCK_INTERNAL_ASSERT_VALID_SPEC_ELEMENT(_i, _, _elem) \
|
||||
static_assert( \
|
||||
(GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_CONST(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_OVERRIDE(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_FINAL(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_NOEXCEPT(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_REF(_i, _, _elem)) + \
|
||||
GMOCK_INTERNAL_IS_CALLTYPE(_elem)) == 1, \
|
||||
GMOCK_PP_STRINGIZE( \
|
||||
#ifdef GMOCK_INTERNAL_STRICT_SPEC_ASSERT
|
||||
#define GMOCK_INTERNAL_ASSERT_VALID_SPEC_ELEMENT(_i, _, _elem) \
|
||||
static_assert( \
|
||||
::testing::internal::ValidateSpec(GMOCK_PP_STRINGIZE(_elem)), \
|
||||
"Token \'" GMOCK_PP_STRINGIZE( \
|
||||
_elem) "\' cannot be recognized as a valid specification " \
|
||||
"modifier. Is a ',' missing?");
|
||||
#else
|
||||
#define GMOCK_INTERNAL_ASSERT_VALID_SPEC_ELEMENT(_i, _, _elem) \
|
||||
static_assert( \
|
||||
(GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_CONST(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_OVERRIDE(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_FINAL(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_NOEXCEPT(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_REF(_i, _, _elem)) + \
|
||||
GMOCK_PP_HAS_COMMA(GMOCK_INTERNAL_DETECT_CALLTYPE(_i, _, _elem))) == 1, \
|
||||
GMOCK_PP_STRINGIZE( \
|
||||
_elem) " cannot be recognized as a valid specification modifier.");
|
||||
#endif // GMOCK_INTERNAL_STRICT_SPEC_ASSERT
|
||||
|
||||
// Modifiers implementation.
|
||||
#define GMOCK_INTERNAL_DETECT_CONST(_i, _, _elem) \
|
||||
@@ -238,26 +292,12 @@ using internal::FunctionMocker;
|
||||
|
||||
#define GMOCK_INTERNAL_UNPACK_ref(x) x
|
||||
|
||||
#define GMOCK_INTERNAL_GET_CALLTYPE_IMPL(_i, _, _elem) \
|
||||
GMOCK_PP_IF(GMOCK_INTERNAL_IS_CALLTYPE(_elem), \
|
||||
GMOCK_INTERNAL_GET_VALUE_CALLTYPE, GMOCK_PP_EMPTY) \
|
||||
(_elem)
|
||||
#define GMOCK_INTERNAL_DETECT_CALLTYPE(_i, _, _elem) \
|
||||
GMOCK_PP_CAT(GMOCK_INTERNAL_DETECT_CALLTYPE_I_, _elem)
|
||||
|
||||
// TODO(iserna): GMOCK_INTERNAL_IS_CALLTYPE and
|
||||
// GMOCK_INTERNAL_GET_VALUE_CALLTYPE needed more expansions to work on windows
|
||||
// maybe they can be simplified somehow.
|
||||
#define GMOCK_INTERNAL_IS_CALLTYPE(_arg) \
|
||||
GMOCK_INTERNAL_IS_CALLTYPE_I( \
|
||||
GMOCK_PP_CAT(GMOCK_INTERNAL_IS_CALLTYPE_HELPER_, _arg))
|
||||
#define GMOCK_INTERNAL_IS_CALLTYPE_I(_arg) GMOCK_PP_IS_ENCLOSED_PARENS(_arg)
|
||||
#define GMOCK_INTERNAL_DETECT_CALLTYPE_I_Calltype ,
|
||||
|
||||
#define GMOCK_INTERNAL_GET_VALUE_CALLTYPE(_arg) \
|
||||
GMOCK_INTERNAL_GET_VALUE_CALLTYPE_I( \
|
||||
GMOCK_PP_CAT(GMOCK_INTERNAL_IS_CALLTYPE_HELPER_, _arg))
|
||||
#define GMOCK_INTERNAL_GET_VALUE_CALLTYPE_I(_arg) \
|
||||
GMOCK_PP_IDENTITY _arg
|
||||
|
||||
#define GMOCK_INTERNAL_IS_CALLTYPE_HELPER_Calltype
|
||||
#define GMOCK_INTERNAL_UNPACK_Calltype(...) __VA_ARGS__
|
||||
|
||||
// Note: The use of `identity_t` here allows _Ret to represent return types that
|
||||
// would normally need to be specified in a different way. For example, a method
|
||||
@@ -476,4 +516,4 @@ using internal::FunctionMocker;
|
||||
#define GMOCK_MOCKER_(arity, constness, Method) \
|
||||
GTEST_CONCAT_TOKEN_(gmock##constness##arity##_##Method##_, __LINE__)
|
||||
|
||||
#endif // GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_FUNCTION_MOCKER_H_
|
||||
#endif // GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_FUNCTION_MOCKER_H_
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -27,12 +27,12 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements some commonly used variadic actions.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_MORE_ACTIONS_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_MORE_ACTIONS_H_
|
||||
@@ -129,170 +129,207 @@
|
||||
|
||||
// Declares the template parameters.
|
||||
#define GMOCK_INTERNAL_DECL_HAS_1_TEMPLATE_PARAMS(kind0, name0) kind0 name0
|
||||
#define GMOCK_INTERNAL_DECL_HAS_2_TEMPLATE_PARAMS(kind0, name0, kind1, \
|
||||
name1) kind0 name0, kind1 name1
|
||||
#define GMOCK_INTERNAL_DECL_HAS_2_TEMPLATE_PARAMS(kind0, name0, kind1, name1) \
|
||||
kind0 name0, kind1 name1
|
||||
#define GMOCK_INTERNAL_DECL_HAS_3_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2) kind0 name0, kind1 name1, kind2 name2
|
||||
kind2, name2) \
|
||||
kind0 name0, kind1 name1, kind2 name2
|
||||
#define GMOCK_INTERNAL_DECL_HAS_4_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3) kind0 name0, kind1 name1, kind2 name2, \
|
||||
kind3 name3
|
||||
#define GMOCK_INTERNAL_DECL_HAS_5_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4) kind0 name0, kind1 name1, \
|
||||
kind2 name2, kind3 name3, kind4 name4
|
||||
kind2, name2, kind3, name3) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3
|
||||
#define GMOCK_INTERNAL_DECL_HAS_5_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4
|
||||
#define GMOCK_INTERNAL_DECL_HAS_6_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5) kind0 name0, \
|
||||
kind1 name1, kind2 name2, kind3 name3, kind4 name4, kind5 name5
|
||||
#define GMOCK_INTERNAL_DECL_HAS_7_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, \
|
||||
name6) kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, \
|
||||
kind5 name5, kind6 name6
|
||||
#define GMOCK_INTERNAL_DECL_HAS_8_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, name6, \
|
||||
kind7, name7) kind0 name0, kind1 name1, kind2 name2, kind3 name3, \
|
||||
kind4 name4, kind5 name5, kind6 name6, kind7 name7
|
||||
#define GMOCK_INTERNAL_DECL_HAS_9_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, name6, \
|
||||
kind7, name7, kind8, name8) kind0 name0, kind1 name1, kind2 name2, \
|
||||
kind3 name3, kind4 name4, kind5 name5, kind6 name6, kind7 name7, \
|
||||
kind8 name8
|
||||
#define GMOCK_INTERNAL_DECL_HAS_10_TEMPLATE_PARAMS(kind0, name0, kind1, \
|
||||
name1, kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, \
|
||||
name6, kind7, name7, kind8, name8, kind9, name9) kind0 name0, \
|
||||
kind1 name1, kind2 name2, kind3 name3, kind4 name4, kind5 name5, \
|
||||
kind6 name6, kind7 name7, kind8 name8, kind9 name9
|
||||
kind2, name2, kind3, name3, \
|
||||
kind4, name4, kind5, name5) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, kind5 name5
|
||||
#define GMOCK_INTERNAL_DECL_HAS_7_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, \
|
||||
kind5 name5, kind6 name6
|
||||
#define GMOCK_INTERNAL_DECL_HAS_8_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, \
|
||||
kind5 name5, kind6 name6, kind7 name7
|
||||
#define GMOCK_INTERNAL_DECL_HAS_9_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7, kind8, name8) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, \
|
||||
kind5 name5, kind6 name6, kind7 name7, kind8 name8
|
||||
#define GMOCK_INTERNAL_DECL_HAS_10_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7, kind8, name8, kind9, name9) \
|
||||
kind0 name0, kind1 name1, kind2 name2, kind3 name3, kind4 name4, \
|
||||
kind5 name5, kind6 name6, kind7 name7, kind8 name8, kind9 name9
|
||||
|
||||
// Lists the template parameters.
|
||||
#define GMOCK_INTERNAL_LIST_HAS_1_TEMPLATE_PARAMS(kind0, name0) name0
|
||||
#define GMOCK_INTERNAL_LIST_HAS_2_TEMPLATE_PARAMS(kind0, name0, kind1, \
|
||||
name1) name0, name1
|
||||
#define GMOCK_INTERNAL_LIST_HAS_2_TEMPLATE_PARAMS(kind0, name0, kind1, name1) \
|
||||
name0, name1
|
||||
#define GMOCK_INTERNAL_LIST_HAS_3_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2) name0, name1, name2
|
||||
kind2, name2) \
|
||||
name0, name1, name2
|
||||
#define GMOCK_INTERNAL_LIST_HAS_4_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3) name0, name1, name2, name3
|
||||
#define GMOCK_INTERNAL_LIST_HAS_5_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4) name0, name1, name2, name3, \
|
||||
name4
|
||||
kind2, name2, kind3, name3) \
|
||||
name0, name1, name2, name3
|
||||
#define GMOCK_INTERNAL_LIST_HAS_5_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4) \
|
||||
name0, name1, name2, name3, name4
|
||||
#define GMOCK_INTERNAL_LIST_HAS_6_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5) name0, name1, \
|
||||
name2, name3, name4, name5
|
||||
#define GMOCK_INTERNAL_LIST_HAS_7_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, \
|
||||
name6) name0, name1, name2, name3, name4, name5, name6
|
||||
#define GMOCK_INTERNAL_LIST_HAS_8_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, name6, \
|
||||
kind7, name7) name0, name1, name2, name3, name4, name5, name6, name7
|
||||
#define GMOCK_INTERNAL_LIST_HAS_9_TEMPLATE_PARAMS(kind0, name0, kind1, name1, \
|
||||
kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, name6, \
|
||||
kind7, name7, kind8, name8) name0, name1, name2, name3, name4, name5, \
|
||||
name6, name7, name8
|
||||
#define GMOCK_INTERNAL_LIST_HAS_10_TEMPLATE_PARAMS(kind0, name0, kind1, \
|
||||
name1, kind2, name2, kind3, name3, kind4, name4, kind5, name5, kind6, \
|
||||
name6, kind7, name7, kind8, name8, kind9, name9) name0, name1, name2, \
|
||||
name3, name4, name5, name6, name7, name8, name9
|
||||
kind2, name2, kind3, name3, \
|
||||
kind4, name4, kind5, name5) \
|
||||
name0, name1, name2, name3, name4, name5
|
||||
#define GMOCK_INTERNAL_LIST_HAS_7_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6) \
|
||||
name0, name1, name2, name3, name4, name5, name6
|
||||
#define GMOCK_INTERNAL_LIST_HAS_8_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7) \
|
||||
name0, name1, name2, name3, name4, name5, name6, name7
|
||||
#define GMOCK_INTERNAL_LIST_HAS_9_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7, kind8, name8) \
|
||||
name0, name1, name2, name3, name4, name5, name6, name7, name8
|
||||
#define GMOCK_INTERNAL_LIST_HAS_10_TEMPLATE_PARAMS( \
|
||||
kind0, name0, kind1, name1, kind2, name2, kind3, name3, kind4, name4, \
|
||||
kind5, name5, kind6, name6, kind7, name7, kind8, name8, kind9, name9) \
|
||||
name0, name1, name2, name3, name4, name5, name6, name7, name8, name9
|
||||
|
||||
// Declares the types of value parameters.
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_0_VALUE_PARAMS()
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_1_VALUE_PARAMS(p0) , typename p0##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_2_VALUE_PARAMS(p0, p1) , \
|
||||
typename p0##_type, typename p1##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_3_VALUE_PARAMS(p0, p1, p2) , \
|
||||
typename p0##_type, typename p1##_type, typename p2##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_4_VALUE_PARAMS(p0, p1, p2, p3) , \
|
||||
typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) , \
|
||||
typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) , \
|
||||
typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_2_VALUE_PARAMS(p0, p1) \
|
||||
, typename p0##_type, typename p1##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_3_VALUE_PARAMS(p0, p1, p2) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_4_VALUE_PARAMS(p0, p1, p2, p3) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6) , typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type
|
||||
p6) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7) , typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type, typename p7##_type
|
||||
p6, p7) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type, typename p7##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7, p8) , typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type, typename p7##_type, typename p8##_type
|
||||
p6, p7, p8) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type, typename p7##_type, typename p8##_type
|
||||
#define GMOCK_INTERNAL_DECL_TYPE_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7, p8, p9) , typename p0##_type, typename p1##_type, \
|
||||
typename p2##_type, typename p3##_type, typename p4##_type, \
|
||||
typename p5##_type, typename p6##_type, typename p7##_type, \
|
||||
typename p8##_type, typename p9##_type
|
||||
p6, p7, p8, p9) \
|
||||
, typename p0##_type, typename p1##_type, typename p2##_type, \
|
||||
typename p3##_type, typename p4##_type, typename p5##_type, \
|
||||
typename p6##_type, typename p7##_type, typename p8##_type, \
|
||||
typename p9##_type
|
||||
|
||||
// Initializes the value parameters.
|
||||
#define GMOCK_INTERNAL_INIT_AND_0_VALUE_PARAMS()\
|
||||
()
|
||||
#define GMOCK_INTERNAL_INIT_AND_1_VALUE_PARAMS(p0)\
|
||||
(p0##_type gmock_p0) : p0(::std::move(gmock_p0))
|
||||
#define GMOCK_INTERNAL_INIT_AND_2_VALUE_PARAMS(p0, p1)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1))
|
||||
#define GMOCK_INTERNAL_INIT_AND_3_VALUE_PARAMS(p0, p1, p2)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, \
|
||||
p2##_type gmock_p2) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2))
|
||||
#define GMOCK_INTERNAL_INIT_AND_4_VALUE_PARAMS(p0, p1, p2, p3)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
#define GMOCK_INTERNAL_INIT_AND_0_VALUE_PARAMS() ()
|
||||
#define GMOCK_INTERNAL_INIT_AND_1_VALUE_PARAMS(p0) \
|
||||
(p0##_type gmock_p0) : p0(::std::move(gmock_p0))
|
||||
#define GMOCK_INTERNAL_INIT_AND_2_VALUE_PARAMS(p0, p1) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1) \
|
||||
: p0(::std::move(gmock_p0)), p1(::std::move(gmock_p1))
|
||||
#define GMOCK_INTERNAL_INIT_AND_3_VALUE_PARAMS(p0, p1, p2) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2))
|
||||
#define GMOCK_INTERNAL_INIT_AND_4_VALUE_PARAMS(p0, p1, p2, p3) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3))
|
||||
#define GMOCK_INTERNAL_INIT_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4))
|
||||
#define GMOCK_INTERNAL_INIT_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, \
|
||||
p5##_type gmock_p5) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4)), \
|
||||
#define GMOCK_INTERNAL_INIT_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4))
|
||||
#define GMOCK_INTERNAL_INIT_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5))
|
||||
#define GMOCK_INTERNAL_INIT_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), p6(::std::move(gmock_p6))
|
||||
#define GMOCK_INTERNAL_INIT_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), p6(::std::move(gmock_p6)), \
|
||||
#define GMOCK_INTERNAL_INIT_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), \
|
||||
p6(::std::move(gmock_p6))
|
||||
#define GMOCK_INTERNAL_INIT_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), \
|
||||
p6(::std::move(gmock_p6)), \
|
||||
p7(::std::move(gmock_p7))
|
||||
#define GMOCK_INTERNAL_INIT_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7, \
|
||||
p8##_type gmock_p8) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), p6(::std::move(gmock_p6)), \
|
||||
p7(::std::move(gmock_p7)), p8(::std::move(gmock_p8))
|
||||
#define GMOCK_INTERNAL_INIT_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7, \
|
||||
p8) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7, p8##_type gmock_p8) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), \
|
||||
p6(::std::move(gmock_p6)), \
|
||||
p7(::std::move(gmock_p7)), \
|
||||
p8(::std::move(gmock_p8))
|
||||
#define GMOCK_INTERNAL_INIT_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8, p9)\
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7, p8##_type gmock_p8, \
|
||||
p9##_type gmock_p9) : p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), p6(::std::move(gmock_p6)), \
|
||||
p7(::std::move(gmock_p7)), p8(::std::move(gmock_p8)), \
|
||||
p7, p8, p9) \
|
||||
(p0##_type gmock_p0, p1##_type gmock_p1, p2##_type gmock_p2, \
|
||||
p3##_type gmock_p3, p4##_type gmock_p4, p5##_type gmock_p5, \
|
||||
p6##_type gmock_p6, p7##_type gmock_p7, p8##_type gmock_p8, \
|
||||
p9##_type gmock_p9) \
|
||||
: p0(::std::move(gmock_p0)), \
|
||||
p1(::std::move(gmock_p1)), \
|
||||
p2(::std::move(gmock_p2)), \
|
||||
p3(::std::move(gmock_p3)), \
|
||||
p4(::std::move(gmock_p4)), \
|
||||
p5(::std::move(gmock_p5)), \
|
||||
p6(::std::move(gmock_p6)), \
|
||||
p7(::std::move(gmock_p7)), \
|
||||
p8(::std::move(gmock_p8)), \
|
||||
p9(::std::move(gmock_p9))
|
||||
|
||||
// Defines the copy constructor
|
||||
#define GMOCK_INTERNAL_DEFN_COPY_AND_0_VALUE_PARAMS() \
|
||||
{} // Avoid https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82134
|
||||
{} // Avoid https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82134
|
||||
#define GMOCK_INTERNAL_DEFN_COPY_AND_1_VALUE_PARAMS(...) = default;
|
||||
#define GMOCK_INTERNAL_DEFN_COPY_AND_2_VALUE_PARAMS(...) = default;
|
||||
#define GMOCK_INTERNAL_DEFN_COPY_AND_3_VALUE_PARAMS(...) = default;
|
||||
@@ -307,30 +344,71 @@
|
||||
// Declares the fields for storing the value parameters.
|
||||
#define GMOCK_INTERNAL_DEFN_AND_0_VALUE_PARAMS()
|
||||
#define GMOCK_INTERNAL_DEFN_AND_1_VALUE_PARAMS(p0) p0##_type p0;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_2_VALUE_PARAMS(p0, p1) p0##_type p0; \
|
||||
p1##_type p1;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_3_VALUE_PARAMS(p0, p1, p2) p0##_type p0; \
|
||||
p1##_type p1; p2##_type p2;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_4_VALUE_PARAMS(p0, p1, p2, p3) p0##_type p0; \
|
||||
p1##_type p1; p2##_type p2; p3##_type p3;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_5_VALUE_PARAMS(p0, p1, p2, p3, \
|
||||
p4) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; p4##_type p4;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, \
|
||||
p5) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; p4##_type p4; \
|
||||
p5##_type p5;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; p4##_type p4; \
|
||||
p5##_type p5; p6##_type p6;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; p4##_type p4; \
|
||||
p5##_type p5; p6##_type p6; p7##_type p7;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; \
|
||||
p4##_type p4; p5##_type p5; p6##_type p6; p7##_type p7; p8##_type p8;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_2_VALUE_PARAMS(p0, p1) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_3_VALUE_PARAMS(p0, p1, p2) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_4_VALUE_PARAMS(p0, p1, p2, p3) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4; \
|
||||
p5##_type p5;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4; \
|
||||
p5##_type p5; \
|
||||
p6##_type p6;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4; \
|
||||
p5##_type p5; \
|
||||
p6##_type p6; \
|
||||
p7##_type p7;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7, \
|
||||
p8) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4; \
|
||||
p5##_type p5; \
|
||||
p6##_type p6; \
|
||||
p7##_type p7; \
|
||||
p8##_type p8;
|
||||
#define GMOCK_INTERNAL_DEFN_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8, p9) p0##_type p0; p1##_type p1; p2##_type p2; p3##_type p3; \
|
||||
p4##_type p4; p5##_type p5; p6##_type p6; p7##_type p7; p8##_type p8; \
|
||||
p9##_type p9;
|
||||
p7, p8, p9) \
|
||||
p0##_type p0; \
|
||||
p1##_type p1; \
|
||||
p2##_type p2; \
|
||||
p3##_type p3; \
|
||||
p4##_type p4; \
|
||||
p5##_type p5; \
|
||||
p6##_type p6; \
|
||||
p7##_type p7; \
|
||||
p8##_type p8; \
|
||||
p9##_type p9;
|
||||
|
||||
// Lists the value parameters.
|
||||
#define GMOCK_INTERNAL_LIST_AND_0_VALUE_PARAMS()
|
||||
@@ -338,72 +416,78 @@
|
||||
#define GMOCK_INTERNAL_LIST_AND_2_VALUE_PARAMS(p0, p1) p0, p1
|
||||
#define GMOCK_INTERNAL_LIST_AND_3_VALUE_PARAMS(p0, p1, p2) p0, p1, p2
|
||||
#define GMOCK_INTERNAL_LIST_AND_4_VALUE_PARAMS(p0, p1, p2, p3) p0, p1, p2, p3
|
||||
#define GMOCK_INTERNAL_LIST_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) p0, p1, \
|
||||
p2, p3, p4
|
||||
#define GMOCK_INTERNAL_LIST_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) p0, \
|
||||
p1, p2, p3, p4, p5
|
||||
#define GMOCK_INTERNAL_LIST_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6) p0, p1, p2, p3, p4, p5, p6
|
||||
#define GMOCK_INTERNAL_LIST_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7) p0, p1, p2, p3, p4, p5, p6, p7
|
||||
#define GMOCK_INTERNAL_LIST_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8) p0, p1, p2, p3, p4, p5, p6, p7, p8
|
||||
#define GMOCK_INTERNAL_LIST_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
p0, p1, p2, p3, p4
|
||||
#define GMOCK_INTERNAL_LIST_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
p0, p1, p2, p3, p4, p5
|
||||
#define GMOCK_INTERNAL_LIST_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6) \
|
||||
p0, p1, p2, p3, p4, p5, p6
|
||||
#define GMOCK_INTERNAL_LIST_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7) \
|
||||
p0, p1, p2, p3, p4, p5, p6, p7
|
||||
#define GMOCK_INTERNAL_LIST_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7, \
|
||||
p8) \
|
||||
p0, p1, p2, p3, p4, p5, p6, p7, p8
|
||||
#define GMOCK_INTERNAL_LIST_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8, p9) p0, p1, p2, p3, p4, p5, p6, p7, p8, p9
|
||||
p7, p8, p9) \
|
||||
p0, p1, p2, p3, p4, p5, p6, p7, p8, p9
|
||||
|
||||
// Lists the value parameter types.
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_0_VALUE_PARAMS()
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_1_VALUE_PARAMS(p0) , p0##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_2_VALUE_PARAMS(p0, p1) , p0##_type, \
|
||||
p1##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_3_VALUE_PARAMS(p0, p1, p2) , p0##_type, \
|
||||
p1##_type, p2##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_4_VALUE_PARAMS(p0, p1, p2, p3) , \
|
||||
p0##_type, p1##_type, p2##_type, p3##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) , \
|
||||
p0##_type, p1##_type, p2##_type, p3##_type, p4##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) , \
|
||||
p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_2_VALUE_PARAMS(p0, p1) \
|
||||
, p0##_type, p1##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_3_VALUE_PARAMS(p0, p1, p2) \
|
||||
, p0##_type, p1##_type, p2##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_4_VALUE_PARAMS(p0, p1, p2, p3) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6) , p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type, \
|
||||
p6##_type
|
||||
p6) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type, p6##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7) , p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, \
|
||||
p5##_type, p6##_type, p7##_type
|
||||
p6, p7) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type, \
|
||||
p6##_type, p7##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7, p8) , p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, \
|
||||
p5##_type, p6##_type, p7##_type, p8##_type
|
||||
p6, p7, p8) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type, \
|
||||
p6##_type, p7##_type, p8##_type
|
||||
#define GMOCK_INTERNAL_LIST_TYPE_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6, p7, p8, p9) , p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, \
|
||||
p5##_type, p6##_type, p7##_type, p8##_type, p9##_type
|
||||
p6, p7, p8, p9) \
|
||||
, p0##_type, p1##_type, p2##_type, p3##_type, p4##_type, p5##_type, \
|
||||
p6##_type, p7##_type, p8##_type, p9##_type
|
||||
|
||||
// Declares the value parameters.
|
||||
#define GMOCK_INTERNAL_DECL_AND_0_VALUE_PARAMS()
|
||||
#define GMOCK_INTERNAL_DECL_AND_1_VALUE_PARAMS(p0) p0##_type p0
|
||||
#define GMOCK_INTERNAL_DECL_AND_2_VALUE_PARAMS(p0, p1) p0##_type p0, \
|
||||
p1##_type p1
|
||||
#define GMOCK_INTERNAL_DECL_AND_3_VALUE_PARAMS(p0, p1, p2) p0##_type p0, \
|
||||
p1##_type p1, p2##_type p2
|
||||
#define GMOCK_INTERNAL_DECL_AND_4_VALUE_PARAMS(p0, p1, p2, p3) p0##_type p0, \
|
||||
p1##_type p1, p2##_type p2, p3##_type p3
|
||||
#define GMOCK_INTERNAL_DECL_AND_5_VALUE_PARAMS(p0, p1, p2, p3, \
|
||||
p4) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4
|
||||
#define GMOCK_INTERNAL_DECL_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, \
|
||||
p5) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5
|
||||
#define GMOCK_INTERNAL_DECL_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, \
|
||||
p6) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6
|
||||
#define GMOCK_INTERNAL_DECL_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6, p7##_type p7
|
||||
#define GMOCK_INTERNAL_DECL_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, \
|
||||
p4##_type p4, p5##_type p5, p6##_type p6, p7##_type p7, p8##_type p8
|
||||
#define GMOCK_INTERNAL_DECL_AND_2_VALUE_PARAMS(p0, p1) \
|
||||
p0##_type p0, p1##_type p1
|
||||
#define GMOCK_INTERNAL_DECL_AND_3_VALUE_PARAMS(p0, p1, p2) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2
|
||||
#define GMOCK_INTERNAL_DECL_AND_4_VALUE_PARAMS(p0, p1, p2, p3) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3
|
||||
#define GMOCK_INTERNAL_DECL_AND_5_VALUE_PARAMS(p0, p1, p2, p3, p4) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4
|
||||
#define GMOCK_INTERNAL_DECL_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5
|
||||
#define GMOCK_INTERNAL_DECL_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6
|
||||
#define GMOCK_INTERNAL_DECL_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6, p7##_type p7
|
||||
#define GMOCK_INTERNAL_DECL_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, p7, \
|
||||
p8) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6, p7##_type p7, p8##_type p8
|
||||
#define GMOCK_INTERNAL_DECL_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8, p9) p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, \
|
||||
p4##_type p4, p5##_type p5, p6##_type p6, p7##_type p7, p8##_type p8, \
|
||||
p9##_type p9
|
||||
p7, p8, p9) \
|
||||
p0##_type p0, p1##_type p1, p2##_type p2, p3##_type p3, p4##_type p4, \
|
||||
p5##_type p5, p6##_type p6, p7##_type p7, p8##_type p8, p9##_type p9
|
||||
|
||||
// The suffix of the class template implementing the action template.
|
||||
#define GMOCK_INTERNAL_COUNT_AND_0_VALUE_PARAMS()
|
||||
@@ -415,40 +499,43 @@
|
||||
#define GMOCK_INTERNAL_COUNT_AND_6_VALUE_PARAMS(p0, p1, p2, p3, p4, p5) P6
|
||||
#define GMOCK_INTERNAL_COUNT_AND_7_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6) P7
|
||||
#define GMOCK_INTERNAL_COUNT_AND_8_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7) P8
|
||||
p7) \
|
||||
P8
|
||||
#define GMOCK_INTERNAL_COUNT_AND_9_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8) P9
|
||||
p7, p8) \
|
||||
P9
|
||||
#define GMOCK_INTERNAL_COUNT_AND_10_VALUE_PARAMS(p0, p1, p2, p3, p4, p5, p6, \
|
||||
p7, p8, p9) P10
|
||||
p7, p8, p9) \
|
||||
P10
|
||||
|
||||
// The name of the class template implementing the action template.
|
||||
#define GMOCK_ACTION_CLASS_(name, value_params)\
|
||||
GTEST_CONCAT_TOKEN_(name##Action, GMOCK_INTERNAL_COUNT_##value_params)
|
||||
#define GMOCK_ACTION_CLASS_(name, value_params) \
|
||||
GTEST_CONCAT_TOKEN_(name##Action, GMOCK_INTERNAL_COUNT_##value_params)
|
||||
|
||||
#define ACTION_TEMPLATE(name, template_params, value_params) \
|
||||
template <GMOCK_INTERNAL_DECL_##template_params \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
class GMOCK_ACTION_CLASS_(name, value_params) { \
|
||||
public: \
|
||||
explicit GMOCK_ACTION_CLASS_(name, value_params)( \
|
||||
GMOCK_INTERNAL_DECL_##value_params) \
|
||||
GMOCK_PP_IF(GMOCK_PP_IS_EMPTY(GMOCK_INTERNAL_COUNT_##value_params), \
|
||||
= default; , \
|
||||
: impl_(std::make_shared<gmock_Impl>( \
|
||||
GMOCK_INTERNAL_LIST_##value_params)) { }) \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)( \
|
||||
const GMOCK_ACTION_CLASS_(name, value_params)&) noexcept \
|
||||
GMOCK_INTERNAL_DEFN_COPY_##value_params \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)( \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)&&) noexcept \
|
||||
GMOCK_INTERNAL_DEFN_COPY_##value_params \
|
||||
template <typename F> \
|
||||
operator ::testing::Action<F>() const { \
|
||||
= default; \
|
||||
, : impl_(std::make_shared<gmock_Impl>( \
|
||||
GMOCK_INTERNAL_LIST_##value_params)){}) \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)(const GMOCK_ACTION_CLASS_( \
|
||||
name, value_params) &) noexcept GMOCK_INTERNAL_DEFN_COPY_ \
|
||||
##value_params \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)(GMOCK_ACTION_CLASS_( \
|
||||
name, value_params) &&) noexcept GMOCK_INTERNAL_DEFN_COPY_ \
|
||||
##value_params template <typename F> \
|
||||
operator ::testing::Action<F>() const { \
|
||||
return GMOCK_PP_IF( \
|
||||
GMOCK_PP_IS_EMPTY(GMOCK_INTERNAL_COUNT_##value_params), \
|
||||
(::testing::internal::MakeAction<F, gmock_Impl>()), \
|
||||
(::testing::internal::MakeAction<F>(impl_))); \
|
||||
(::testing::internal::MakeAction<F, gmock_Impl>()), \
|
||||
(::testing::internal::MakeAction<F>(impl_))); \
|
||||
} \
|
||||
\
|
||||
private: \
|
||||
class gmock_Impl { \
|
||||
public: \
|
||||
@@ -458,34 +545,35 @@
|
||||
return_type gmock_PerformImpl(GMOCK_ACTION_ARG_TYPES_AND_NAMES_) const; \
|
||||
GMOCK_INTERNAL_DEFN_##value_params \
|
||||
}; \
|
||||
GMOCK_PP_IF(GMOCK_PP_IS_EMPTY(GMOCK_INTERNAL_COUNT_##value_params), \
|
||||
, std::shared_ptr<const gmock_Impl> impl_;) \
|
||||
GMOCK_PP_IF(GMOCK_PP_IS_EMPTY(GMOCK_INTERNAL_COUNT_##value_params), , \
|
||||
std::shared_ptr<const gmock_Impl> impl_;) \
|
||||
}; \
|
||||
template <GMOCK_INTERNAL_DECL_##template_params \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
GMOCK_ACTION_CLASS_(name, value_params)< \
|
||||
GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params> name( \
|
||||
GMOCK_INTERNAL_DECL_##value_params) GTEST_MUST_USE_RESULT_; \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
[[nodiscard]] GMOCK_ACTION_CLASS_( \
|
||||
name, value_params)<GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params> \
|
||||
name(GMOCK_INTERNAL_DECL_##value_params); \
|
||||
template <GMOCK_INTERNAL_DECL_##template_params \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
inline GMOCK_ACTION_CLASS_(name, value_params)< \
|
||||
GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params> name( \
|
||||
GMOCK_INTERNAL_DECL_##value_params) { \
|
||||
return GMOCK_ACTION_CLASS_(name, value_params)< \
|
||||
GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params>( \
|
||||
GMOCK_INTERNAL_LIST_##value_params); \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
inline GMOCK_ACTION_CLASS_( \
|
||||
name, value_params)<GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params> \
|
||||
name(GMOCK_INTERNAL_DECL_##value_params) { \
|
||||
return GMOCK_ACTION_CLASS_( \
|
||||
name, value_params)<GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params>( \
|
||||
GMOCK_INTERNAL_LIST_##value_params); \
|
||||
} \
|
||||
template <GMOCK_INTERNAL_DECL_##template_params \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
GMOCK_INTERNAL_DECL_TYPE_##value_params> \
|
||||
template <typename function_type, typename return_type, typename args_type, \
|
||||
GMOCK_ACTION_TEMPLATE_ARGS_NAMES_> \
|
||||
return_type GMOCK_ACTION_CLASS_(name, value_params)< \
|
||||
GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params>::gmock_Impl::gmock_PerformImpl( \
|
||||
GMOCK_ACTION_ARG_TYPES_AND_NAMES_UNUSED_) const
|
||||
return_type GMOCK_ACTION_CLASS_( \
|
||||
name, value_params)<GMOCK_INTERNAL_LIST_##template_params \
|
||||
GMOCK_INTERNAL_LIST_TYPE_##value_params>:: \
|
||||
gmock_Impl::gmock_PerformImpl(GMOCK_ACTION_ARG_TYPES_AND_NAMES_UNUSED_) \
|
||||
const
|
||||
|
||||
namespace testing {
|
||||
|
||||
@@ -494,10 +582,7 @@ namespace testing {
|
||||
// the macro definition, as the warnings are generated when the macro
|
||||
// is expanded and macro expansion cannot contain #pragma. Therefore
|
||||
// we suppress them here.
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4100)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100)
|
||||
|
||||
namespace internal {
|
||||
|
||||
@@ -506,20 +591,23 @@ namespace internal {
|
||||
// Overloads for other custom-callables are provided in the
|
||||
// internal/custom/gmock-generated-actions.h header.
|
||||
template <typename F, typename... Args>
|
||||
auto InvokeArgument(F f, Args... args) -> decltype(f(args...)) {
|
||||
return f(args...);
|
||||
auto InvokeArgument(F &&f,
|
||||
Args... args) -> decltype(std::forward<F>(f)(args...)) {
|
||||
return std::forward<F>(f)(args...);
|
||||
}
|
||||
|
||||
template <std::size_t index, typename... Params>
|
||||
struct InvokeArgumentAction {
|
||||
template <typename... Args>
|
||||
auto operator()(Args&&... args) const -> decltype(internal::InvokeArgument(
|
||||
std::get<index>(std::forward_as_tuple(std::forward<Args>(args)...)),
|
||||
std::declval<const Params&>()...)) {
|
||||
internal::FlatTuple<Args&&...> args_tuple(FlatTupleConstructTag{},
|
||||
std::forward<Args>(args)...);
|
||||
return params.Apply([&](const Params&... unpacked_params) {
|
||||
auto&& callable = args_tuple.template Get<index>();
|
||||
template <typename... Args,
|
||||
typename = typename std::enable_if<(index < sizeof...(Args))>::type>
|
||||
auto operator()(Args &&...args) const
|
||||
-> decltype(internal::InvokeArgument(
|
||||
std::get<index>(std::forward_as_tuple(std::forward<Args>(args)...)),
|
||||
std::declval<const Params &>()...)) {
|
||||
internal::FlatTuple<Args &&...> args_tuple(FlatTupleConstructTag{},
|
||||
std::forward<Args>(args)...);
|
||||
return params.Apply([&](const Params &...unpacked_params) {
|
||||
auto &&callable = std::move(args_tuple.template Get<index>());
|
||||
return internal::InvokeArgument(
|
||||
std::forward<decltype(callable)>(callable), unpacked_params...);
|
||||
});
|
||||
@@ -559,14 +647,12 @@ struct InvokeArgumentAction {
|
||||
// later.
|
||||
template <std::size_t index, typename... Params>
|
||||
internal::InvokeArgumentAction<index, typename std::decay<Params>::type...>
|
||||
InvokeArgument(Params&&... params) {
|
||||
InvokeArgument(Params &&...params) {
|
||||
return {internal::FlatTuple<typename std::decay<Params>::type...>(
|
||||
internal::FlatTupleConstructTag{}, std::forward<Params>(params)...)};
|
||||
}
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100
|
||||
|
||||
} // namespace testing
|
||||
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements some matchers that depend on gmock-matchers.h.
|
||||
@@ -35,35 +34,77 @@
|
||||
// Note that tests are implemented in gmock-matchers_test.cc rather than
|
||||
// gmock-more-matchers-test.cc.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_MORE_MATCHERS_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_MORE_MATCHERS_H_
|
||||
|
||||
#include <ostream>
|
||||
#include <string>
|
||||
|
||||
#include "gmock/gmock-matchers.h"
|
||||
|
||||
namespace testing {
|
||||
|
||||
// Silence C4100 (unreferenced formal
|
||||
// parameter) for MSVC
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4100)
|
||||
#if (_MSC_VER == 1900)
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100)
|
||||
#if defined(_MSC_VER) && (_MSC_VER == 1900)
|
||||
// and silence C4800 (C4800: 'int *const ': forcing value
|
||||
// to bool 'true' or 'false') for MSVC 14
|
||||
# pragma warning(disable:4800)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4800)
|
||||
#endif
|
||||
|
||||
// Defines a matcher that matches an empty container. The container must
|
||||
// support both size() and empty(), which all STL-like containers provide.
|
||||
MATCHER(IsEmpty, negation ? "isn't empty" : "is empty") {
|
||||
if (arg.empty()) {
|
||||
return true;
|
||||
namespace internal {
|
||||
|
||||
// Implements the polymorphic IsEmpty matcher, which
|
||||
// can be used as a Matcher<T> as long as T is either a container that defines
|
||||
// empty() and size() (e.g. std::vector or std::string), or a C-style string.
|
||||
class [[nodiscard]] IsEmptyMatcher {
|
||||
public:
|
||||
// Matches anything that defines empty() and size().
|
||||
template <typename MatcheeContainerType>
|
||||
bool MatchAndExplain(const MatcheeContainerType& c,
|
||||
MatchResultListener* listener) const {
|
||||
if (c.empty()) {
|
||||
return true;
|
||||
}
|
||||
*listener << "whose size is " << c.size();
|
||||
return false;
|
||||
}
|
||||
*result_listener << "whose size is " << arg.size();
|
||||
return false;
|
||||
|
||||
// Matches C-style strings.
|
||||
bool MatchAndExplain(const char* s, MatchResultListener* listener) const {
|
||||
if (s == nullptr) {
|
||||
return false;
|
||||
}
|
||||
return MatchAndExplain(std::string(s), listener);
|
||||
}
|
||||
|
||||
#if GTEST_HAS_STD_WSTRING
|
||||
// Matches C-style wide strings.
|
||||
bool MatchAndExplain(const wchar_t* s, MatchResultListener* listener) const {
|
||||
if (s == nullptr) {
|
||||
return false;
|
||||
}
|
||||
return MatchAndExplain(std::wstring(s), listener);
|
||||
}
|
||||
#endif // GTEST_HAS_STD_WSTRING
|
||||
|
||||
// Describes what this matcher matches.
|
||||
void DescribeTo(std::ostream* os) const { *os << "is empty"; }
|
||||
|
||||
void DescribeNegationTo(std::ostream* os) const { *os << "isn't empty"; }
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
|
||||
// Creates a polymorphic matcher that matches an empty container or C-style
|
||||
// string. The container must support both size() and empty(), which all
|
||||
// STL-like containers provide.
|
||||
inline PolymorphicMatcher<internal::IsEmptyMatcher> IsEmpty() {
|
||||
return MakePolymorphicMatcher(internal::IsEmptyMatcher());
|
||||
}
|
||||
|
||||
// Define a matcher that matches a value that evaluates in boolean
|
||||
@@ -82,10 +123,10 @@ MATCHER(IsFalse, negation ? "is true" : "is false") {
|
||||
return !static_cast<bool>(arg);
|
||||
}
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#if defined(_MSC_VER) && (_MSC_VER == 1900)
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4800
|
||||
#endif
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100
|
||||
|
||||
} // namespace testing
|
||||
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Implements class templates NiceMock, NaggyMock, and StrictMock.
|
||||
//
|
||||
// Given a mock class MockFoo that is created using Google Mock,
|
||||
@@ -58,11 +57,13 @@
|
||||
// In particular, nesting NiceMock, NaggyMock, and StrictMock is NOT
|
||||
// supported.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_NICE_STRICT_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_NICE_STRICT_H_
|
||||
|
||||
#include <cstdint>
|
||||
#include <type_traits>
|
||||
|
||||
#include "gmock/gmock-spec-builders.h"
|
||||
@@ -70,11 +71,11 @@
|
||||
|
||||
namespace testing {
|
||||
template <class MockClass>
|
||||
class NiceMock;
|
||||
class [[nodiscard]] NiceMock;
|
||||
template <class MockClass>
|
||||
class NaggyMock;
|
||||
class [[nodiscard]] NaggyMock;
|
||||
template <class MockClass>
|
||||
class StrictMock;
|
||||
class [[nodiscard]] StrictMock;
|
||||
|
||||
namespace internal {
|
||||
template <typename T>
|
||||
@@ -97,7 +98,7 @@ constexpr bool HasStrictnessModifier() {
|
||||
// deregistration. This guarantees that MockClass's constructor and destructor
|
||||
// run with the same level of strictness as its instance methods.
|
||||
|
||||
#if GTEST_OS_WINDOWS && !GTEST_OS_WINDOWS_MINGW && \
|
||||
#if defined(GTEST_OS_WINDOWS) && !defined(GTEST_OS_WINDOWS_MINGW) && \
|
||||
(defined(_MSC_VER) || defined(__clang__))
|
||||
// We need to mark these classes with this declspec to ensure that
|
||||
// the empty base class optimization is performed.
|
||||
@@ -107,33 +108,45 @@ constexpr bool HasStrictnessModifier() {
|
||||
#endif
|
||||
|
||||
template <typename Base>
|
||||
class NiceMockImpl {
|
||||
class [[nodiscard]] NiceMockImpl {
|
||||
public:
|
||||
NiceMockImpl() { ::testing::Mock::AllowUninterestingCalls(this); }
|
||||
NiceMockImpl() {
|
||||
::testing::Mock::AllowUninterestingCalls(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
|
||||
~NiceMockImpl() { ::testing::Mock::UnregisterCallReaction(this); }
|
||||
~NiceMockImpl() {
|
||||
::testing::Mock::UnregisterCallReaction(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Base>
|
||||
class NaggyMockImpl {
|
||||
class [[nodiscard]] NaggyMockImpl {
|
||||
public:
|
||||
NaggyMockImpl() { ::testing::Mock::WarnUninterestingCalls(this); }
|
||||
NaggyMockImpl() {
|
||||
::testing::Mock::WarnUninterestingCalls(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
|
||||
~NaggyMockImpl() { ::testing::Mock::UnregisterCallReaction(this); }
|
||||
~NaggyMockImpl() {
|
||||
::testing::Mock::UnregisterCallReaction(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Base>
|
||||
class StrictMockImpl {
|
||||
class [[nodiscard]] StrictMockImpl {
|
||||
public:
|
||||
StrictMockImpl() { ::testing::Mock::FailUninterestingCalls(this); }
|
||||
StrictMockImpl() {
|
||||
::testing::Mock::FailUninterestingCalls(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
|
||||
~StrictMockImpl() { ::testing::Mock::UnregisterCallReaction(this); }
|
||||
~StrictMockImpl() {
|
||||
::testing::Mock::UnregisterCallReaction(reinterpret_cast<uintptr_t>(this));
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
|
||||
template <class MockClass>
|
||||
class GTEST_INTERNAL_EMPTY_BASE_CLASS NiceMock
|
||||
class [[nodiscard]] GTEST_INTERNAL_EMPTY_BASE_CLASS NiceMock
|
||||
: private internal::NiceMockImpl<MockClass>,
|
||||
public MockClass {
|
||||
public:
|
||||
@@ -169,11 +182,12 @@ class GTEST_INTERNAL_EMPTY_BASE_CLASS NiceMock
|
||||
}
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(NiceMock);
|
||||
NiceMock(const NiceMock&) = delete;
|
||||
NiceMock& operator=(const NiceMock&) = delete;
|
||||
};
|
||||
|
||||
template <class MockClass>
|
||||
class GTEST_INTERNAL_EMPTY_BASE_CLASS NaggyMock
|
||||
class [[nodiscard]] GTEST_INTERNAL_EMPTY_BASE_CLASS NaggyMock
|
||||
: private internal::NaggyMockImpl<MockClass>,
|
||||
public MockClass {
|
||||
static_assert(!internal::HasStrictnessModifier<MockClass>(),
|
||||
@@ -210,11 +224,12 @@ class GTEST_INTERNAL_EMPTY_BASE_CLASS NaggyMock
|
||||
}
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(NaggyMock);
|
||||
NaggyMock(const NaggyMock&) = delete;
|
||||
NaggyMock& operator=(const NaggyMock&) = delete;
|
||||
};
|
||||
|
||||
template <class MockClass>
|
||||
class GTEST_INTERNAL_EMPTY_BASE_CLASS StrictMock
|
||||
class [[nodiscard]] GTEST_INTERNAL_EMPTY_BASE_CLASS StrictMock
|
||||
: private internal::StrictMockImpl<MockClass>,
|
||||
public MockClass {
|
||||
public:
|
||||
@@ -251,7 +266,8 @@ class GTEST_INTERNAL_EMPTY_BASE_CLASS StrictMock
|
||||
}
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(StrictMock);
|
||||
StrictMock(const StrictMock&) = delete;
|
||||
StrictMock& operator=(const StrictMock&) = delete;
|
||||
};
|
||||
|
||||
#undef GTEST_INTERNAL_EMPTY_BASE_CLASS
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -27,13 +27,10 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This is the main header file a user should include.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_GMOCK_H_
|
||||
|
||||
@@ -56,22 +53,24 @@
|
||||
//
|
||||
// where all clauses are optional and WillOnce() can be repeated.
|
||||
|
||||
#include "gmock/gmock-actions.h"
|
||||
#include "gmock/gmock-cardinalities.h"
|
||||
#include "gmock/gmock-function-mocker.h"
|
||||
#include "gmock/gmock-matchers.h"
|
||||
#include "gmock/gmock-more-actions.h"
|
||||
#include "gmock/gmock-more-matchers.h"
|
||||
#include "gmock/gmock-nice-strict.h"
|
||||
#include "gmock/gmock-actions.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-cardinalities.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-function-mocker.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-matchers.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-more-actions.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-more-matchers.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-nice-strict.h" // IWYU pragma: export
|
||||
#include "gmock/gmock-spec-builders.h" // IWYU pragma: export
|
||||
#include "gmock/internal/gmock-internal-utils.h"
|
||||
|
||||
namespace testing {
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
|
||||
// Declares Google Mock flags that we want a user to use programmatically.
|
||||
GMOCK_DECLARE_bool_(catch_leaked_mocks);
|
||||
GMOCK_DECLARE_string_(verbose);
|
||||
GMOCK_DECLARE_int32_(default_mock_behavior);
|
||||
|
||||
namespace testing {
|
||||
|
||||
// Initializes Google Mock. This must be called before running the
|
||||
// tests. In particular, it parses the command line for the flags
|
||||
// that Google Mock recognizes. Whenever a Google Mock flag is seen,
|
||||
|
||||
@@ -14,3 +14,5 @@ The following macros can be defined:
|
||||
* `GMOCK_DEFINE_bool_(name, default_val, doc)`
|
||||
* `GMOCK_DEFINE_int32_(name, default_val, doc)`
|
||||
* `GMOCK_DEFINE_string_(name, default_val, doc)`
|
||||
* `GMOCK_FLAG_GET(flag_name)`
|
||||
* `GMOCK_FLAG_SET(flag_name, value)`
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_GENERATED_ACTIONS_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_GENERATED_ACTIONS_H_
|
||||
|
||||
@@ -26,10 +26,11 @@
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
//
|
||||
|
||||
// Injection point for custom user configurations. See README for details
|
||||
//
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_MATCHERS_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_MATCHERS_H_
|
||||
|
||||
@@ -26,12 +26,13 @@
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
//
|
||||
|
||||
// Injection point for custom user configurations. See README for details
|
||||
//
|
||||
// ** Custom implementation starts here **
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_PORT_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_CUSTOM_GMOCK_PORT_H_
|
||||
|
||||
@@ -27,22 +27,27 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file defines some utilities useful for implementing Google
|
||||
// Mock. They are subject to change without notice, so please DO NOT
|
||||
// USE THEM IN USER CODE.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_INTERNAL_UTILS_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_INTERNAL_UTILS_H_
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include <iterator>
|
||||
#include <ostream> // NOLINT
|
||||
#include <string>
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
@@ -55,15 +60,12 @@ namespace internal {
|
||||
|
||||
// Silence MSVC C4100 (unreferenced formal parameter) and
|
||||
// C4805('==': unsafe mix of type 'const int' and type 'const bool')
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4100)
|
||||
# pragma warning(disable:4805)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100 4805)
|
||||
|
||||
// Joins a vector of strings as if they are fields of a tuple; returns
|
||||
// the joined string.
|
||||
GTEST_API_ std::string JoinAsTuple(const Strings& fields);
|
||||
GTEST_API_ std::string JoinAsKeyValueTuple(
|
||||
const std::vector<const char*>& names, const Strings& values);
|
||||
|
||||
// Converts an identifier name to a space-separated list of lower-case
|
||||
// words. Each maximum substring of the form [A-Za-z][a-z]*|\d+ is
|
||||
@@ -78,9 +80,36 @@ template <typename Pointer>
|
||||
inline const typename Pointer::element_type* GetRawPointer(const Pointer& p) {
|
||||
return p.get();
|
||||
}
|
||||
// This overload version is for std::reference_wrapper, which does not work with
|
||||
// the overload above, as it does not have an `element_type`.
|
||||
template <typename Element>
|
||||
inline const Element* GetRawPointer(const std::reference_wrapper<Element>& r) {
|
||||
return &r.get();
|
||||
}
|
||||
|
||||
// This overloaded version is for the raw pointer case.
|
||||
template <typename Element>
|
||||
inline Element* GetRawPointer(Element* p) { return p; }
|
||||
inline Element* GetRawPointer(Element* p) {
|
||||
return p;
|
||||
}
|
||||
|
||||
// Default definitions for all compilers.
|
||||
// NOTE: If you implement support for other compilers, make sure to avoid
|
||||
// unexpected overlaps.
|
||||
// (e.g., Clang also processes #pragma GCC, and clang-cl also handles _MSC_VER.)
|
||||
#define GMOCK_INTERNAL_WARNING_PUSH()
|
||||
#define GMOCK_INTERNAL_WARNING_CLANG(Level, Name)
|
||||
#define GMOCK_INTERNAL_WARNING_POP()
|
||||
|
||||
#if defined(__clang__)
|
||||
#undef GMOCK_INTERNAL_WARNING_PUSH
|
||||
#define GMOCK_INTERNAL_WARNING_PUSH() _Pragma("clang diagnostic push")
|
||||
#undef GMOCK_INTERNAL_WARNING_CLANG
|
||||
#define GMOCK_INTERNAL_WARNING_CLANG(Level, Warning) \
|
||||
_Pragma(GMOCK_PP_INTERNAL_STRINGIZE(clang diagnostic Level Warning))
|
||||
#undef GMOCK_INTERNAL_WARNING_POP
|
||||
#define GMOCK_INTERNAL_WARNING_POP() _Pragma("clang diagnostic pop")
|
||||
#endif
|
||||
|
||||
// MSVC treats wchar_t as a native type usually, but treats it as the
|
||||
// same as unsigned short when the compiler option /Zc:wchar_t- is
|
||||
@@ -89,7 +118,7 @@ inline Element* GetRawPointer(Element* p) { return p; }
|
||||
#if defined(_MSC_VER) && !defined(_NATIVE_WCHAR_T_DEFINED)
|
||||
// wchar_t is a typedef.
|
||||
#else
|
||||
# define GMOCK_WCHAR_T_IS_NATIVE_ 1
|
||||
#define GMOCK_WCHAR_T_IS_NATIVE_ 1
|
||||
#endif
|
||||
|
||||
// In what follows, we use the term "kind" to indicate whether a type
|
||||
@@ -97,18 +126,20 @@ inline Element* GetRawPointer(Element* p) { return p; }
|
||||
// or none of them. This categorization is useful for determining
|
||||
// when a matcher argument type can be safely converted to another
|
||||
// type in the implementation of SafeMatcherCast.
|
||||
enum TypeKind {
|
||||
kBool, kInteger, kFloatingPoint, kOther
|
||||
};
|
||||
enum TypeKind { kBool, kInteger, kFloatingPoint, kOther };
|
||||
|
||||
// KindOf<T>::value is the kind of type T.
|
||||
template <typename T> struct KindOf {
|
||||
template <typename T>
|
||||
struct KindOf {
|
||||
enum { value = kOther }; // The default kind.
|
||||
};
|
||||
|
||||
// This macro declares that the kind of 'type' is 'kind'.
|
||||
#define GMOCK_DECLARE_KIND_(type, kind) \
|
||||
template <> struct KindOf<type> { enum { value = kind }; }
|
||||
template <> \
|
||||
struct KindOf<type> { \
|
||||
enum { value = kind }; \
|
||||
}
|
||||
|
||||
GMOCK_DECLARE_KIND_(bool, kBool);
|
||||
|
||||
@@ -116,13 +147,13 @@ GMOCK_DECLARE_KIND_(bool, kBool);
|
||||
GMOCK_DECLARE_KIND_(char, kInteger);
|
||||
GMOCK_DECLARE_KIND_(signed char, kInteger);
|
||||
GMOCK_DECLARE_KIND_(unsigned char, kInteger);
|
||||
GMOCK_DECLARE_KIND_(short, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(short, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(unsigned short, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(int, kInteger);
|
||||
GMOCK_DECLARE_KIND_(unsigned int, kInteger);
|
||||
GMOCK_DECLARE_KIND_(long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(unsigned long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(long long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(unsigned long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(long long, kInteger); // NOLINT
|
||||
GMOCK_DECLARE_KIND_(unsigned long long, kInteger); // NOLINT
|
||||
|
||||
#if GMOCK_WCHAR_T_IS_NATIVE_
|
||||
@@ -137,7 +168,7 @@ GMOCK_DECLARE_KIND_(long double, kFloatingPoint);
|
||||
#undef GMOCK_DECLARE_KIND_
|
||||
|
||||
// Evaluates to the kind of 'type'.
|
||||
#define GMOCK_KIND_OF_(type) \
|
||||
#define GMOCK_KIND_OF_(type) \
|
||||
static_cast< ::testing::internal::TypeKind>( \
|
||||
::testing::internal::KindOf<type>::value)
|
||||
|
||||
@@ -163,11 +194,11 @@ using LosslessArithmeticConvertibleImpl = std::integral_constant<
|
||||
// Converting between integers of different widths is allowed so long
|
||||
// as the conversion does not go from signed to unsigned.
|
||||
(((sizeof(From) < sizeof(To)) &&
|
||||
!(std::is_signed<From>::value && !std::is_signed<To>::value)) ||
|
||||
!(std::is_signed_v<From> && !std::is_signed_v<To>)) ||
|
||||
// Converting between integers of the same width only requires the
|
||||
// two types to have the same signedness.
|
||||
((sizeof(From) == sizeof(To)) &&
|
||||
(std::is_signed<From>::value == std::is_signed<To>::value)))
|
||||
(std::is_signed_v<From> == std::is_signed_v<To>)))
|
||||
) ? true
|
||||
// Floating point conversions are lossless if and only if `To` is at least
|
||||
// as wide as `From`.
|
||||
@@ -190,14 +221,12 @@ using LosslessArithmeticConvertible =
|
||||
|
||||
// This interface knows how to report a Google Mock failure (either
|
||||
// non-fatal or fatal).
|
||||
class FailureReporterInterface {
|
||||
class [[nodiscard]] FailureReporterInterface {
|
||||
public:
|
||||
// The type of a failure (either non-fatal or fatal).
|
||||
enum FailureType {
|
||||
kNonfatal, kFatal
|
||||
};
|
||||
enum FailureType { kNonfatal, kFatal };
|
||||
|
||||
virtual ~FailureReporterInterface() {}
|
||||
virtual ~FailureReporterInterface() = default;
|
||||
|
||||
// Reports a failure that occurred at the given source file location.
|
||||
virtual void ReportFailure(FailureType type, const char* file, int line,
|
||||
@@ -215,8 +244,8 @@ GTEST_API_ FailureReporterInterface* GetFailureReporter();
|
||||
inline void Assert(bool condition, const char* file, int line,
|
||||
const std::string& msg) {
|
||||
if (!condition) {
|
||||
GetFailureReporter()->ReportFailure(FailureReporterInterface::kFatal,
|
||||
file, line, msg);
|
||||
GetFailureReporter()->ReportFailure(FailureReporterInterface::kFatal, file,
|
||||
line, msg);
|
||||
}
|
||||
}
|
||||
inline void Assert(bool condition, const char* file, int line) {
|
||||
@@ -237,10 +266,7 @@ inline void Expect(bool condition, const char* file, int line) {
|
||||
}
|
||||
|
||||
// Severity level of a log.
|
||||
enum LogSeverity {
|
||||
kInfo = 0,
|
||||
kWarning = 1
|
||||
};
|
||||
enum LogSeverity { kInfo = 0, kWarning = 1 };
|
||||
|
||||
// Valid values for the --gmock_verbose flag.
|
||||
|
||||
@@ -271,22 +297,14 @@ GTEST_API_ void Log(LogSeverity severity, const std::string& message,
|
||||
//
|
||||
// ON_CALL(mock, Method({}, nullptr))...
|
||||
//
|
||||
class WithoutMatchers {
|
||||
class [[nodiscard]] WithoutMatchers {
|
||||
private:
|
||||
WithoutMatchers() {}
|
||||
friend GTEST_API_ WithoutMatchers GetWithoutMatchers();
|
||||
WithoutMatchers() = default;
|
||||
|
||||
public:
|
||||
GTEST_API_ static WithoutMatchers Get();
|
||||
};
|
||||
|
||||
// Internal use only: access the singleton instance of WithoutMatchers.
|
||||
GTEST_API_ WithoutMatchers GetWithoutMatchers();
|
||||
|
||||
// Disable MSVC warnings for infinite recursion, since in this case the
|
||||
// the recursion is unreachable.
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4717)
|
||||
#endif
|
||||
|
||||
// Invalid<T>() is usable as an expression of type T, but will terminate
|
||||
// the program with an assertion failure if actually run. This is useful
|
||||
// when a value of type T is needed for compilation, but the statement
|
||||
@@ -294,16 +312,34 @@ GTEST_API_ WithoutMatchers GetWithoutMatchers();
|
||||
// crashes).
|
||||
template <typename T>
|
||||
inline T Invalid() {
|
||||
Assert(false, "", -1, "Internal error: attempt to return invalid value");
|
||||
// This statement is unreachable, and would never terminate even if it
|
||||
// could be reached. It is provided only to placate compiler warnings
|
||||
// about missing return statements.
|
||||
Assert(/*condition=*/false, /*file=*/"", /*line=*/-1,
|
||||
"Internal error: attempt to return invalid value");
|
||||
#if defined(__GNUC__) || defined(__clang__)
|
||||
__builtin_unreachable();
|
||||
#elif defined(_MSC_VER)
|
||||
__assume(0);
|
||||
#else
|
||||
return Invalid<T>();
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
void GetValueType(const void*);
|
||||
|
||||
template <class T>
|
||||
typename std::iterator_traits<
|
||||
decltype(std::begin(std::declval<T&>()))>::value_type
|
||||
GetValueType(T*);
|
||||
|
||||
template <class T, class = void>
|
||||
struct RangeTraits {
|
||||
typedef decltype(internal::GetValueType(
|
||||
static_cast<std::remove_reference_t<T>*>(nullptr))) value_type;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
struct RangeTraits<T, std::conditional_t<true, void, typename T::value_type>> {
|
||||
typedef typename T::value_type value_type;
|
||||
};
|
||||
|
||||
// Given a raw type (i.e. having no top-level reference or const
|
||||
// modifier) RawContainer that's either an STL-style container or a
|
||||
@@ -322,13 +358,13 @@ inline T Invalid() {
|
||||
// This generic version is used when RawContainer itself is already an
|
||||
// STL-style container.
|
||||
template <class RawContainer>
|
||||
class StlContainerView {
|
||||
class [[nodiscard]] StlContainerView {
|
||||
public:
|
||||
typedef RawContainer type;
|
||||
typedef const type& const_reference;
|
||||
|
||||
static const_reference ConstReference(const RawContainer& container) {
|
||||
static_assert(!std::is_const<RawContainer>::value,
|
||||
static_assert(!std::is_const_v<RawContainer>,
|
||||
"RawContainer type must not be const");
|
||||
return container;
|
||||
}
|
||||
@@ -337,7 +373,7 @@ class StlContainerView {
|
||||
|
||||
// This specialization is used when RawContainer is a native array type.
|
||||
template <typename Element, size_t N>
|
||||
class StlContainerView<Element[N]> {
|
||||
class [[nodiscard]] StlContainerView<Element[N]> {
|
||||
public:
|
||||
typedef typename std::remove_const<Element>::type RawElement;
|
||||
typedef internal::NativeArray<RawElement> type;
|
||||
@@ -349,7 +385,7 @@ class StlContainerView<Element[N]> {
|
||||
typedef const type const_reference;
|
||||
|
||||
static const_reference ConstReference(const Element (&array)[N]) {
|
||||
static_assert(std::is_same<Element, RawElement>::value,
|
||||
static_assert(std::is_same_v<Element, RawElement>,
|
||||
"Element type must not be const");
|
||||
return type(array, N, RelationToSourceReference());
|
||||
}
|
||||
@@ -361,7 +397,7 @@ class StlContainerView<Element[N]> {
|
||||
// This specialization is used when RawContainer is a native array
|
||||
// represented as a (pointer, size) tuple.
|
||||
template <typename ElementPointer, typename Size>
|
||||
class StlContainerView< ::std::tuple<ElementPointer, Size> > {
|
||||
class [[nodiscard]] StlContainerView< ::std::tuple<ElementPointer, Size> > {
|
||||
public:
|
||||
typedef typename std::remove_const<
|
||||
typename std::pointer_traits<ElementPointer>::element_type>::type
|
||||
@@ -381,7 +417,8 @@ class StlContainerView< ::std::tuple<ElementPointer, Size> > {
|
||||
|
||||
// The following specialization prevents the user from instantiating
|
||||
// StlContainer with a reference type.
|
||||
template <typename T> class StlContainerView<T&>;
|
||||
template <typename T>
|
||||
class StlContainerView<T&>;
|
||||
|
||||
// A type transform to remove constness from the first part of a pair.
|
||||
// Pairs like that are used as the value_type of associative containers,
|
||||
@@ -402,20 +439,21 @@ struct RemoveConstFromKey<std::pair<const K, V> > {
|
||||
GTEST_API_ void IllegalDoDefault(const char* file, int line);
|
||||
|
||||
template <typename F, typename Tuple, size_t... Idx>
|
||||
auto ApplyImpl(F&& f, Tuple&& args, IndexSequence<Idx...>) -> decltype(
|
||||
std::forward<F>(f)(std::get<Idx>(std::forward<Tuple>(args))...)) {
|
||||
auto ApplyImpl(F&& f, Tuple&& args, std::index_sequence<Idx...>)
|
||||
-> decltype(std::forward<F>(f)(
|
||||
std::get<Idx>(std::forward<Tuple>(args))...)) {
|
||||
return std::forward<F>(f)(std::get<Idx>(std::forward<Tuple>(args))...);
|
||||
}
|
||||
|
||||
// Apply the function to a tuple of arguments.
|
||||
template <typename F, typename Tuple>
|
||||
auto Apply(F&& f, Tuple&& args) -> decltype(
|
||||
ApplyImpl(std::forward<F>(f), std::forward<Tuple>(args),
|
||||
MakeIndexSequence<std::tuple_size<
|
||||
typename std::remove_reference<Tuple>::type>::value>())) {
|
||||
auto Apply(F&& f, Tuple&& args) -> decltype(ApplyImpl(
|
||||
std::forward<F>(f), std::forward<Tuple>(args),
|
||||
std::make_index_sequence<
|
||||
std::tuple_size_v<std::remove_reference_t<Tuple>>>())) {
|
||||
return ApplyImpl(std::forward<F>(f), std::forward<Tuple>(args),
|
||||
MakeIndexSequence<std::tuple_size<
|
||||
typename std::remove_reference<Tuple>::type>::value>());
|
||||
std::make_index_sequence<
|
||||
std::tuple_size_v<std::remove_reference_t<Tuple>>>());
|
||||
}
|
||||
|
||||
// Template struct Function<F>, where F must be a function type, contains
|
||||
@@ -446,12 +484,16 @@ struct Function<R(Args...)> {
|
||||
using MakeResultIgnoredValue = IgnoredValue(Args...);
|
||||
};
|
||||
|
||||
template <typename R, typename... Args>
|
||||
constexpr size_t Function<R(Args...)>::ArgumentCount;
|
||||
// Workaround for MSVC error C2039: 'type': is not a member of 'std'
|
||||
// when std::tuple_element is used.
|
||||
// See: https://github.com/google/googletest/issues/3931
|
||||
// Can be replaced with std::tuple_element_t in C++14.
|
||||
template <size_t I, typename T>
|
||||
using TupleElement = std::tuple_element_t<I, T>;
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
bool Base64Unescape(const std::string& encoded, std::string* decoded);
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100 4805
|
||||
|
||||
} // namespace internal
|
||||
} // namespace testing
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
//
|
||||
// Low-level types and utilities for porting Google Mock to various
|
||||
// platforms. All macros ending with _ and symbols defined in an
|
||||
// internal namespace are subject to change without notice. Code
|
||||
@@ -35,13 +34,15 @@
|
||||
// end with _ are part of Google Mock's public API and can be used by
|
||||
// code outside Google Mock.
|
||||
|
||||
// GOOGLETEST_CM0002 DO NOT DELETE
|
||||
// IWYU pragma: private, include "gmock/gmock.h"
|
||||
// IWYU pragma: friend gmock/.*
|
||||
|
||||
#ifndef GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_PORT_H_
|
||||
#define GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_PORT_H_
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <cstdint>
|
||||
#include <iostream>
|
||||
|
||||
@@ -53,35 +54,87 @@
|
||||
// here, as Google Mock depends on Google Test. Only add a utility
|
||||
// here if it's truly specific to Google Mock.
|
||||
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
#include "gmock/internal/custom/gmock-port.h"
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
|
||||
#if defined(GTEST_HAS_ABSL) && !defined(GTEST_NO_ABSL_FLAGS)
|
||||
#include "absl/flags/declare.h"
|
||||
#include "absl/flags/flag.h"
|
||||
#endif
|
||||
|
||||
// For MS Visual C++, check the compiler version. At least VS 2015 is
|
||||
// required to compile Google Mock.
|
||||
#if defined(_MSC_VER) && _MSC_VER < 1900
|
||||
# error "At least Visual C++ 2015 (14.0) is required to compile Google Mock."
|
||||
#error "At least Visual C++ 2015 (14.0) is required to compile Google Mock."
|
||||
#endif
|
||||
|
||||
// Macro for referencing flags. This is public as we want the user to
|
||||
// use this syntax to reference Google Mock flags.
|
||||
#define GMOCK_FLAG_NAME_(name) gmock_##name
|
||||
#define GMOCK_FLAG(name) FLAGS_gmock_##name
|
||||
|
||||
#if !defined(GMOCK_DECLARE_bool_)
|
||||
|
||||
// Macros for declaring flags.
|
||||
# define GMOCK_DECLARE_bool_(name) extern GTEST_API_ bool GMOCK_FLAG(name)
|
||||
# define GMOCK_DECLARE_int32_(name) extern GTEST_API_ int32_t GMOCK_FLAG(name)
|
||||
# define GMOCK_DECLARE_string_(name) \
|
||||
extern GTEST_API_ ::std::string GMOCK_FLAG(name)
|
||||
// Pick a command line flags implementation.
|
||||
#if defined(GTEST_HAS_ABSL) && !defined(GTEST_NO_ABSL_FLAGS)
|
||||
|
||||
// Macros for defining flags.
|
||||
# define GMOCK_DEFINE_bool_(name, default_val, doc) \
|
||||
GTEST_API_ bool GMOCK_FLAG(name) = (default_val)
|
||||
# define GMOCK_DEFINE_int32_(name, default_val, doc) \
|
||||
GTEST_API_ int32_t GMOCK_FLAG(name) = (default_val)
|
||||
# define GMOCK_DEFINE_string_(name, default_val, doc) \
|
||||
GTEST_API_ ::std::string GMOCK_FLAG(name) = (default_val)
|
||||
#define GMOCK_DEFINE_bool_(name, default_val, doc) \
|
||||
ABSL_FLAG(bool, GMOCK_FLAG_NAME_(name), default_val, doc)
|
||||
#define GMOCK_DEFINE_int32_(name, default_val, doc) \
|
||||
ABSL_FLAG(int32_t, GMOCK_FLAG_NAME_(name), default_val, doc)
|
||||
#define GMOCK_DEFINE_string_(name, default_val, doc) \
|
||||
ABSL_FLAG(std::string, GMOCK_FLAG_NAME_(name), default_val, doc)
|
||||
|
||||
#endif // !defined(GMOCK_DECLARE_bool_)
|
||||
// Macros for declaring flags.
|
||||
#define GMOCK_DECLARE_bool_(name) \
|
||||
GTEST_API_ ABSL_DECLARE_FLAG(bool, GMOCK_FLAG_NAME_(name))
|
||||
#define GMOCK_DECLARE_int32_(name) \
|
||||
GTEST_API_ ABSL_DECLARE_FLAG(int32_t, GMOCK_FLAG_NAME_(name))
|
||||
#define GMOCK_DECLARE_string_(name) \
|
||||
GTEST_API_ ABSL_DECLARE_FLAG(std::string, GMOCK_FLAG_NAME_(name))
|
||||
|
||||
#define GMOCK_FLAG_GET(name) ::absl::GetFlag(GMOCK_FLAG(name))
|
||||
#define GMOCK_FLAG_SET(name, value) \
|
||||
(void)(::absl::SetFlag(&GMOCK_FLAG(name), value))
|
||||
|
||||
#else // defined(GTEST_HAS_ABSL) && !defined(GTEST_NO_ABSL_FLAGS)
|
||||
|
||||
// Macros for defining flags.
|
||||
#define GMOCK_DEFINE_bool_(name, default_val, doc) \
|
||||
namespace testing { \
|
||||
GTEST_API_ bool GMOCK_FLAG(name) = (default_val); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
#define GMOCK_DEFINE_int32_(name, default_val, doc) \
|
||||
namespace testing { \
|
||||
GTEST_API_ int32_t GMOCK_FLAG(name) = (default_val); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
#define GMOCK_DEFINE_string_(name, default_val, doc) \
|
||||
namespace testing { \
|
||||
GTEST_API_ ::std::string GMOCK_FLAG(name) = (default_val); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
|
||||
// Macros for declaring flags.
|
||||
#define GMOCK_DECLARE_bool_(name) \
|
||||
namespace testing { \
|
||||
GTEST_API_ extern bool GMOCK_FLAG(name); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
#define GMOCK_DECLARE_int32_(name) \
|
||||
namespace testing { \
|
||||
GTEST_API_ extern int32_t GMOCK_FLAG(name); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
#define GMOCK_DECLARE_string_(name) \
|
||||
namespace testing { \
|
||||
GTEST_API_ extern ::std::string GMOCK_FLAG(name); \
|
||||
} \
|
||||
static_assert(true, "no-op to require trailing semicolon")
|
||||
|
||||
#define GMOCK_FLAG_GET(name) ::testing::GMOCK_FLAG(name)
|
||||
#define GMOCK_FLAG_SET(name, value) (void)(::testing::GMOCK_FLAG(name) = value)
|
||||
|
||||
#endif // defined(GTEST_HAS_ABSL) && !defined(GTEST_NO_ABSL_FLAGS)
|
||||
|
||||
#endif // GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_PORT_H_
|
||||
|
||||
@@ -25,16 +25,18 @@
|
||||
// GMOCK_PP_NARG(x, y) => 2
|
||||
// GMOCK_PP_NARG(PAIR) => 2
|
||||
//
|
||||
// Requires: the number of arguments after expansion is at most 15.
|
||||
#define GMOCK_PP_NARG(...) \
|
||||
GMOCK_PP_INTERNAL_16TH( \
|
||||
(__VA_ARGS__, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0))
|
||||
// Requires: the number of arguments after expansion is at most 31.
|
||||
#define GMOCK_PP_NARG(...) \
|
||||
GMOCK_PP_INTERNAL_32ND((__VA_ARGS__, 31, 30, 29, 28, 27, 26, 25, 24, 23, 22, \
|
||||
21, 20, 19, 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, \
|
||||
8, 7, 6, 5, 4, 3, 2, 1, 0))
|
||||
|
||||
// Returns 1 if the expansion of arguments has an unprotected comma. Otherwise
|
||||
// returns 0. Requires no more than 15 unprotected commas.
|
||||
#define GMOCK_PP_HAS_COMMA(...) \
|
||||
GMOCK_PP_INTERNAL_16TH( \
|
||||
(__VA_ARGS__, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0))
|
||||
// returns 0. Requires no more than 31 unprotected commas.
|
||||
#define GMOCK_PP_HAS_COMMA(...) \
|
||||
GMOCK_PP_INTERNAL_32ND((__VA_ARGS__, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, \
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, \
|
||||
0, 0))
|
||||
|
||||
// Returns the first argument.
|
||||
#define GMOCK_PP_HEAD(...) GMOCK_PP_INTERNAL_HEAD((__VA_ARGS__, unusedArg))
|
||||
@@ -51,7 +53,7 @@
|
||||
// If the arguments after expansion have no tokens, evaluates to `1`. Otherwise
|
||||
// evaluates to `0`.
|
||||
//
|
||||
// Requires: * the number of arguments after expansion is at most 15.
|
||||
// Requires: * the number of arguments after expansion is at most 31.
|
||||
// * If the argument is a macro, it must be able to be called with one
|
||||
// argument.
|
||||
//
|
||||
@@ -104,7 +106,7 @@
|
||||
// GMOCK_PP_NARG0(x, y) => 2
|
||||
// GMOCK_PP_NARG0(PAIR) => 2
|
||||
//
|
||||
// Requires: * the number of arguments after expansion is at most 15.
|
||||
// Requires: * the number of arguments after expansion is at most 31.
|
||||
// * If the argument is a macro, it must be able to be called with one
|
||||
// argument.
|
||||
#define GMOCK_PP_NARG0(...) \
|
||||
@@ -127,7 +129,7 @@
|
||||
// Expands to _Macro(0, _Data, e1) _Macro(1, _Data, e2) ... _Macro(K -1, _Data,
|
||||
// eK) as many of GMOCK_INTERNAL_NARG0 _Tuple.
|
||||
// Requires: * |_Macro| can be called with 3 arguments.
|
||||
// * |_Tuple| expansion has no more than 15 elements.
|
||||
// * |_Tuple| expansion has no more than 31 elements.
|
||||
#define GMOCK_PP_FOR_EACH(_Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_CAT(GMOCK_PP_INTERNAL_FOR_EACH_IMPL_, GMOCK_PP_NARG0 _Tuple) \
|
||||
(0, _Macro, _Data, _Tuple)
|
||||
@@ -135,20 +137,21 @@
|
||||
// Expands to _Macro(0, _Data, ) _Macro(1, _Data, ) ... _Macro(K - 1, _Data, )
|
||||
// Empty if _K = 0.
|
||||
// Requires: * |_Macro| can be called with 3 arguments.
|
||||
// * |_K| literal between 0 and 15
|
||||
// * |_K| literal between 0 and 31
|
||||
#define GMOCK_PP_REPEAT(_Macro, _Data, _N) \
|
||||
GMOCK_PP_CAT(GMOCK_PP_INTERNAL_FOR_EACH_IMPL_, _N) \
|
||||
(0, _Macro, _Data, GMOCK_PP_INTENRAL_EMPTY_TUPLE)
|
||||
|
||||
// Increments the argument, requires the argument to be between 0 and 15.
|
||||
// Increments the argument, requires the argument to be between 0 and 31.
|
||||
#define GMOCK_PP_INC(_i) GMOCK_PP_CAT(GMOCK_PP_INTERNAL_INC_, _i)
|
||||
|
||||
// Returns comma if _i != 0. Requires _i to be between 0 and 15.
|
||||
// Returns comma if _i != 0. Requires _i to be between 0 and 31.
|
||||
#define GMOCK_PP_COMMA_IF(_i) GMOCK_PP_CAT(GMOCK_PP_INTERNAL_COMMA_IF_, _i)
|
||||
|
||||
// Internal details follow. Do not use any of these symbols outside of this
|
||||
// file or we will break your code.
|
||||
#define GMOCK_PP_INTENRAL_EMPTY_TUPLE (, , , , , , , , , , , , , , , )
|
||||
#define GMOCK_PP_INTENRAL_EMPTY_TUPLE \
|
||||
(, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , )
|
||||
#define GMOCK_PP_INTERNAL_CAT(_1, _2) _1##_2
|
||||
#define GMOCK_PP_INTERNAL_STRINGIZE(...) #__VA_ARGS__
|
||||
#define GMOCK_PP_INTERNAL_CAT_5(_1, _2, _3, _4, _5) _1##_2##_3##_4##_5
|
||||
@@ -164,12 +167,13 @@
|
||||
// tokens. We do that by using a "IDENTITY(MACRO PARENTHESIZED_ARGS)" macro. We
|
||||
// define one per possible macro that relies on this behavior. Note "_Args" must
|
||||
// be parenthesized.
|
||||
#define GMOCK_PP_INTERNAL_INTERNAL_16TH(_1, _2, _3, _4, _5, _6, _7, _8, _9, \
|
||||
_10, _11, _12, _13, _14, _15, _16, \
|
||||
...) \
|
||||
_16
|
||||
#define GMOCK_PP_INTERNAL_16TH(_Args) \
|
||||
GMOCK_PP_IDENTITY(GMOCK_PP_INTERNAL_INTERNAL_16TH _Args)
|
||||
#define GMOCK_PP_INTERNAL_INTERNAL_32ND( \
|
||||
_1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, \
|
||||
_17, _18, _19, _20, _21, _22, _23, _24, _25, _26, _27, _28, _29, _30, _31, \
|
||||
_32, ...) \
|
||||
_32
|
||||
#define GMOCK_PP_INTERNAL_32ND(_Args) \
|
||||
GMOCK_PP_IDENTITY(GMOCK_PP_INTERNAL_INTERNAL_32ND _Args)
|
||||
#define GMOCK_PP_INTERNAL_INTERNAL_HEAD(_1, ...) _1
|
||||
#define GMOCK_PP_INTERNAL_HEAD(_Args) \
|
||||
GMOCK_PP_IDENTITY(GMOCK_PP_INTERNAL_INTERNAL_HEAD _Args)
|
||||
@@ -198,6 +202,22 @@
|
||||
#define GMOCK_PP_INTERNAL_INC_13 14
|
||||
#define GMOCK_PP_INTERNAL_INC_14 15
|
||||
#define GMOCK_PP_INTERNAL_INC_15 16
|
||||
#define GMOCK_PP_INTERNAL_INC_16 17
|
||||
#define GMOCK_PP_INTERNAL_INC_17 18
|
||||
#define GMOCK_PP_INTERNAL_INC_18 19
|
||||
#define GMOCK_PP_INTERNAL_INC_19 20
|
||||
#define GMOCK_PP_INTERNAL_INC_20 21
|
||||
#define GMOCK_PP_INTERNAL_INC_21 22
|
||||
#define GMOCK_PP_INTERNAL_INC_22 23
|
||||
#define GMOCK_PP_INTERNAL_INC_23 24
|
||||
#define GMOCK_PP_INTERNAL_INC_24 25
|
||||
#define GMOCK_PP_INTERNAL_INC_25 26
|
||||
#define GMOCK_PP_INTERNAL_INC_26 27
|
||||
#define GMOCK_PP_INTERNAL_INC_27 28
|
||||
#define GMOCK_PP_INTERNAL_INC_28 29
|
||||
#define GMOCK_PP_INTERNAL_INC_29 30
|
||||
#define GMOCK_PP_INTERNAL_INC_30 31
|
||||
#define GMOCK_PP_INTERNAL_INC_31 32
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_0
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_1 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_2 ,
|
||||
@@ -214,6 +234,22 @@
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_13 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_14 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_15 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_16 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_17 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_18 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_19 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_20 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_21 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_22 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_23 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_24 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_25 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_26 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_27 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_28 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_29 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_30 ,
|
||||
#define GMOCK_PP_INTERNAL_COMMA_IF_31 ,
|
||||
#define GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, _element) \
|
||||
_Macro(_i, _Data, _element)
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_0(_i, _Macro, _Data, _Tuple)
|
||||
@@ -275,5 +311,69 @@
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_14(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_16(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_15(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_17(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_16(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_18(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_17(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_19(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_18(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_20(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_19(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_21(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_20(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_22(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_21(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_23(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_22(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_24(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_23(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_25(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_24(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_26(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_25(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_27(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_26(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_28(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_27(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_29(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_28(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_30(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_29(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
#define GMOCK_PP_INTERNAL_FOR_EACH_IMPL_31(_i, _Macro, _Data, _Tuple) \
|
||||
GMOCK_PP_INTERNAL_CALL_MACRO(_Macro, _i, _Data, GMOCK_PP_HEAD _Tuple) \
|
||||
GMOCK_PP_INTERNAL_FOR_EACH_IMPL_30(GMOCK_PP_INC(_i), _Macro, _Data, \
|
||||
(GMOCK_PP_TAIL _Tuple))
|
||||
|
||||
#endif // GOOGLEMOCK_INCLUDE_GMOCK_INTERNAL_GMOCK_PP_H_
|
||||
|
||||
@@ -1,5 +0,0 @@
|
||||
# Please Note:
|
||||
|
||||
Files in this directory are no longer supported by the maintainers. They
|
||||
represent mostly historical artifacts and supported by the community only. There
|
||||
is no guarantee whatsoever that these scripts still work.
|
||||
@@ -1,256 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2009, Google Inc.
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are
|
||||
# met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright
|
||||
# notice, this list of conditions and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above
|
||||
# copyright notice, this list of conditions and the following disclaimer
|
||||
# in the documentation and/or other materials provided with the
|
||||
# distribution.
|
||||
# * Neither the name of Google Inc. nor the names of its
|
||||
# contributors may be used to endorse or promote products derived from
|
||||
# this software without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
"""fuse_gmock_files.py v0.1.0.
|
||||
|
||||
Fuses Google Mock and Google Test source code into two .h files and a .cc file.
|
||||
|
||||
SYNOPSIS
|
||||
fuse_gmock_files.py [GMOCK_ROOT_DIR] OUTPUT_DIR
|
||||
|
||||
Scans GMOCK_ROOT_DIR for Google Mock and Google Test source
|
||||
code, assuming Google Test is in the GMOCK_ROOT_DIR/../googletest
|
||||
directory, and generates three files:
|
||||
OUTPUT_DIR/gtest/gtest.h, OUTPUT_DIR/gmock/gmock.h, and
|
||||
OUTPUT_DIR/gmock-gtest-all.cc. Then you can build your tests
|
||||
by adding OUTPUT_DIR to the include search path and linking
|
||||
with OUTPUT_DIR/gmock-gtest-all.cc. These three files contain
|
||||
everything you need to use Google Mock. Hence you can
|
||||
"install" Google Mock by copying them to wherever you want.
|
||||
|
||||
GMOCK_ROOT_DIR can be omitted and defaults to the parent
|
||||
directory of the directory holding this script.
|
||||
|
||||
EXAMPLES
|
||||
./fuse_gmock_files.py fused_gmock
|
||||
./fuse_gmock_files.py path/to/unpacked/gmock fused_gmock
|
||||
|
||||
This tool is experimental. In particular, it assumes that there is no
|
||||
conditional inclusion of Google Mock or Google Test headers. Please
|
||||
report any problems to googlemock@googlegroups.com. You can read
|
||||
https://github.com/google/googletest/blob/master/docs/gmock_cook_book.md
|
||||
for more
|
||||
information.
|
||||
"""
|
||||
|
||||
from __future__ import print_function
|
||||
|
||||
import os
|
||||
import re
|
||||
import sys
|
||||
|
||||
__author__ = 'wan@google.com (Zhanyong Wan)'
|
||||
|
||||
# We assume that this file is in the scripts/ directory in the Google
|
||||
# Mock root directory.
|
||||
DEFAULT_GMOCK_ROOT_DIR = os.path.join(os.path.dirname(__file__), '..')
|
||||
|
||||
# We need to call into googletest/scripts/fuse_gtest_files.py.
|
||||
sys.path.append(os.path.join(DEFAULT_GMOCK_ROOT_DIR, '../googletest/scripts'))
|
||||
import fuse_gtest_files as gtest # pylint:disable=g-import-not-at-top
|
||||
|
||||
# Regex for matching
|
||||
# '#include "gmock/..."'.
|
||||
INCLUDE_GMOCK_FILE_REGEX = re.compile(r'^\s*#\s*include\s*"(gmock/.+)"')
|
||||
|
||||
# Where to find the source seed files.
|
||||
GMOCK_H_SEED = 'include/gmock/gmock.h'
|
||||
GMOCK_ALL_CC_SEED = 'src/gmock-all.cc'
|
||||
|
||||
# Where to put the generated files.
|
||||
GTEST_H_OUTPUT = 'gtest/gtest.h'
|
||||
GMOCK_H_OUTPUT = 'gmock/gmock.h'
|
||||
GMOCK_GTEST_ALL_CC_OUTPUT = 'gmock-gtest-all.cc'
|
||||
|
||||
|
||||
def GetGTestRootDir(gmock_root):
|
||||
"""Returns the root directory of Google Test."""
|
||||
|
||||
return os.path.join(gmock_root, '../googletest')
|
||||
|
||||
|
||||
def ValidateGMockRootDir(gmock_root):
|
||||
"""Makes sure gmock_root points to a valid gmock root directory.
|
||||
|
||||
The function aborts the program on failure.
|
||||
|
||||
Args:
|
||||
gmock_root: A string with the mock root directory.
|
||||
"""
|
||||
|
||||
gtest.ValidateGTestRootDir(GetGTestRootDir(gmock_root))
|
||||
gtest.VerifyFileExists(gmock_root, GMOCK_H_SEED)
|
||||
gtest.VerifyFileExists(gmock_root, GMOCK_ALL_CC_SEED)
|
||||
|
||||
|
||||
def ValidateOutputDir(output_dir):
|
||||
"""Makes sure output_dir points to a valid output directory.
|
||||
|
||||
The function aborts the program on failure.
|
||||
|
||||
Args:
|
||||
output_dir: A string representing the output directory.
|
||||
"""
|
||||
|
||||
gtest.VerifyOutputFile(output_dir, gtest.GTEST_H_OUTPUT)
|
||||
gtest.VerifyOutputFile(output_dir, GMOCK_H_OUTPUT)
|
||||
gtest.VerifyOutputFile(output_dir, GMOCK_GTEST_ALL_CC_OUTPUT)
|
||||
|
||||
|
||||
def FuseGMockH(gmock_root, output_dir):
|
||||
"""Scans folder gmock_root to generate gmock/gmock.h in output_dir."""
|
||||
|
||||
output_file = open(os.path.join(output_dir, GMOCK_H_OUTPUT), 'w')
|
||||
processed_files = set() # Holds all gmock headers we've processed.
|
||||
|
||||
def ProcessFile(gmock_header_path):
|
||||
"""Processes the given gmock header file."""
|
||||
|
||||
# We don't process the same header twice.
|
||||
if gmock_header_path in processed_files:
|
||||
return
|
||||
|
||||
processed_files.add(gmock_header_path)
|
||||
|
||||
# Reads each line in the given gmock header.
|
||||
|
||||
with open(os.path.join(gmock_root, gmock_header_path), 'r') as fh:
|
||||
for line in fh:
|
||||
m = INCLUDE_GMOCK_FILE_REGEX.match(line)
|
||||
if m:
|
||||
# '#include "gmock/..."'
|
||||
# - let's process it recursively.
|
||||
ProcessFile('include/' + m.group(1))
|
||||
else:
|
||||
m = gtest.INCLUDE_GTEST_FILE_REGEX.match(line)
|
||||
if m:
|
||||
# '#include "gtest/foo.h"'
|
||||
# We translate it to "gtest/gtest.h", regardless of what foo is,
|
||||
# since all gtest headers are fused into gtest/gtest.h.
|
||||
|
||||
# There is no need to #include gtest.h twice.
|
||||
if gtest.GTEST_H_SEED not in processed_files:
|
||||
processed_files.add(gtest.GTEST_H_SEED)
|
||||
output_file.write('#include "%s"\n' % (gtest.GTEST_H_OUTPUT,))
|
||||
else:
|
||||
# Otherwise we copy the line unchanged to the output file.
|
||||
output_file.write(line)
|
||||
|
||||
ProcessFile(GMOCK_H_SEED)
|
||||
output_file.close()
|
||||
|
||||
|
||||
def FuseGMockAllCcToFile(gmock_root, output_file):
|
||||
"""Scans folder gmock_root to fuse gmock-all.cc into output_file."""
|
||||
|
||||
processed_files = set()
|
||||
|
||||
def ProcessFile(gmock_source_file):
|
||||
"""Processes the given gmock source file."""
|
||||
|
||||
# We don't process the same #included file twice.
|
||||
if gmock_source_file in processed_files:
|
||||
return
|
||||
|
||||
processed_files.add(gmock_source_file)
|
||||
|
||||
# Reads each line in the given gmock source file.
|
||||
|
||||
with open(os.path.join(gmock_root, gmock_source_file), 'r') as fh:
|
||||
for line in fh:
|
||||
m = INCLUDE_GMOCK_FILE_REGEX.match(line)
|
||||
if m:
|
||||
# '#include "gmock/foo.h"'
|
||||
# We treat it as '#include "gmock/gmock.h"', as all other gmock
|
||||
# headers are being fused into gmock.h and cannot be
|
||||
# included directly. No need to
|
||||
# #include "gmock/gmock.h"
|
||||
# more than once.
|
||||
|
||||
if GMOCK_H_SEED not in processed_files:
|
||||
processed_files.add(GMOCK_H_SEED)
|
||||
output_file.write('#include "%s"\n' % (GMOCK_H_OUTPUT,))
|
||||
else:
|
||||
m = gtest.INCLUDE_GTEST_FILE_REGEX.match(line)
|
||||
if m:
|
||||
# '#include "gtest/..."'
|
||||
# There is no need to #include gtest.h as it has been
|
||||
# #included by gtest-all.cc.
|
||||
|
||||
pass
|
||||
else:
|
||||
m = gtest.INCLUDE_SRC_FILE_REGEX.match(line)
|
||||
if m:
|
||||
# It's '#include "src/foo"' - let's process it recursively.
|
||||
ProcessFile(m.group(1))
|
||||
else:
|
||||
# Otherwise we copy the line unchanged to the output file.
|
||||
output_file.write(line)
|
||||
|
||||
ProcessFile(GMOCK_ALL_CC_SEED)
|
||||
|
||||
|
||||
def FuseGMockGTestAllCc(gmock_root, output_dir):
|
||||
"""Scans folder gmock_root to generate gmock-gtest-all.cc in output_dir."""
|
||||
|
||||
with open(os.path.join(output_dir, GMOCK_GTEST_ALL_CC_OUTPUT),
|
||||
'w') as output_file:
|
||||
# First, fuse gtest-all.cc into gmock-gtest-all.cc.
|
||||
gtest.FuseGTestAllCcToFile(GetGTestRootDir(gmock_root), output_file)
|
||||
# Next, append fused gmock-all.cc to gmock-gtest-all.cc.
|
||||
FuseGMockAllCcToFile(gmock_root, output_file)
|
||||
|
||||
|
||||
def FuseGMock(gmock_root, output_dir):
|
||||
"""Fuses gtest.h, gmock.h, and gmock-gtest-all.h."""
|
||||
|
||||
ValidateGMockRootDir(gmock_root)
|
||||
ValidateOutputDir(output_dir)
|
||||
|
||||
gtest.FuseGTestH(GetGTestRootDir(gmock_root), output_dir)
|
||||
FuseGMockH(gmock_root, output_dir)
|
||||
FuseGMockGTestAllCc(gmock_root, output_dir)
|
||||
|
||||
|
||||
def main():
|
||||
argc = len(sys.argv)
|
||||
if argc == 2:
|
||||
# fuse_gmock_files.py OUTPUT_DIR
|
||||
FuseGMock(DEFAULT_GMOCK_ROOT_DIR, sys.argv[1])
|
||||
elif argc == 3:
|
||||
# fuse_gmock_files.py GMOCK_ROOT_DIR OUTPUT_DIR
|
||||
FuseGMock(sys.argv[1], sys.argv[2])
|
||||
else:
|
||||
print(__doc__)
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
@@ -1,203 +0,0 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [2007] Neal Norwitz
|
||||
Portions Copyright [2007] Google Inc.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@@ -1,34 +0,0 @@
|
||||
|
||||
The Google Mock class generator is an application that is part of cppclean.
|
||||
For more information about cppclean, visit http://code.google.com/p/cppclean/
|
||||
|
||||
The mock generator requires Python 2.3.5 or later. If you don't have Python
|
||||
installed on your system, you will also need to install it. You can download
|
||||
Python from: http://www.python.org/download/releases/
|
||||
|
||||
To use the Google Mock class generator, you need to call it
|
||||
on the command line passing the header file and class for which you want
|
||||
to generate a Google Mock class.
|
||||
|
||||
Make sure to install the scripts somewhere in your path. Then you can
|
||||
run the program.
|
||||
|
||||
gmock_gen.py header-file.h [ClassName]...
|
||||
|
||||
If no ClassNames are specified, all classes in the file are emitted.
|
||||
|
||||
To change the indentation from the default of 2, set INDENT in
|
||||
the environment. For example to use an indent of 4 spaces:
|
||||
|
||||
INDENT=4 gmock_gen.py header-file.h ClassName
|
||||
|
||||
This version was made from SVN revision 281 in the cppclean repository.
|
||||
|
||||
Known Limitations
|
||||
-----------------
|
||||
Not all code will be generated properly. For example, when mocking templated
|
||||
classes, the template information is lost. You will need to add the template
|
||||
information manually.
|
||||
|
||||
Not all permutations of using multiple pointers/references will be rendered
|
||||
properly. These will also have to be fixed manually.
|
||||
@@ -1,115 +0,0 @@
|
||||
Goal:
|
||||
-----
|
||||
CppClean attempts to find problems in C++ source that slow development
|
||||
in large code bases, for example various forms of unused code.
|
||||
Unused code can be unused functions, methods, data members, types, etc
|
||||
to unnecessary #include directives. Unnecessary #includes can cause
|
||||
considerable extra compiles increasing the edit-compile-run cycle.
|
||||
|
||||
The project home page is: http://code.google.com/p/cppclean/
|
||||
|
||||
|
||||
Features:
|
||||
---------
|
||||
* Find and print C++ language constructs: classes, methods, functions, etc.
|
||||
* Find classes with virtual methods, no virtual destructor, and no bases
|
||||
* Find global/static data that are potential problems when using threads
|
||||
* Unnecessary forward class declarations
|
||||
* Unnecessary function declarations
|
||||
* Undeclared function definitions
|
||||
* (planned) Find unnecessary header files #included
|
||||
- No direct reference to anything in the header
|
||||
- Header is unnecessary if classes were forward declared instead
|
||||
* (planned) Source files that reference headers not directly #included,
|
||||
ie, files that rely on a transitive #include from another header
|
||||
* (planned) Unused members (private, protected, & public) methods and data
|
||||
* (planned) Store AST in a SQL database so relationships can be queried
|
||||
|
||||
AST is Abstract Syntax Tree, a representation of parsed source code.
|
||||
http://en.wikipedia.org/wiki/Abstract_syntax_tree
|
||||
|
||||
|
||||
System Requirements:
|
||||
--------------------
|
||||
* Python 2.4 or later (2.3 probably works too)
|
||||
* Works on Windows (untested), Mac OS X, and Unix
|
||||
|
||||
|
||||
How to Run:
|
||||
-----------
|
||||
For all examples, it is assumed that cppclean resides in a directory called
|
||||
/cppclean.
|
||||
|
||||
To print warnings for classes with virtual methods, no virtual destructor and
|
||||
no base classes:
|
||||
|
||||
/cppclean/run.sh nonvirtual_dtors.py file1.h file2.h file3.cc ...
|
||||
|
||||
To print all the functions defined in header file(s):
|
||||
|
||||
/cppclean/run.sh functions.py file1.h file2.h ...
|
||||
|
||||
All the commands take multiple files on the command line. Other programs
|
||||
include: find_warnings, headers, methods, and types. Some other programs
|
||||
are available, but used primarily for debugging.
|
||||
|
||||
run.sh is a simple wrapper that sets PYTHONPATH to /cppclean and then
|
||||
runs the program in /cppclean/cpp/PROGRAM.py. There is currently
|
||||
no equivalent for Windows. Contributions for a run.bat file
|
||||
would be greatly appreciated.
|
||||
|
||||
|
||||
How to Configure:
|
||||
-----------------
|
||||
You can add a siteheaders.py file in /cppclean/cpp to configure where
|
||||
to look for other headers (typically -I options passed to a compiler).
|
||||
Currently two values are supported: _TRANSITIVE and GetIncludeDirs.
|
||||
_TRANSITIVE should be set to a boolean value (True or False) indicating
|
||||
whether to transitively process all header files. The default is False.
|
||||
|
||||
GetIncludeDirs is a function that takes a single argument and returns
|
||||
a sequence of directories to include. This can be a generator or
|
||||
return a static list.
|
||||
|
||||
def GetIncludeDirs(filename):
|
||||
return ['/some/path/with/other/headers']
|
||||
|
||||
# Here is a more complicated example.
|
||||
def GetIncludeDirs(filename):
|
||||
yield '/path1'
|
||||
yield os.path.join('/path2', os.path.dirname(filename))
|
||||
yield '/path3'
|
||||
|
||||
|
||||
How to Test:
|
||||
------------
|
||||
For all examples, it is assumed that cppclean resides in a directory called
|
||||
/cppclean. The tests require
|
||||
|
||||
cd /cppclean
|
||||
make test
|
||||
# To generate expected results after a change:
|
||||
make expected
|
||||
|
||||
|
||||
Current Status:
|
||||
---------------
|
||||
The parser works pretty well for header files, parsing about 99% of Google's
|
||||
header files. Anything which inspects structure of C++ source files should
|
||||
work reasonably well. Function bodies are not transformed to an AST,
|
||||
but left as tokens. Much work is still needed on finding unused header files
|
||||
and storing an AST in a database.
|
||||
|
||||
|
||||
Non-goals:
|
||||
----------
|
||||
* Parsing all valid C++ source
|
||||
* Handling invalid C++ source gracefully
|
||||
* Compiling to machine code (or anything beyond an AST)
|
||||
|
||||
|
||||
Contact:
|
||||
--------
|
||||
If you used cppclean, I would love to hear about your experiences
|
||||
cppclean@googlegroups.com. Even if you don't use cppclean, I'd like to
|
||||
hear from you. :-) (You can contact me directly at: nnorwitz@gmail.com)
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,247 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2008 Google Inc. All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""Generate Google Mock classes from base classes.
|
||||
|
||||
This program will read in a C++ source file and output the Google Mock
|
||||
classes for the specified classes. If no class is specified, all
|
||||
classes in the source file are emitted.
|
||||
|
||||
Usage:
|
||||
gmock_class.py header-file.h [ClassName]...
|
||||
|
||||
Output is sent to stdout.
|
||||
"""
|
||||
|
||||
import os
|
||||
import re
|
||||
import sys
|
||||
|
||||
from cpp import ast
|
||||
from cpp import utils
|
||||
|
||||
# Preserve compatibility with Python 2.3.
|
||||
try:
|
||||
_dummy = set
|
||||
except NameError:
|
||||
import sets
|
||||
|
||||
set = sets.Set
|
||||
|
||||
_VERSION = (1, 0, 1) # The version of this script.
|
||||
# How many spaces to indent. Can set me with the INDENT environment variable.
|
||||
_INDENT = 2
|
||||
|
||||
|
||||
def _RenderType(ast_type):
|
||||
"""Renders the potentially recursively templated type into a string.
|
||||
|
||||
Args:
|
||||
ast_type: The AST of the type.
|
||||
|
||||
Returns:
|
||||
Rendered string of the type.
|
||||
"""
|
||||
# Add modifiers like 'const'.
|
||||
modifiers = ''
|
||||
if ast_type.modifiers:
|
||||
modifiers = ' '.join(ast_type.modifiers) + ' '
|
||||
return_type = modifiers + ast_type.name
|
||||
if ast_type.templated_types:
|
||||
# Collect template args.
|
||||
template_args = []
|
||||
for arg in ast_type.templated_types:
|
||||
rendered_arg = _RenderType(arg)
|
||||
template_args.append(rendered_arg)
|
||||
return_type += '<' + ', '.join(template_args) + '>'
|
||||
if ast_type.pointer:
|
||||
return_type += '*'
|
||||
if ast_type.reference:
|
||||
return_type += '&'
|
||||
return return_type
|
||||
|
||||
|
||||
def _GenerateArg(source):
|
||||
"""Strips out comments, default arguments, and redundant spaces from a single argument.
|
||||
|
||||
Args:
|
||||
source: A string for a single argument.
|
||||
|
||||
Returns:
|
||||
Rendered string of the argument.
|
||||
"""
|
||||
# Remove end of line comments before eliminating newlines.
|
||||
arg = re.sub(r'//.*', '', source)
|
||||
|
||||
# Remove c-style comments.
|
||||
arg = re.sub(r'/\*.*\*/', '', arg)
|
||||
|
||||
# Remove default arguments.
|
||||
arg = re.sub(r'=.*', '', arg)
|
||||
|
||||
# Collapse spaces and newlines into a single space.
|
||||
arg = re.sub(r'\s+', ' ', arg)
|
||||
return arg.strip()
|
||||
|
||||
|
||||
def _EscapeForMacro(s):
|
||||
"""Escapes a string for use as an argument to a C++ macro."""
|
||||
paren_count = 0
|
||||
for c in s:
|
||||
if c == '(':
|
||||
paren_count += 1
|
||||
elif c == ')':
|
||||
paren_count -= 1
|
||||
elif c == ',' and paren_count == 0:
|
||||
return '(' + s + ')'
|
||||
return s
|
||||
|
||||
|
||||
def _GenerateMethods(output_lines, source, class_node):
|
||||
function_type = (
|
||||
ast.FUNCTION_VIRTUAL | ast.FUNCTION_PURE_VIRTUAL | ast.FUNCTION_OVERRIDE)
|
||||
ctor_or_dtor = ast.FUNCTION_CTOR | ast.FUNCTION_DTOR
|
||||
indent = ' ' * _INDENT
|
||||
|
||||
for node in class_node.body:
|
||||
# We only care about virtual functions.
|
||||
if (isinstance(node, ast.Function) and node.modifiers & function_type and
|
||||
not node.modifiers & ctor_or_dtor):
|
||||
# Pick out all the elements we need from the original function.
|
||||
modifiers = 'override'
|
||||
if node.modifiers & ast.FUNCTION_CONST:
|
||||
modifiers = 'const, ' + modifiers
|
||||
|
||||
return_type = 'void'
|
||||
if node.return_type:
|
||||
return_type = _EscapeForMacro(_RenderType(node.return_type))
|
||||
|
||||
args = []
|
||||
for p in node.parameters:
|
||||
arg = _GenerateArg(source[p.start:p.end])
|
||||
if arg != 'void':
|
||||
args.append(_EscapeForMacro(arg))
|
||||
|
||||
# Create the mock method definition.
|
||||
output_lines.extend([
|
||||
'%sMOCK_METHOD(%s, %s, (%s), (%s));' %
|
||||
(indent, return_type, node.name, ', '.join(args), modifiers)
|
||||
])
|
||||
|
||||
|
||||
def _GenerateMocks(filename, source, ast_list, desired_class_names):
|
||||
processed_class_names = set()
|
||||
lines = []
|
||||
for node in ast_list:
|
||||
if (isinstance(node, ast.Class) and node.body and
|
||||
# desired_class_names being None means that all classes are selected.
|
||||
(not desired_class_names or node.name in desired_class_names)):
|
||||
class_name = node.name
|
||||
parent_name = class_name
|
||||
processed_class_names.add(class_name)
|
||||
class_node = node
|
||||
# Add namespace before the class.
|
||||
if class_node.namespace:
|
||||
lines.extend(['namespace %s {' % n for n in class_node.namespace]) # }
|
||||
lines.append('')
|
||||
|
||||
# Add template args for templated classes.
|
||||
if class_node.templated_types:
|
||||
# TODO(paulchang): Handle non-type template arguments (e.g.
|
||||
# template<typename T, int N>).
|
||||
|
||||
# class_node.templated_types is an OrderedDict from strings to a tuples.
|
||||
# The key is the name of the template, and the value is
|
||||
# (type_name, default). Both type_name and default could be None.
|
||||
template_args = class_node.templated_types.keys()
|
||||
template_decls = ['typename ' + arg for arg in template_args]
|
||||
lines.append('template <' + ', '.join(template_decls) + '>')
|
||||
parent_name += '<' + ', '.join(template_args) + '>'
|
||||
|
||||
# Add the class prolog.
|
||||
lines.append('class Mock%s : public %s {' # }
|
||||
% (class_name, parent_name))
|
||||
lines.append('%spublic:' % (' ' * (_INDENT // 2)))
|
||||
|
||||
# Add all the methods.
|
||||
_GenerateMethods(lines, source, class_node)
|
||||
|
||||
# Close the class.
|
||||
if lines:
|
||||
# If there are no virtual methods, no need for a public label.
|
||||
if len(lines) == 2:
|
||||
del lines[-1]
|
||||
|
||||
# Only close the class if there really is a class.
|
||||
lines.append('};')
|
||||
lines.append('') # Add an extra newline.
|
||||
|
||||
# Close the namespace.
|
||||
if class_node.namespace:
|
||||
for i in range(len(class_node.namespace) - 1, -1, -1):
|
||||
lines.append('} // namespace %s' % class_node.namespace[i])
|
||||
lines.append('') # Add an extra newline.
|
||||
|
||||
if desired_class_names:
|
||||
missing_class_name_list = list(desired_class_names - processed_class_names)
|
||||
if missing_class_name_list:
|
||||
missing_class_name_list.sort()
|
||||
sys.stderr.write('Class(es) not found in %s: %s\n' %
|
||||
(filename, ', '.join(missing_class_name_list)))
|
||||
elif not processed_class_names:
|
||||
sys.stderr.write('No class found in %s\n' % filename)
|
||||
|
||||
return lines
|
||||
|
||||
|
||||
def main(argv=sys.argv):
|
||||
if len(argv) < 2:
|
||||
sys.stderr.write('Google Mock Class Generator v%s\n\n' %
|
||||
'.'.join(map(str, _VERSION)))
|
||||
sys.stderr.write(__doc__)
|
||||
return 1
|
||||
|
||||
global _INDENT
|
||||
try:
|
||||
_INDENT = int(os.environ['INDENT'])
|
||||
except KeyError:
|
||||
pass
|
||||
except:
|
||||
sys.stderr.write('Unable to use indent of %s\n' % os.environ.get('INDENT'))
|
||||
|
||||
filename = argv[1]
|
||||
desired_class_names = None # None means all classes in the source file.
|
||||
if len(argv) >= 3:
|
||||
desired_class_names = set(argv[2:])
|
||||
source = utils.ReadFile(filename)
|
||||
if source is None:
|
||||
return 1
|
||||
|
||||
builder = ast.BuilderFromSource(source, filename)
|
||||
try:
|
||||
entire_ast = filter(None, builder.Generate())
|
||||
except KeyboardInterrupt:
|
||||
return
|
||||
except:
|
||||
# An error message was already printed since we couldn't parse.
|
||||
sys.exit(1)
|
||||
else:
|
||||
lines = _GenerateMocks(filename, source, entire_ast, desired_class_names)
|
||||
sys.stdout.write('\n'.join(lines))
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main(sys.argv)
|
||||
@@ -1,570 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2009 Neal Norwitz All Rights Reserved.
|
||||
# Portions Copyright 2009 Google Inc. All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""Tests for gmock.scripts.generator.cpp.gmock_class."""
|
||||
|
||||
import os
|
||||
import sys
|
||||
import unittest
|
||||
|
||||
# Allow the cpp imports below to work when run as a standalone script.
|
||||
sys.path.append(os.path.join(os.path.dirname(__file__), '..'))
|
||||
|
||||
from cpp import ast
|
||||
from cpp import gmock_class
|
||||
|
||||
|
||||
class TestCase(unittest.TestCase):
|
||||
"""Helper class that adds assert methods."""
|
||||
|
||||
@staticmethod
|
||||
def StripLeadingWhitespace(lines):
|
||||
"""Strip leading whitespace in each line in 'lines'."""
|
||||
return '\n'.join([s.lstrip() for s in lines.split('\n')])
|
||||
|
||||
def assertEqualIgnoreLeadingWhitespace(self, expected_lines, lines):
|
||||
"""Specialized assert that ignores the indent level."""
|
||||
self.assertEqual(expected_lines, self.StripLeadingWhitespace(lines))
|
||||
|
||||
|
||||
class GenerateMethodsTest(TestCase):
|
||||
|
||||
@staticmethod
|
||||
def GenerateMethodSource(cpp_source):
|
||||
"""Convert C++ source to Google Mock output source lines."""
|
||||
method_source_lines = []
|
||||
# <test> is a pseudo-filename, it is not read or written.
|
||||
builder = ast.BuilderFromSource(cpp_source, '<test>')
|
||||
ast_list = list(builder.Generate())
|
||||
gmock_class._GenerateMethods(method_source_lines, cpp_source, ast_list[0])
|
||||
return '\n'.join(method_source_lines)
|
||||
|
||||
def testSimpleMethod(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual int Bar();
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testSimpleConstructorsAndDestructor(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
Foo();
|
||||
Foo(int x);
|
||||
Foo(const Foo& f);
|
||||
Foo(Foo&& f);
|
||||
~Foo();
|
||||
virtual int Bar() = 0;
|
||||
};
|
||||
"""
|
||||
# The constructors and destructor should be ignored.
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testVirtualDestructor(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual ~Foo();
|
||||
virtual int Bar() = 0;
|
||||
};
|
||||
"""
|
||||
# The destructor should be ignored.
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testExplicitlyDefaultedConstructorsAndDestructor(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
Foo() = default;
|
||||
Foo(const Foo& f) = default;
|
||||
Foo(Foo&& f) = default;
|
||||
~Foo() = default;
|
||||
virtual int Bar() = 0;
|
||||
};
|
||||
"""
|
||||
# The constructors and destructor should be ignored.
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testExplicitlyDeletedConstructorsAndDestructor(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
Foo() = delete;
|
||||
Foo(const Foo& f) = delete;
|
||||
Foo(Foo&& f) = delete;
|
||||
~Foo() = delete;
|
||||
virtual int Bar() = 0;
|
||||
};
|
||||
"""
|
||||
# The constructors and destructor should be ignored.
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testSimpleOverrideMethod(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
int Bar() override;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testSimpleConstMethod(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(bool flag) const;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (bool flag), (const, override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testExplicitVoid(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual int Bar(void);
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testStrangeNewlineInParameter(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(int
|
||||
a) = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (int a), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testDefaultParameters(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(int a, char c = 'x') = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (int a, char c), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testMultipleDefaultParameters(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(
|
||||
int a = 42,
|
||||
char c = 'x',
|
||||
const int* const p = nullptr,
|
||||
const std::string& s = "42",
|
||||
char tab[] = {'4','2'},
|
||||
int const *& rp = aDefaultPointer) = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, '
|
||||
'(int a, char c, const int* const p, const std::string& s, char tab[], int const *& rp), '
|
||||
'(override));', self.GenerateMethodSource(source))
|
||||
|
||||
def testMultipleSingleLineDefaultParameters(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(int a = 42, int b = 43, int c = 44) = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (int a, int b, int c), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testConstDefaultParameter(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
virtual bool Bar(const int test_arg = 42) = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(bool, Bar, (const int test_arg), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testConstRefDefaultParameter(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
virtual bool Bar(const std::string& test_arg = "42" ) = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(bool, Bar, (const std::string& test_arg), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testRemovesCommentsWhenDefaultsArePresent(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(int a = 42 /* a comment */,
|
||||
char /* other comment */ c= 'x') = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (int a, char c), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testDoubleSlashCommentsInParameterListAreRemoved(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual void Bar(int a, // inline comments should be elided.
|
||||
int b // inline comments should be elided.
|
||||
) const = 0;
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(void, Bar, (int a, int b), (const, override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testCStyleCommentsInParameterListAreNotRemoved(self):
|
||||
# NOTE(nnorwitz): I'm not sure if it's the best behavior to keep these
|
||||
# comments. Also note that C style comments after the last parameter
|
||||
# are still elided.
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual const string& Bar(int /* keeper */, int b);
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(const string&, Bar, (int, int b), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testArgsOfTemplateTypes(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual int Bar(const vector<int>& v, map<int, string>* output);
|
||||
};"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (const vector<int>& v, (map<int, string>* output)), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testReturnTypeWithOneTemplateArg(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual vector<int>* Bar(int n);
|
||||
};"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(vector<int>*, Bar, (int n), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testReturnTypeWithManyTemplateArgs(self):
|
||||
source = """
|
||||
class Foo {
|
||||
public:
|
||||
virtual map<int, string> Bar();
|
||||
};"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD((map<int, string>), Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testSimpleMethodInTemplatedClass(self):
|
||||
source = """
|
||||
template<class T>
|
||||
class Foo {
|
||||
public:
|
||||
virtual int Bar();
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testPointerArgWithoutNames(self):
|
||||
source = """
|
||||
class Foo {
|
||||
virtual int Bar(C*);
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (C*), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testReferenceArgWithoutNames(self):
|
||||
source = """
|
||||
class Foo {
|
||||
virtual int Bar(C&);
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (C&), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
def testArrayArgWithoutNames(self):
|
||||
source = """
|
||||
class Foo {
|
||||
virtual int Bar(C[]);
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(
|
||||
'MOCK_METHOD(int, Bar, (C[]), (override));',
|
||||
self.GenerateMethodSource(source))
|
||||
|
||||
|
||||
class GenerateMocksTest(TestCase):
|
||||
|
||||
@staticmethod
|
||||
def GenerateMocks(cpp_source):
|
||||
"""Convert C++ source to complete Google Mock output source."""
|
||||
# <test> is a pseudo-filename, it is not read or written.
|
||||
filename = '<test>'
|
||||
builder = ast.BuilderFromSource(cpp_source, filename)
|
||||
ast_list = list(builder.Generate())
|
||||
lines = gmock_class._GenerateMocks(filename, cpp_source, ast_list, None)
|
||||
return '\n'.join(lines)
|
||||
|
||||
def testNamespaces(self):
|
||||
source = """
|
||||
namespace Foo {
|
||||
namespace Bar { class Forward; }
|
||||
namespace Baz::Qux {
|
||||
|
||||
class Test {
|
||||
public:
|
||||
virtual void Foo();
|
||||
};
|
||||
|
||||
} // namespace Baz::Qux
|
||||
} // namespace Foo
|
||||
"""
|
||||
expected = """\
|
||||
namespace Foo {
|
||||
namespace Baz::Qux {
|
||||
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
|
||||
} // namespace Baz::Qux
|
||||
} // namespace Foo
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testClassWithStorageSpecifierMacro(self):
|
||||
source = """
|
||||
class STORAGE_SPECIFIER Test {
|
||||
public:
|
||||
virtual void Foo();
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testTemplatedForwardDeclaration(self):
|
||||
source = """
|
||||
template <class T> class Forward; // Forward declaration should be ignored.
|
||||
class Test {
|
||||
public:
|
||||
virtual void Foo();
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testTemplatedClass(self):
|
||||
source = """
|
||||
template <typename S, typename T>
|
||||
class Test {
|
||||
public:
|
||||
virtual void Foo();
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
template <typename S, typename T>
|
||||
class MockTest : public Test<S, T> {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testTemplateInATemplateTypedef(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
typedef std::vector<std::list<int>> FooType;
|
||||
virtual void Bar(const FooType& test_arg);
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Bar, (const FooType& test_arg), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testTemplatedClassWithTemplatedArguments(self):
|
||||
source = """
|
||||
template <typename S, typename T, typename U, typename V, typename W>
|
||||
class Test {
|
||||
public:
|
||||
virtual U Foo(T some_arg);
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
template <typename S, typename T, typename U, typename V, typename W>
|
||||
class MockTest : public Test<S, T, U, V, W> {
|
||||
public:
|
||||
MOCK_METHOD(U, Foo, (T some_arg), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testTemplateInATemplateTypedefWithComma(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
typedef std::function<void(
|
||||
const vector<std::list<int>>&, int> FooType;
|
||||
virtual void Bar(const FooType& test_arg);
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Bar, (const FooType& test_arg), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testParenthesizedCommaInArg(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
virtual void Bar(std::function<void(int, int)> f);
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Bar, (std::function<void(int, int)> f), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testEnumType(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
enum Bar {
|
||||
BAZ, QUX, QUUX, QUUUX
|
||||
};
|
||||
virtual void Foo();
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testEnumClassType(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
enum class Bar {
|
||||
BAZ, QUX, QUUX, QUUUX
|
||||
};
|
||||
virtual void Foo();
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(void, Foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
def testStdFunction(self):
|
||||
source = """
|
||||
class Test {
|
||||
public:
|
||||
Test(std::function<int(std::string)> foo) : foo_(foo) {}
|
||||
|
||||
virtual std::function<int(std::string)> foo();
|
||||
|
||||
private:
|
||||
std::function<int(std::string)> foo_;
|
||||
};
|
||||
"""
|
||||
expected = """\
|
||||
class MockTest : public Test {
|
||||
public:
|
||||
MOCK_METHOD(std::function<int (std::string)>, foo, (), (override));
|
||||
};
|
||||
"""
|
||||
self.assertEqualIgnoreLeadingWhitespace(expected,
|
||||
self.GenerateMocks(source))
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
||||
@@ -1,56 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2007 Neal Norwitz
|
||||
# Portions Copyright 2007 Google Inc.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""C++ keywords and helper utilities for determining keywords."""
|
||||
|
||||
try:
|
||||
# Python 3.x
|
||||
import builtins
|
||||
except ImportError:
|
||||
# Python 2.x
|
||||
import __builtin__ as builtins
|
||||
|
||||
|
||||
if not hasattr(builtins, 'set'):
|
||||
# Nominal support for Python 2.3.
|
||||
from sets import Set as set
|
||||
|
||||
|
||||
TYPES = set('bool char int long short double float void wchar_t unsigned signed'.split())
|
||||
TYPE_MODIFIERS = set('auto register const inline extern static virtual volatile mutable'.split())
|
||||
ACCESS = set('public protected private friend'.split())
|
||||
|
||||
CASTS = set('static_cast const_cast dynamic_cast reinterpret_cast'.split())
|
||||
|
||||
OTHERS = set('true false asm class namespace using explicit this operator sizeof'.split())
|
||||
OTHER_TYPES = set('new delete typedef struct union enum typeid typename template'.split())
|
||||
|
||||
CONTROL = set('case switch default if else return goto'.split())
|
||||
EXCEPTION = set('try catch throw'.split())
|
||||
LOOP = set('while do for break continue'.split())
|
||||
|
||||
ALL = TYPES | TYPE_MODIFIERS | ACCESS | CASTS | OTHERS | OTHER_TYPES | CONTROL | EXCEPTION | LOOP
|
||||
|
||||
|
||||
def IsKeyword(token):
|
||||
return token in ALL
|
||||
|
||||
def IsBuiltinType(token):
|
||||
if token in ('virtual', 'inline'):
|
||||
# These only apply to methods, they can't be types by themselves.
|
||||
return False
|
||||
return token in TYPES or token in TYPE_MODIFIERS
|
||||
@@ -1,284 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2007 Neal Norwitz
|
||||
# Portions Copyright 2007 Google Inc.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""Tokenize C++ source code."""
|
||||
|
||||
try:
|
||||
# Python 3.x
|
||||
import builtins
|
||||
except ImportError:
|
||||
# Python 2.x
|
||||
import __builtin__ as builtins
|
||||
|
||||
|
||||
import sys
|
||||
|
||||
from cpp import utils
|
||||
|
||||
|
||||
if not hasattr(builtins, 'set'):
|
||||
# Nominal support for Python 2.3.
|
||||
from sets import Set as set
|
||||
|
||||
|
||||
# Add $ as a valid identifier char since so much code uses it.
|
||||
_letters = 'abcdefghijklmnopqrstuvwxyz'
|
||||
VALID_IDENTIFIER_CHARS = set(_letters + _letters.upper() + '_0123456789$')
|
||||
HEX_DIGITS = set('0123456789abcdefABCDEF')
|
||||
INT_OR_FLOAT_DIGITS = set('01234567890eE-+')
|
||||
|
||||
|
||||
# C++0x string preffixes.
|
||||
_STR_PREFIXES = set(('R', 'u8', 'u8R', 'u', 'uR', 'U', 'UR', 'L', 'LR'))
|
||||
|
||||
|
||||
# Token types.
|
||||
UNKNOWN = 'UNKNOWN'
|
||||
SYNTAX = 'SYNTAX'
|
||||
CONSTANT = 'CONSTANT'
|
||||
NAME = 'NAME'
|
||||
PREPROCESSOR = 'PREPROCESSOR'
|
||||
|
||||
# Where the token originated from. This can be used for backtracking.
|
||||
# It is always set to WHENCE_STREAM in this code.
|
||||
WHENCE_STREAM, WHENCE_QUEUE = range(2)
|
||||
|
||||
|
||||
class Token(object):
|
||||
"""Data container to represent a C++ token.
|
||||
|
||||
Tokens can be identifiers, syntax char(s), constants, or
|
||||
pre-processor directives.
|
||||
|
||||
start contains the index of the first char of the token in the source
|
||||
end contains the index of the last char of the token in the source
|
||||
"""
|
||||
|
||||
def __init__(self, token_type, name, start, end):
|
||||
self.token_type = token_type
|
||||
self.name = name
|
||||
self.start = start
|
||||
self.end = end
|
||||
self.whence = WHENCE_STREAM
|
||||
|
||||
def __str__(self):
|
||||
if not utils.DEBUG:
|
||||
return 'Token(%r)' % self.name
|
||||
return 'Token(%r, %s, %s)' % (self.name, self.start, self.end)
|
||||
|
||||
__repr__ = __str__
|
||||
|
||||
|
||||
def _GetString(source, start, i):
|
||||
i = source.find('"', i+1)
|
||||
while source[i-1] == '\\':
|
||||
# Count the trailing backslashes.
|
||||
backslash_count = 1
|
||||
j = i - 2
|
||||
while source[j] == '\\':
|
||||
backslash_count += 1
|
||||
j -= 1
|
||||
# When trailing backslashes are even, they escape each other.
|
||||
if (backslash_count % 2) == 0:
|
||||
break
|
||||
i = source.find('"', i+1)
|
||||
return i + 1
|
||||
|
||||
|
||||
def _GetChar(source, start, i):
|
||||
# NOTE(nnorwitz): may not be quite correct, should be good enough.
|
||||
i = source.find("'", i+1)
|
||||
while source[i-1] == '\\':
|
||||
# Need to special case '\\'.
|
||||
if (i - 2) > start and source[i-2] == '\\':
|
||||
break
|
||||
i = source.find("'", i+1)
|
||||
# Try to handle unterminated single quotes (in a #if 0 block).
|
||||
if i < 0:
|
||||
i = start
|
||||
return i + 1
|
||||
|
||||
|
||||
def GetTokens(source):
|
||||
"""Returns a sequence of Tokens.
|
||||
|
||||
Args:
|
||||
source: string of C++ source code.
|
||||
|
||||
Yields:
|
||||
Token that represents the next token in the source.
|
||||
"""
|
||||
# Cache various valid character sets for speed.
|
||||
valid_identifier_chars = VALID_IDENTIFIER_CHARS
|
||||
hex_digits = HEX_DIGITS
|
||||
int_or_float_digits = INT_OR_FLOAT_DIGITS
|
||||
int_or_float_digits2 = int_or_float_digits | set('.')
|
||||
|
||||
# Only ignore errors while in a #if 0 block.
|
||||
ignore_errors = False
|
||||
count_ifs = 0
|
||||
|
||||
i = 0
|
||||
end = len(source)
|
||||
while i < end:
|
||||
# Skip whitespace.
|
||||
while i < end and source[i].isspace():
|
||||
i += 1
|
||||
if i >= end:
|
||||
return
|
||||
|
||||
token_type = UNKNOWN
|
||||
start = i
|
||||
c = source[i]
|
||||
if c.isalpha() or c == '_': # Find a string token.
|
||||
token_type = NAME
|
||||
while source[i] in valid_identifier_chars:
|
||||
i += 1
|
||||
# String and character constants can look like a name if
|
||||
# they are something like L"".
|
||||
if (source[i] == "'" and (i - start) == 1 and
|
||||
source[start:i] in 'uUL'):
|
||||
# u, U, and L are valid C++0x character preffixes.
|
||||
token_type = CONSTANT
|
||||
i = _GetChar(source, start, i)
|
||||
elif source[i] == "'" and source[start:i] in _STR_PREFIXES:
|
||||
token_type = CONSTANT
|
||||
i = _GetString(source, start, i)
|
||||
elif c == '/' and source[i+1] == '/': # Find // comments.
|
||||
i = source.find('\n', i)
|
||||
if i == -1: # Handle EOF.
|
||||
i = end
|
||||
continue
|
||||
elif c == '/' and source[i+1] == '*': # Find /* comments. */
|
||||
i = source.find('*/', i) + 2
|
||||
continue
|
||||
elif c in ':+-<>&|*=': # : or :: (plus other chars).
|
||||
token_type = SYNTAX
|
||||
i += 1
|
||||
new_ch = source[i]
|
||||
if new_ch == c and c != '>': # Treat ">>" as two tokens.
|
||||
i += 1
|
||||
elif c == '-' and new_ch == '>':
|
||||
i += 1
|
||||
elif new_ch == '=':
|
||||
i += 1
|
||||
elif c in '()[]{}~!?^%;/.,': # Handle single char tokens.
|
||||
token_type = SYNTAX
|
||||
i += 1
|
||||
if c == '.' and source[i].isdigit():
|
||||
token_type = CONSTANT
|
||||
i += 1
|
||||
while source[i] in int_or_float_digits:
|
||||
i += 1
|
||||
# Handle float suffixes.
|
||||
for suffix in ('l', 'f'):
|
||||
if suffix == source[i:i+1].lower():
|
||||
i += 1
|
||||
break
|
||||
elif c.isdigit(): # Find integer.
|
||||
token_type = CONSTANT
|
||||
if c == '0' and source[i+1] in 'xX':
|
||||
# Handle hex digits.
|
||||
i += 2
|
||||
while source[i] in hex_digits:
|
||||
i += 1
|
||||
else:
|
||||
while source[i] in int_or_float_digits2:
|
||||
i += 1
|
||||
# Handle integer (and float) suffixes.
|
||||
for suffix in ('ull', 'll', 'ul', 'l', 'f', 'u'):
|
||||
size = len(suffix)
|
||||
if suffix == source[i:i+size].lower():
|
||||
i += size
|
||||
break
|
||||
elif c == '"': # Find string.
|
||||
token_type = CONSTANT
|
||||
i = _GetString(source, start, i)
|
||||
elif c == "'": # Find char.
|
||||
token_type = CONSTANT
|
||||
i = _GetChar(source, start, i)
|
||||
elif c == '#': # Find pre-processor command.
|
||||
token_type = PREPROCESSOR
|
||||
got_if = source[i:i+3] == '#if' and source[i+3:i+4].isspace()
|
||||
if got_if:
|
||||
count_ifs += 1
|
||||
elif source[i:i+6] == '#endif':
|
||||
count_ifs -= 1
|
||||
if count_ifs == 0:
|
||||
ignore_errors = False
|
||||
|
||||
# TODO(nnorwitz): handle preprocessor statements (\ continuations).
|
||||
while 1:
|
||||
i1 = source.find('\n', i)
|
||||
i2 = source.find('//', i)
|
||||
i3 = source.find('/*', i)
|
||||
i4 = source.find('"', i)
|
||||
# NOTE(nnorwitz): doesn't handle comments in #define macros.
|
||||
# Get the first important symbol (newline, comment, EOF/end).
|
||||
i = min([x for x in (i1, i2, i3, i4, end) if x != -1])
|
||||
|
||||
# Handle #include "dir//foo.h" properly.
|
||||
if source[i] == '"':
|
||||
i = source.find('"', i+1) + 1
|
||||
assert i > 0
|
||||
continue
|
||||
# Keep going if end of the line and the line ends with \.
|
||||
if not (i == i1 and source[i-1] == '\\'):
|
||||
if got_if:
|
||||
condition = source[start+4:i].lstrip()
|
||||
if (condition.startswith('0') or
|
||||
condition.startswith('(0)')):
|
||||
ignore_errors = True
|
||||
break
|
||||
i += 1
|
||||
elif c == '\\': # Handle \ in code.
|
||||
# This is different from the pre-processor \ handling.
|
||||
i += 1
|
||||
continue
|
||||
elif ignore_errors:
|
||||
# The tokenizer seems to be in pretty good shape. This
|
||||
# raise is conditionally disabled so that bogus code
|
||||
# in an #if 0 block can be handled. Since we will ignore
|
||||
# it anyways, this is probably fine. So disable the
|
||||
# exception and return the bogus char.
|
||||
i += 1
|
||||
else:
|
||||
sys.stderr.write('Got invalid token in %s @ %d token:%s: %r\n' %
|
||||
('?', i, c, source[i-10:i+10]))
|
||||
raise RuntimeError('unexpected token')
|
||||
|
||||
if i <= 0:
|
||||
print('Invalid index, exiting now.')
|
||||
return
|
||||
yield Token(token_type, source[start:i], start, i)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
def main(argv):
|
||||
"""Driver mostly for testing purposes."""
|
||||
for filename in argv[1:]:
|
||||
source = utils.ReadFile(filename)
|
||||
if source is None:
|
||||
continue
|
||||
|
||||
for token in GetTokens(source):
|
||||
print('%-12s: %s' % (token.token_type, token.name))
|
||||
# print('\r%6.2f%%' % (100.0 * index / token.end),)
|
||||
sys.stdout.write('\n')
|
||||
|
||||
|
||||
main(sys.argv)
|
||||
@@ -1,37 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2007 Neal Norwitz
|
||||
# Portions Copyright 2007 Google Inc.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""Generic utilities for C++ parsing."""
|
||||
|
||||
import sys
|
||||
|
||||
# Set to True to see the start/end token indices.
|
||||
DEBUG = True
|
||||
|
||||
|
||||
def ReadFile(filename, print_error=True):
|
||||
"""Returns the contents of a file."""
|
||||
try:
|
||||
fp = open(filename)
|
||||
try:
|
||||
return fp.read()
|
||||
finally:
|
||||
fp.close()
|
||||
except IOError:
|
||||
if print_error:
|
||||
print('Error reading %s: %s' % (filename, sys.exc_info()[1]))
|
||||
return None
|
||||
@@ -1,30 +0,0 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2008 Google Inc. All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
"""Driver for starting up Google Mock class generator."""
|
||||
|
||||
|
||||
import os
|
||||
import sys
|
||||
|
||||
if __name__ == '__main__':
|
||||
# Add the directory of this script to the path so we can import gmock_class.
|
||||
sys.path.append(os.path.dirname(__file__))
|
||||
|
||||
from cpp import gmock_class
|
||||
# Fix the docstring in case they require the usage.
|
||||
gmock_class.__doc__ = gmock_class.__doc__.replace('gmock_class.py', __file__)
|
||||
gmock_class.main()
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements cardinalities.
|
||||
@@ -35,9 +34,11 @@
|
||||
#include "gmock/gmock-cardinalities.h"
|
||||
|
||||
#include <limits.h>
|
||||
|
||||
#include <ostream> // NOLINT
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
|
||||
#include "gmock/internal/gmock-internal-utils.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
@@ -49,21 +50,19 @@ namespace {
|
||||
class BetweenCardinalityImpl : public CardinalityInterface {
|
||||
public:
|
||||
BetweenCardinalityImpl(int min, int max)
|
||||
: min_(min >= 0 ? min : 0),
|
||||
max_(max >= min_ ? max : min_) {
|
||||
: min_(min >= 0 ? min : 0), max_(max >= min_ ? max : min_) {
|
||||
std::stringstream ss;
|
||||
if (min < 0) {
|
||||
ss << "The invocation lower bound must be >= 0, "
|
||||
<< "but is actually " << min << ".";
|
||||
ss << "The invocation lower bound must be >= 0, " << "but is actually "
|
||||
<< min << ".";
|
||||
internal::Expect(false, __FILE__, __LINE__, ss.str());
|
||||
} else if (max < 0) {
|
||||
ss << "The invocation upper bound must be >= 0, "
|
||||
<< "but is actually " << max << ".";
|
||||
ss << "The invocation upper bound must be >= 0, " << "but is actually "
|
||||
<< max << ".";
|
||||
internal::Expect(false, __FILE__, __LINE__, ss.str());
|
||||
} else if (min > max) {
|
||||
ss << "The invocation upper bound (" << max
|
||||
<< ") must be >= the invocation lower bound (" << min
|
||||
<< ").";
|
||||
<< ") must be >= the invocation lower bound (" << min << ").";
|
||||
internal::Expect(false, __FILE__, __LINE__, ss.str());
|
||||
}
|
||||
}
|
||||
@@ -87,7 +86,8 @@ class BetweenCardinalityImpl : public CardinalityInterface {
|
||||
const int min_;
|
||||
const int max_;
|
||||
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(BetweenCardinalityImpl);
|
||||
BetweenCardinalityImpl(const BetweenCardinalityImpl&) = delete;
|
||||
BetweenCardinalityImpl& operator=(const BetweenCardinalityImpl&) = delete;
|
||||
};
|
||||
|
||||
// Formats "n times" in a human-friendly way.
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file defines some utilities useful for implementing Google
|
||||
@@ -37,8 +36,17 @@
|
||||
#include "gmock/internal/gmock-internal-utils.h"
|
||||
|
||||
#include <ctype.h>
|
||||
|
||||
#include <array>
|
||||
#include <cctype>
|
||||
#include <cstdint>
|
||||
#include <cstring>
|
||||
#include <iostream>
|
||||
#include <ostream> // NOLINT
|
||||
#include <string>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
#include "gtest/gtest.h"
|
||||
@@ -48,21 +56,22 @@ namespace internal {
|
||||
|
||||
// Joins a vector of strings as if they are fields of a tuple; returns
|
||||
// the joined string.
|
||||
GTEST_API_ std::string JoinAsTuple(const Strings& fields) {
|
||||
switch (fields.size()) {
|
||||
case 0:
|
||||
return "";
|
||||
case 1:
|
||||
return fields[0];
|
||||
default:
|
||||
std::string result = "(" + fields[0];
|
||||
for (size_t i = 1; i < fields.size(); i++) {
|
||||
result += ", ";
|
||||
result += fields[i];
|
||||
}
|
||||
result += ")";
|
||||
return result;
|
||||
GTEST_API_ std::string JoinAsKeyValueTuple(
|
||||
const std::vector<const char*>& names, const Strings& values) {
|
||||
GTEST_CHECK_(names.size() == values.size());
|
||||
if (values.empty()) {
|
||||
return "";
|
||||
}
|
||||
const auto build_one = [&](const size_t i) {
|
||||
return std::string(names[i]) + ": " + values[i];
|
||||
};
|
||||
std::string result = "(" + build_one(0);
|
||||
for (size_t i = 1; i < values.size(); i++) {
|
||||
result += ", ";
|
||||
result += build_one(i);
|
||||
}
|
||||
result += ")";
|
||||
return result;
|
||||
}
|
||||
|
||||
// Converts an identifier name to a space-separated list of lower-case
|
||||
@@ -76,12 +85,11 @@ GTEST_API_ std::string ConvertIdentifierNameToWords(const char* id_name) {
|
||||
// We don't care about the current locale as the input is
|
||||
// guaranteed to be a valid C++ identifier name.
|
||||
const bool starts_new_word = IsUpper(*p) ||
|
||||
(!IsAlpha(prev_char) && IsLower(*p)) ||
|
||||
(!IsDigit(prev_char) && IsDigit(*p));
|
||||
(!IsAlpha(prev_char) && IsLower(*p)) ||
|
||||
(!IsDigit(prev_char) && IsDigit(*p));
|
||||
|
||||
if (IsAlNum(*p)) {
|
||||
if (starts_new_word && result != "")
|
||||
result += ' ';
|
||||
if (starts_new_word && !result.empty()) result += ' ';
|
||||
result += ToLower(*p);
|
||||
}
|
||||
}
|
||||
@@ -95,12 +103,9 @@ class GoogleTestFailureReporter : public FailureReporterInterface {
|
||||
public:
|
||||
void ReportFailure(FailureType type, const char* file, int line,
|
||||
const std::string& message) override {
|
||||
AssertHelper(type == kFatal ?
|
||||
TestPartResult::kFatalFailure :
|
||||
TestPartResult::kNonFatalFailure,
|
||||
file,
|
||||
line,
|
||||
message.c_str()) = Message();
|
||||
AssertHelper(type == kFatal ? TestPartResult::kFatalFailure
|
||||
: TestPartResult::kNonFatalFailure,
|
||||
file, line, message.c_str()) = Message();
|
||||
if (type == kFatal) {
|
||||
posix::Abort();
|
||||
}
|
||||
@@ -126,10 +131,10 @@ static GTEST_DEFINE_STATIC_MUTEX_(g_log_mutex);
|
||||
// Returns true if and only if a log with the given severity is visible
|
||||
// according to the --gmock_verbose flag.
|
||||
GTEST_API_ bool LogIsVisible(LogSeverity severity) {
|
||||
if (GMOCK_FLAG(verbose) == kInfoVerbosity) {
|
||||
if (GMOCK_FLAG_GET(verbose) == kInfoVerbosity) {
|
||||
// Always show the log if --gmock_verbose=info.
|
||||
return true;
|
||||
} else if (GMOCK_FLAG(verbose) == kErrorVerbosity) {
|
||||
} else if (GMOCK_FLAG_GET(verbose) == kErrorVerbosity) {
|
||||
// Always hide it if --gmock_verbose=error.
|
||||
return false;
|
||||
} else {
|
||||
@@ -148,11 +153,10 @@ GTEST_API_ bool LogIsVisible(LogSeverity severity) {
|
||||
// conservative.
|
||||
GTEST_API_ void Log(LogSeverity severity, const std::string& message,
|
||||
int stack_frames_to_skip) {
|
||||
if (!LogIsVisible(severity))
|
||||
return;
|
||||
if (!LogIsVisible(severity)) return;
|
||||
|
||||
// Ensures that logs from different threads don't interleave.
|
||||
MutexLock l(&g_log_mutex);
|
||||
MutexLock l(g_log_mutex);
|
||||
|
||||
if (severity == kWarning) {
|
||||
// Prints a GMOCK WARNING marker to make the warnings easily searchable.
|
||||
@@ -178,13 +182,13 @@ GTEST_API_ void Log(LogSeverity severity, const std::string& message,
|
||||
std::cout << "\n";
|
||||
}
|
||||
std::cout << "Stack trace:\n"
|
||||
<< ::testing::internal::GetCurrentOsStackTraceExceptTop(
|
||||
::testing::UnitTest::GetInstance(), actual_to_skip);
|
||||
<< ::testing::internal::GetCurrentOsStackTraceExceptTop(
|
||||
actual_to_skip);
|
||||
}
|
||||
std::cout << ::std::flush;
|
||||
}
|
||||
|
||||
GTEST_API_ WithoutMatchers GetWithoutMatchers() { return WithoutMatchers(); }
|
||||
GTEST_API_ WithoutMatchers WithoutMatchers::Get() { return WithoutMatchers(); }
|
||||
|
||||
GTEST_API_ void IllegalDoDefault(const char* file, int line) {
|
||||
internal::Assert(
|
||||
@@ -196,5 +200,59 @@ GTEST_API_ void IllegalDoDefault(const char* file, int line) {
|
||||
"the variable in various places.");
|
||||
}
|
||||
|
||||
constexpr char UndoWebSafeEncoding(char c) {
|
||||
return c == '-' ? '+' : c == '_' ? '/' : c;
|
||||
}
|
||||
|
||||
constexpr char UnBase64Impl(char c, const char* const base64, char carry) {
|
||||
return *base64 == 0 ? static_cast<char>(65)
|
||||
: *base64 == c
|
||||
? carry
|
||||
: UnBase64Impl(c, base64 + 1, static_cast<char>(carry + 1));
|
||||
}
|
||||
|
||||
template <size_t... I>
|
||||
constexpr std::array<char, 256> UnBase64Impl(std::index_sequence<I...>,
|
||||
const char* const base64) {
|
||||
return {
|
||||
{UnBase64Impl(UndoWebSafeEncoding(static_cast<char>(I)), base64, 0)...}};
|
||||
}
|
||||
|
||||
constexpr std::array<char, 256> UnBase64(const char* const base64) {
|
||||
return UnBase64Impl(std::make_index_sequence<256>{}, base64);
|
||||
}
|
||||
|
||||
static constexpr char kBase64[] =
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
||||
static constexpr std::array<char, 256> kUnBase64 = UnBase64(kBase64);
|
||||
|
||||
bool Base64Unescape(const std::string& encoded, std::string* decoded) {
|
||||
decoded->clear();
|
||||
size_t encoded_len = encoded.size();
|
||||
decoded->reserve(3 * (encoded_len / 4) + (encoded_len % 4));
|
||||
int bit_pos = 0;
|
||||
char dst = 0;
|
||||
for (int src : encoded) {
|
||||
if (std::isspace(src) || src == '=') {
|
||||
continue;
|
||||
}
|
||||
char src_bin = kUnBase64[static_cast<size_t>(src)];
|
||||
if (src_bin >= 64) {
|
||||
decoded->clear();
|
||||
return false;
|
||||
}
|
||||
if (bit_pos == 0) {
|
||||
dst |= static_cast<char>(src_bin << 2);
|
||||
bit_pos = 6;
|
||||
} else {
|
||||
dst |= static_cast<char>(src_bin >> (bit_pos - 2));
|
||||
decoded->push_back(dst);
|
||||
dst = static_cast<char>(src_bin << (10 - bit_pos));
|
||||
bit_pos = (bit_pos + 6) % 8;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
} // namespace testing
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements Matcher<const string&>, Matcher<string>, and
|
||||
@@ -36,9 +35,11 @@
|
||||
#include "gmock/gmock-matchers.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include <iostream>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace testing {
|
||||
namespace internal {
|
||||
@@ -48,11 +49,13 @@ namespace internal {
|
||||
// 'negation' is false; otherwise returns the description of the
|
||||
// negation of the matcher. 'param_values' contains a list of strings
|
||||
// that are the print-out of the matcher's parameters.
|
||||
GTEST_API_ std::string FormatMatcherDescription(bool negation,
|
||||
const char* matcher_name,
|
||||
const Strings& param_values) {
|
||||
GTEST_API_ std::string FormatMatcherDescription(
|
||||
bool negation, const char* matcher_name,
|
||||
const std::vector<const char*>& param_names, const Strings& param_values) {
|
||||
std::string result = ConvertIdentifierNameToWords(matcher_name);
|
||||
if (param_values.size() >= 1) result += " " + JoinAsTuple(param_values);
|
||||
if (!param_values.empty()) {
|
||||
result += " " + JoinAsKeyValueTuple(param_names, param_values);
|
||||
}
|
||||
return negation ? "not (" + result + ")" : result;
|
||||
}
|
||||
|
||||
@@ -117,7 +120,7 @@ GTEST_API_ std::string FormatMatcherDescription(bool negation,
|
||||
// [1] Cormen, et al (2001). "Section 26.2: The Ford-Fulkerson method".
|
||||
// "Introduction to Algorithms (Second ed.)", pp. 651-664.
|
||||
// [2] "Ford-Fulkerson algorithm", Wikipedia,
|
||||
// 'http://en.wikipedia.org/wiki/Ford%E2%80%93Fulkerson_algorithm'
|
||||
// 'https://en.wikipedia.org/wiki/Ford%E2%80%93Fulkerson_algorithm'
|
||||
class MaxBipartiteMatchState {
|
||||
public:
|
||||
explicit MaxBipartiteMatchState(const MatchMatrix& graph)
|
||||
@@ -233,9 +236,8 @@ static void LogElementMatcherPairVec(const ElementMatcherPairs& pairs,
|
||||
os << "{";
|
||||
const char* sep = "";
|
||||
for (Iter it = pairs.begin(); it != pairs.end(); ++it) {
|
||||
os << sep << "\n ("
|
||||
<< "element #" << it->first << ", "
|
||||
<< "matcher #" << it->second << ")";
|
||||
os << sep << "\n (" << "element #" << it->first << ", " << "matcher #"
|
||||
<< it->second << ")";
|
||||
sep = ",";
|
||||
}
|
||||
os << "\n}";
|
||||
@@ -367,7 +369,24 @@ void UnorderedElementsAreMatcherImplBase::DescribeNegationToImpl(
|
||||
bool UnorderedElementsAreMatcherImplBase::VerifyMatchMatrix(
|
||||
const ::std::vector<std::string>& element_printouts,
|
||||
const MatchMatrix& matrix, MatchResultListener* listener) const {
|
||||
bool result = true;
|
||||
if (matrix.LhsSize() == 0 && matrix.RhsSize() == 0) {
|
||||
return true;
|
||||
}
|
||||
|
||||
const bool is_exact_match_with_size_discrepency =
|
||||
match_flags() == UnorderedMatcherRequire::ExactMatch &&
|
||||
matrix.LhsSize() != matrix.RhsSize();
|
||||
if (is_exact_match_with_size_discrepency) {
|
||||
// The element count doesn't match. If the container is empty,
|
||||
// there's no need to explain anything as Google Mock already
|
||||
// prints the empty container. Otherwise we just need to show
|
||||
// how many elements there actually are.
|
||||
if (matrix.LhsSize() != 0 && listener->IsInterested()) {
|
||||
*listener << "which has " << Elements(matrix.LhsSize()) << "\n";
|
||||
}
|
||||
}
|
||||
|
||||
bool result = !is_exact_match_with_size_discrepency;
|
||||
::std::vector<char> element_matched(matrix.LhsSize(), 0);
|
||||
::std::vector<char> matcher_matched(matrix.RhsSize(), 0);
|
||||
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file implements the spec builder syntax (ON_CALL and
|
||||
@@ -41,24 +40,26 @@
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <set>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
|
||||
#if GTEST_OS_CYGWIN || GTEST_OS_LINUX || GTEST_OS_MAC
|
||||
# include <unistd.h> // NOLINT
|
||||
#if defined(GTEST_OS_CYGWIN) || defined(GTEST_OS_LINUX) || defined(GTEST_OS_MAC)
|
||||
#include <unistd.h> // NOLINT
|
||||
#endif
|
||||
#ifdef GTEST_OS_QURT
|
||||
#include <qurt_event.h>
|
||||
#endif
|
||||
|
||||
// Silence C4800 (C4800: 'int *const ': forcing value
|
||||
// to bool 'true' or 'false') for MSVC 15
|
||||
#ifdef _MSC_VER
|
||||
#if _MSC_VER == 1900
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4800)
|
||||
#endif
|
||||
#if defined(_MSC_VER) && (_MSC_VER == 1900)
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4800)
|
||||
#endif
|
||||
|
||||
namespace testing {
|
||||
@@ -95,7 +96,7 @@ ExpectationBase::ExpectationBase(const char* a_file, int a_line,
|
||||
action_count_checked_(false) {}
|
||||
|
||||
// Destructs an ExpectationBase object.
|
||||
ExpectationBase::~ExpectationBase() {}
|
||||
ExpectationBase::~ExpectationBase() = default;
|
||||
|
||||
// Explicitly specifies the cardinality of this expectation. Used by
|
||||
// the subclasses to implement the .Times() clause.
|
||||
@@ -195,11 +196,12 @@ void ExpectationBase::DescribeCallCountTo(::std::ostream* os) const
|
||||
|
||||
// Describes the state of the expectation (e.g. is it satisfied?
|
||||
// is it active?).
|
||||
*os << " - " << (IsOverSaturated() ? "over-saturated" :
|
||||
IsSaturated() ? "saturated" :
|
||||
IsSatisfied() ? "satisfied" : "unsatisfied")
|
||||
<< " and "
|
||||
<< (is_retired() ? "retired" : "active");
|
||||
*os << " - "
|
||||
<< (IsOverSaturated() ? "over-saturated"
|
||||
: IsSaturated() ? "saturated"
|
||||
: IsSatisfied() ? "satisfied"
|
||||
: "unsatisfied")
|
||||
<< " and " << (is_retired() ? "retired" : "active");
|
||||
}
|
||||
|
||||
// Checks the action count (i.e. the number of WillOnce() and
|
||||
@@ -210,7 +212,7 @@ void ExpectationBase::CheckActionCountIfNotDone() const
|
||||
GTEST_LOCK_EXCLUDED_(mutex_) {
|
||||
bool should_check = false;
|
||||
{
|
||||
MutexLock l(&mutex_);
|
||||
MutexLock l(mutex_);
|
||||
if (!action_count_checked_) {
|
||||
action_count_checked_ = true;
|
||||
should_check = true;
|
||||
@@ -242,13 +244,12 @@ void ExpectationBase::CheckActionCountIfNotDone() const
|
||||
|
||||
::std::stringstream ss;
|
||||
DescribeLocationTo(&ss);
|
||||
ss << "Too " << (too_many ? "many" : "few")
|
||||
<< " actions specified in " << source_text() << "...\n"
|
||||
ss << "Too " << (too_many ? "many" : "few") << " actions specified in "
|
||||
<< source_text() << "...\n"
|
||||
<< "Expected to be ";
|
||||
cardinality().DescribeTo(&ss);
|
||||
ss << ", but has " << (too_many ? "" : "only ")
|
||||
<< action_count << " WillOnce()"
|
||||
<< (action_count == 1 ? "" : "s");
|
||||
ss << ", but has " << (too_many ? "" : "only ") << action_count
|
||||
<< " WillOnce()" << (action_count == 1 ? "" : "s");
|
||||
if (repeated_action_specified_) {
|
||||
ss << " and a WillRepeatedly()";
|
||||
}
|
||||
@@ -264,10 +265,10 @@ void ExpectationBase::UntypedTimes(const Cardinality& a_cardinality) {
|
||||
".Times() cannot appear "
|
||||
"more than once in an EXPECT_CALL().");
|
||||
} else {
|
||||
ExpectSpecProperty(last_clause_ < kTimes,
|
||||
".Times() cannot appear after "
|
||||
".InSequence(), .WillOnce(), .WillRepeatedly(), "
|
||||
"or .RetiresOnSaturation().");
|
||||
ExpectSpecProperty(
|
||||
last_clause_ < kTimes,
|
||||
".Times() may only appear *before* .InSequence(), .WillOnce(), "
|
||||
".WillRepeatedly(), or .RetiresOnSaturation(), not after.");
|
||||
}
|
||||
last_clause_ = kTimes;
|
||||
|
||||
@@ -283,7 +284,7 @@ GTEST_API_ ThreadLocal<Sequence*> g_gmock_implicit_sequence;
|
||||
void ReportUninterestingCall(CallReaction reaction, const std::string& msg) {
|
||||
// Include a stack trace only if --gmock_verbose=info is specified.
|
||||
const int stack_frames_to_skip =
|
||||
GMOCK_FLAG(verbose) == kInfoVerbosity ? 3 : -1;
|
||||
GMOCK_FLAG_GET(verbose) == kInfoVerbosity ? 3 : -1;
|
||||
switch (reaction) {
|
||||
case kAllow:
|
||||
Log(kInfo, msg, stack_frames_to_skip);
|
||||
@@ -292,12 +293,12 @@ void ReportUninterestingCall(CallReaction reaction, const std::string& msg) {
|
||||
Log(kWarning,
|
||||
msg +
|
||||
"\nNOTE: You can safely ignore the above warning unless this "
|
||||
"call should not happen. Do not suppress it by blindly adding "
|
||||
"call should not happen. Do not suppress it by adding "
|
||||
"an EXPECT_CALL() if you don't mean to enforce the call. "
|
||||
"See "
|
||||
"https://github.com/google/googletest/blob/master/docs/"
|
||||
"https://github.com/google/googletest/blob/main/docs/"
|
||||
"gmock_cook_book.md#"
|
||||
"knowing-when-to-expect for details.\n",
|
||||
"knowing-when-to-expect-useoncall for details.\n",
|
||||
stack_frames_to_skip);
|
||||
break;
|
||||
default: // FAIL
|
||||
@@ -308,7 +309,7 @@ void ReportUninterestingCall(CallReaction reaction, const std::string& msg) {
|
||||
UntypedFunctionMockerBase::UntypedFunctionMockerBase()
|
||||
: mock_obj_(nullptr), name_("") {}
|
||||
|
||||
UntypedFunctionMockerBase::~UntypedFunctionMockerBase() {}
|
||||
UntypedFunctionMockerBase::~UntypedFunctionMockerBase() = default;
|
||||
|
||||
// Sets the mock object this mock method belongs to, and registers
|
||||
// this information in the global mock registry. Will be called
|
||||
@@ -317,7 +318,7 @@ UntypedFunctionMockerBase::~UntypedFunctionMockerBase() {}
|
||||
void UntypedFunctionMockerBase::RegisterOwner(const void* mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(g_gmock_mutex) {
|
||||
{
|
||||
MutexLock l(&g_gmock_mutex);
|
||||
MutexLock l(g_gmock_mutex);
|
||||
mock_obj_ = mock_obj;
|
||||
}
|
||||
Mock::Register(mock_obj, this);
|
||||
@@ -331,7 +332,7 @@ void UntypedFunctionMockerBase::SetOwnerAndName(const void* mock_obj,
|
||||
GTEST_LOCK_EXCLUDED_(g_gmock_mutex) {
|
||||
// We protect name_ under g_gmock_mutex in case this mock function
|
||||
// is called from two threads concurrently.
|
||||
MutexLock l(&g_gmock_mutex);
|
||||
MutexLock l(g_gmock_mutex);
|
||||
mock_obj_ = mock_obj;
|
||||
name_ = name;
|
||||
}
|
||||
@@ -344,7 +345,7 @@ const void* UntypedFunctionMockerBase::MockObject() const
|
||||
{
|
||||
// We protect mock_obj_ under g_gmock_mutex in case this mock
|
||||
// function is called from two threads concurrently.
|
||||
MutexLock l(&g_gmock_mutex);
|
||||
MutexLock l(g_gmock_mutex);
|
||||
Assert(mock_obj_ != nullptr, __FILE__, __LINE__,
|
||||
"MockObject() must not be called before RegisterOwner() or "
|
||||
"SetOwnerAndName() has been called.");
|
||||
@@ -361,7 +362,7 @@ const char* UntypedFunctionMockerBase::Name() const
|
||||
{
|
||||
// We protect name_ under g_gmock_mutex in case this mock
|
||||
// function is called from two threads concurrently.
|
||||
MutexLock l(&g_gmock_mutex);
|
||||
MutexLock l(g_gmock_mutex);
|
||||
Assert(name_ != nullptr, __FILE__, __LINE__,
|
||||
"Name() must not be called before SetOwnerAndName() has "
|
||||
"been called.");
|
||||
@@ -370,143 +371,12 @@ const char* UntypedFunctionMockerBase::Name() const
|
||||
return name;
|
||||
}
|
||||
|
||||
// Calculates the result of invoking this mock function with the given
|
||||
// arguments, prints it, and returns it. The caller is responsible
|
||||
// for deleting the result.
|
||||
UntypedActionResultHolderBase* UntypedFunctionMockerBase::UntypedInvokeWith(
|
||||
void* const untyped_args) GTEST_LOCK_EXCLUDED_(g_gmock_mutex) {
|
||||
// See the definition of untyped_expectations_ for why access to it
|
||||
// is unprotected here.
|
||||
if (untyped_expectations_.size() == 0) {
|
||||
// No expectation is set on this mock method - we have an
|
||||
// uninteresting call.
|
||||
|
||||
// We must get Google Mock's reaction on uninteresting calls
|
||||
// made on this mock object BEFORE performing the action,
|
||||
// because the action may DELETE the mock object and make the
|
||||
// following expression meaningless.
|
||||
const CallReaction reaction =
|
||||
Mock::GetReactionOnUninterestingCalls(MockObject());
|
||||
|
||||
// True if and only if we need to print this call's arguments and return
|
||||
// value. This definition must be kept in sync with
|
||||
// the behavior of ReportUninterestingCall().
|
||||
const bool need_to_report_uninteresting_call =
|
||||
// If the user allows this uninteresting call, we print it
|
||||
// only when they want informational messages.
|
||||
reaction == kAllow ? LogIsVisible(kInfo) :
|
||||
// If the user wants this to be a warning, we print
|
||||
// it only when they want to see warnings.
|
||||
reaction == kWarn
|
||||
? LogIsVisible(kWarning)
|
||||
:
|
||||
// Otherwise, the user wants this to be an error, and we
|
||||
// should always print detailed information in the error.
|
||||
true;
|
||||
|
||||
if (!need_to_report_uninteresting_call) {
|
||||
// Perform the action without printing the call information.
|
||||
return this->UntypedPerformDefaultAction(
|
||||
untyped_args, "Function call: " + std::string(Name()));
|
||||
}
|
||||
|
||||
// Warns about the uninteresting call.
|
||||
::std::stringstream ss;
|
||||
this->UntypedDescribeUninterestingCall(untyped_args, &ss);
|
||||
|
||||
// Calculates the function result.
|
||||
UntypedActionResultHolderBase* const result =
|
||||
this->UntypedPerformDefaultAction(untyped_args, ss.str());
|
||||
|
||||
// Prints the function result.
|
||||
if (result != nullptr) result->PrintAsActionResult(&ss);
|
||||
|
||||
ReportUninterestingCall(reaction, ss.str());
|
||||
return result;
|
||||
}
|
||||
|
||||
bool is_excessive = false;
|
||||
::std::stringstream ss;
|
||||
::std::stringstream why;
|
||||
::std::stringstream loc;
|
||||
const void* untyped_action = nullptr;
|
||||
|
||||
// The UntypedFindMatchingExpectation() function acquires and
|
||||
// releases g_gmock_mutex.
|
||||
|
||||
const ExpectationBase* const untyped_expectation =
|
||||
this->UntypedFindMatchingExpectation(untyped_args, &untyped_action,
|
||||
&is_excessive, &ss, &why);
|
||||
const bool found = untyped_expectation != nullptr;
|
||||
|
||||
// True if and only if we need to print the call's arguments
|
||||
// and return value.
|
||||
// This definition must be kept in sync with the uses of Expect()
|
||||
// and Log() in this function.
|
||||
const bool need_to_report_call =
|
||||
!found || is_excessive || LogIsVisible(kInfo);
|
||||
if (!need_to_report_call) {
|
||||
// Perform the action without printing the call information.
|
||||
return untyped_action == nullptr
|
||||
? this->UntypedPerformDefaultAction(untyped_args, "")
|
||||
: this->UntypedPerformAction(untyped_action, untyped_args);
|
||||
}
|
||||
|
||||
ss << " Function call: " << Name();
|
||||
this->UntypedPrintArgs(untyped_args, &ss);
|
||||
|
||||
// In case the action deletes a piece of the expectation, we
|
||||
// generate the message beforehand.
|
||||
if (found && !is_excessive) {
|
||||
untyped_expectation->DescribeLocationTo(&loc);
|
||||
}
|
||||
|
||||
UntypedActionResultHolderBase* result = nullptr;
|
||||
|
||||
auto perform_action = [&] {
|
||||
return untyped_action == nullptr
|
||||
? this->UntypedPerformDefaultAction(untyped_args, ss.str())
|
||||
: this->UntypedPerformAction(untyped_action, untyped_args);
|
||||
};
|
||||
auto handle_failures = [&] {
|
||||
ss << "\n" << why.str();
|
||||
|
||||
if (!found) {
|
||||
// No expectation matches this call - reports a failure.
|
||||
Expect(false, nullptr, -1, ss.str());
|
||||
} else if (is_excessive) {
|
||||
// We had an upper-bound violation and the failure message is in ss.
|
||||
Expect(false, untyped_expectation->file(), untyped_expectation->line(),
|
||||
ss.str());
|
||||
} else {
|
||||
// We had an expected call and the matching expectation is
|
||||
// described in ss.
|
||||
Log(kInfo, loc.str() + ss.str(), 2);
|
||||
}
|
||||
};
|
||||
#if GTEST_HAS_EXCEPTIONS
|
||||
try {
|
||||
result = perform_action();
|
||||
} catch (...) {
|
||||
handle_failures();
|
||||
throw;
|
||||
}
|
||||
#else
|
||||
result = perform_action();
|
||||
#endif
|
||||
|
||||
if (result != nullptr) result->PrintAsActionResult(&ss);
|
||||
handle_failures();
|
||||
return result;
|
||||
}
|
||||
|
||||
// Returns an Expectation object that references and co-owns exp,
|
||||
// which must be an expectation on this mock function.
|
||||
Expectation UntypedFunctionMockerBase::GetHandleOf(ExpectationBase* exp) {
|
||||
// See the definition of untyped_expectations_ for why access to it
|
||||
// is unprotected here.
|
||||
for (UntypedExpectations::const_iterator it =
|
||||
untyped_expectations_.begin();
|
||||
for (UntypedExpectations::const_iterator it = untyped_expectations_.begin();
|
||||
it != untyped_expectations_.end(); ++it) {
|
||||
if (it->get() == exp) {
|
||||
return Expectation(*it);
|
||||
@@ -526,8 +396,7 @@ bool UntypedFunctionMockerBase::VerifyAndClearExpectationsLocked()
|
||||
GTEST_EXCLUSIVE_LOCK_REQUIRED_(g_gmock_mutex) {
|
||||
g_gmock_mutex.AssertHeld();
|
||||
bool expectations_met = true;
|
||||
for (UntypedExpectations::const_iterator it =
|
||||
untyped_expectations_.begin();
|
||||
for (UntypedExpectations::const_iterator it = untyped_expectations_.begin();
|
||||
it != untyped_expectations_.end(); ++it) {
|
||||
ExpectationBase* const untyped_expectation = it->get();
|
||||
if (untyped_expectation->IsOverSaturated()) {
|
||||
@@ -538,15 +407,22 @@ bool UntypedFunctionMockerBase::VerifyAndClearExpectationsLocked()
|
||||
} else if (!untyped_expectation->IsSatisfied()) {
|
||||
expectations_met = false;
|
||||
::std::stringstream ss;
|
||||
ss << "Actual function call count doesn't match "
|
||||
<< untyped_expectation->source_text() << "...\n";
|
||||
|
||||
const ::std::string& expectation_name =
|
||||
untyped_expectation->GetDescription();
|
||||
ss << "Actual function ";
|
||||
if (!expectation_name.empty()) {
|
||||
ss << "\"" << expectation_name << "\" ";
|
||||
}
|
||||
ss << "call count doesn't match " << untyped_expectation->source_text()
|
||||
<< "...\n";
|
||||
// No need to show the source file location of the expectation
|
||||
// in the description, as the Expect() call that follows already
|
||||
// takes care of it.
|
||||
untyped_expectation->MaybeDescribeExtraMatcherTo(&ss);
|
||||
untyped_expectation->DescribeCallCountTo(&ss);
|
||||
Expect(false, untyped_expectation->file(),
|
||||
untyped_expectation->line(), ss.str());
|
||||
Expect(false, untyped_expectation->file(), untyped_expectation->line(),
|
||||
ss.str());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -560,14 +436,14 @@ bool UntypedFunctionMockerBase::VerifyAndClearExpectationsLocked()
|
||||
UntypedExpectations expectations_to_delete;
|
||||
untyped_expectations_.swap(expectations_to_delete);
|
||||
|
||||
g_gmock_mutex.Unlock();
|
||||
g_gmock_mutex.unlock();
|
||||
expectations_to_delete.clear();
|
||||
g_gmock_mutex.Lock();
|
||||
g_gmock_mutex.lock();
|
||||
|
||||
return expectations_met;
|
||||
}
|
||||
|
||||
CallReaction intToCallReaction(int mock_behavior) {
|
||||
static CallReaction intToCallReaction(int mock_behavior) {
|
||||
if (mock_behavior >= kAllow && mock_behavior <= kFail) {
|
||||
return static_cast<internal::CallReaction>(mock_behavior);
|
||||
}
|
||||
@@ -613,8 +489,8 @@ class MockObjectRegistry {
|
||||
// object alive. Therefore we report any living object as test
|
||||
// failure, unless the user explicitly asked us to ignore it.
|
||||
~MockObjectRegistry() {
|
||||
if (!GMOCK_FLAG(catch_leaked_mocks))
|
||||
return;
|
||||
if (!GMOCK_FLAG_GET(catch_leaked_mocks)) return;
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
|
||||
int leaked_count = 0;
|
||||
for (StateMap::const_iterator it = states_.begin(); it != states_.end();
|
||||
@@ -629,12 +505,12 @@ class MockObjectRegistry {
|
||||
std::cout << internal::FormatFileLocation(state.first_used_file,
|
||||
state.first_used_line);
|
||||
std::cout << " ERROR: this mock object";
|
||||
if (state.first_used_test != "") {
|
||||
if (!state.first_used_test.empty()) {
|
||||
std::cout << " (used in test " << state.first_used_test_suite << "."
|
||||
<< state.first_used_test << ")";
|
||||
}
|
||||
std::cout << " should be deleted but never is. Its address is @"
|
||||
<< it->first << ".";
|
||||
<< it->first << ".";
|
||||
leaked_count++;
|
||||
}
|
||||
if (leaked_count > 0) {
|
||||
@@ -652,8 +528,12 @@ class MockObjectRegistry {
|
||||
// RUN_ALL_TESTS() has already returned when this destructor is
|
||||
// called. Therefore we cannot use the normal Google Test
|
||||
// failure reporting mechanism.
|
||||
_exit(1); // We cannot call exit() as it is not reentrant and
|
||||
#ifdef GTEST_OS_QURT
|
||||
qurt_exception_raise_fatal();
|
||||
#else
|
||||
_Exit(1); // We cannot call exit() as it is not reentrant and
|
||||
// may already have been called.
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
@@ -668,64 +548,70 @@ MockObjectRegistry g_mock_object_registry;
|
||||
|
||||
// Maps a mock object to the reaction Google Mock should have when an
|
||||
// uninteresting method is called. Protected by g_gmock_mutex.
|
||||
std::map<const void*, internal::CallReaction> g_uninteresting_call_reaction;
|
||||
std::unordered_map<uintptr_t, internal::CallReaction>&
|
||||
UninterestingCallReactionMap() {
|
||||
static auto* map = new std::unordered_map<uintptr_t, internal::CallReaction>;
|
||||
return *map;
|
||||
}
|
||||
|
||||
// Sets the reaction Google Mock should have when an uninteresting
|
||||
// method of the given mock object is called.
|
||||
void SetReactionOnUninterestingCalls(const void* mock_obj,
|
||||
void SetReactionOnUninterestingCalls(uintptr_t mock_obj,
|
||||
internal::CallReaction reaction)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
g_uninteresting_call_reaction[mock_obj] = reaction;
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
UninterestingCallReactionMap()[mock_obj] = reaction;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
// Tells Google Mock to allow uninteresting calls on the given mock
|
||||
// object.
|
||||
void Mock::AllowUninterestingCalls(const void* mock_obj)
|
||||
void Mock::AllowUninterestingCalls(uintptr_t mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
SetReactionOnUninterestingCalls(mock_obj, internal::kAllow);
|
||||
}
|
||||
|
||||
// Tells Google Mock to warn the user about uninteresting calls on the
|
||||
// given mock object.
|
||||
void Mock::WarnUninterestingCalls(const void* mock_obj)
|
||||
void Mock::WarnUninterestingCalls(uintptr_t mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
SetReactionOnUninterestingCalls(mock_obj, internal::kWarn);
|
||||
}
|
||||
|
||||
// Tells Google Mock to fail uninteresting calls on the given mock
|
||||
// object.
|
||||
void Mock::FailUninterestingCalls(const void* mock_obj)
|
||||
void Mock::FailUninterestingCalls(uintptr_t mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
SetReactionOnUninterestingCalls(mock_obj, internal::kFail);
|
||||
}
|
||||
|
||||
// Tells Google Mock the given mock object is being destroyed and its
|
||||
// entry in the call-reaction table should be removed.
|
||||
void Mock::UnregisterCallReaction(const void* mock_obj)
|
||||
void Mock::UnregisterCallReaction(uintptr_t mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
g_uninteresting_call_reaction.erase(mock_obj);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
UninterestingCallReactionMap().erase(static_cast<uintptr_t>(mock_obj));
|
||||
}
|
||||
|
||||
// Returns the reaction Google Mock will have on uninteresting calls
|
||||
// made on the given mock object.
|
||||
internal::CallReaction Mock::GetReactionOnUninterestingCalls(
|
||||
const void* mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
return (g_uninteresting_call_reaction.count(mock_obj) == 0) ?
|
||||
internal::intToCallReaction(GMOCK_FLAG(default_mock_behavior)) :
|
||||
g_uninteresting_call_reaction[mock_obj];
|
||||
const void* mock_obj) GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
return (UninterestingCallReactionMap().count(
|
||||
reinterpret_cast<uintptr_t>(mock_obj)) == 0)
|
||||
? internal::intToCallReaction(
|
||||
GMOCK_FLAG_GET(default_mock_behavior))
|
||||
: UninterestingCallReactionMap()[reinterpret_cast<uintptr_t>(
|
||||
mock_obj)];
|
||||
}
|
||||
|
||||
// Tells Google Mock to ignore mock_obj when checking for leaked mock
|
||||
// objects.
|
||||
void Mock::AllowLeak(const void* mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
g_mock_object_registry.states()[mock_obj].leakable = true;
|
||||
}
|
||||
|
||||
@@ -734,7 +620,7 @@ void Mock::AllowLeak(const void* mock_obj)
|
||||
// Test non-fatal failures and returns false.
|
||||
bool Mock::VerifyAndClearExpectations(void* mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
return VerifyAndClearExpectationsLocked(mock_obj);
|
||||
}
|
||||
|
||||
@@ -743,7 +629,7 @@ bool Mock::VerifyAndClearExpectations(void* mock_obj)
|
||||
// verification was successful.
|
||||
bool Mock::VerifyAndClear(void* mock_obj)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
ClearDefaultActionsLocked(mock_obj);
|
||||
return VerifyAndClearExpectationsLocked(mock_obj);
|
||||
}
|
||||
@@ -793,7 +679,7 @@ bool Mock::IsStrict(void* mock_obj)
|
||||
void Mock::Register(const void* mock_obj,
|
||||
internal::UntypedFunctionMockerBase* mocker)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
g_mock_object_registry.states()[mock_obj].function_mockers.insert(mocker);
|
||||
}
|
||||
|
||||
@@ -803,7 +689,7 @@ void Mock::Register(const void* mock_obj,
|
||||
void Mock::RegisterUseByOnCallOrExpectCall(const void* mock_obj,
|
||||
const char* file, int line)
|
||||
GTEST_LOCK_EXCLUDED_(internal::g_gmock_mutex) {
|
||||
internal::MutexLock l(&internal::g_gmock_mutex);
|
||||
internal::MutexLock l(internal::g_gmock_mutex);
|
||||
MockObjectState& state = g_mock_object_registry.states()[mock_obj];
|
||||
if (state.first_used_file == nullptr) {
|
||||
state.first_used_file = file;
|
||||
@@ -861,20 +747,20 @@ void Mock::ClearDefaultActionsLocked(void* mock_obj)
|
||||
// needed by VerifyAndClearExpectationsLocked().
|
||||
}
|
||||
|
||||
Expectation::Expectation() {}
|
||||
Expectation::Expectation() = default;
|
||||
|
||||
Expectation::Expectation(
|
||||
const std::shared_ptr<internal::ExpectationBase>& an_expectation_base)
|
||||
: expectation_base_(an_expectation_base) {}
|
||||
|
||||
Expectation::~Expectation() {}
|
||||
Expectation::~Expectation() = default;
|
||||
|
||||
// Adds an expectation to a sequence.
|
||||
void Sequence::AddExpectation(const Expectation& expectation) const {
|
||||
if (*last_expectation_ != expectation) {
|
||||
if (last_expectation_->expectation_base() != nullptr) {
|
||||
expectation.expectation_base()->immediate_prerequisites_
|
||||
+= *last_expectation_;
|
||||
expectation.expectation_base()->immediate_prerequisites_ +=
|
||||
*last_expectation_;
|
||||
}
|
||||
*last_expectation_ = expectation;
|
||||
}
|
||||
@@ -901,8 +787,6 @@ InSequence::~InSequence() {
|
||||
|
||||
} // namespace testing
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#if _MSC_VER == 1900
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
#if defined(_MSC_VER) && (_MSC_VER == 1900)
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4800
|
||||
#endif
|
||||
|
||||
+38
-26
@@ -27,17 +27,17 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
|
||||
namespace testing {
|
||||
#include <string>
|
||||
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
|
||||
GMOCK_DEFINE_bool_(catch_leaked_mocks, true,
|
||||
"true if and only if Google Mock should report leaked "
|
||||
"mock objects as failures.");
|
||||
|
||||
GMOCK_DEFINE_string_(verbose, internal::kWarningVerbosity,
|
||||
GMOCK_DEFINE_string_(verbose, testing::internal::kWarningVerbosity,
|
||||
"Controls how verbose Google Mock's output is."
|
||||
" Valid values:\n"
|
||||
" info - prints all messages.\n"
|
||||
@@ -51,6 +51,7 @@ GMOCK_DEFINE_int32_(default_mock_behavior, 1,
|
||||
" 1 - by default, mocks act as NaggyMocks.\n"
|
||||
" 2 - by default, mocks act as StrictMocks.");
|
||||
|
||||
namespace testing {
|
||||
namespace internal {
|
||||
|
||||
// Parses a string as a command line flag. The string should have the
|
||||
@@ -59,18 +60,18 @@ namespace internal {
|
||||
//
|
||||
// Returns the value of the flag, or NULL if the parsing failed.
|
||||
static const char* ParseGoogleMockFlagValue(const char* str,
|
||||
const char* flag,
|
||||
const char* flag_name,
|
||||
bool def_optional) {
|
||||
// str and flag must not be NULL.
|
||||
if (str == nullptr || flag == nullptr) return nullptr;
|
||||
if (str == nullptr || flag_name == nullptr) return nullptr;
|
||||
|
||||
// The flag must start with "--gmock_".
|
||||
const std::string flag_str = std::string("--gmock_") + flag;
|
||||
const size_t flag_len = flag_str.length();
|
||||
if (strncmp(str, flag_str.c_str(), flag_len) != 0) return nullptr;
|
||||
const std::string flag_name_str = std::string("--gmock_") + flag_name;
|
||||
const size_t flag_name_len = flag_name_str.length();
|
||||
if (strncmp(str, flag_name_str.c_str(), flag_name_len) != 0) return nullptr;
|
||||
|
||||
// Skips the flag name.
|
||||
const char* flag_end = str + flag_len;
|
||||
const char* flag_end = str + flag_name_len;
|
||||
|
||||
// When def_optional is true, it's OK to not have a "=value" part.
|
||||
if (def_optional && (flag_end[0] == '\0')) {
|
||||
@@ -91,10 +92,10 @@ static const char* ParseGoogleMockFlagValue(const char* str,
|
||||
//
|
||||
// On success, stores the value of the flag in *value, and returns
|
||||
// true. On failure, returns false without changing *value.
|
||||
static bool ParseGoogleMockBoolFlag(const char* str, const char* flag,
|
||||
bool* value) {
|
||||
static bool ParseGoogleMockFlag(const char* str, const char* flag_name,
|
||||
bool* value) {
|
||||
// Gets the value of the flag as a string.
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag, true);
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag_name, true);
|
||||
|
||||
// Aborts if the parsing failed.
|
||||
if (value_str == nullptr) return false;
|
||||
@@ -110,10 +111,10 @@ static bool ParseGoogleMockBoolFlag(const char* str, const char* flag,
|
||||
// On success, stores the value of the flag in *value, and returns
|
||||
// true. On failure, returns false without changing *value.
|
||||
template <typename String>
|
||||
static bool ParseGoogleMockStringFlag(const char* str, const char* flag,
|
||||
String* value) {
|
||||
static bool ParseGoogleMockFlag(const char* str, const char* flag_name,
|
||||
String* value) {
|
||||
// Gets the value of the flag as a string.
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag, false);
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag_name, false);
|
||||
|
||||
// Aborts if the parsing failed.
|
||||
if (value_str == nullptr) return false;
|
||||
@@ -123,17 +124,17 @@ static bool ParseGoogleMockStringFlag(const char* str, const char* flag,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool ParseGoogleMockIntFlag(const char* str, const char* flag,
|
||||
int32_t* value) {
|
||||
static bool ParseGoogleMockFlag(const char* str, const char* flag_name,
|
||||
int32_t* value) {
|
||||
// Gets the value of the flag as a string.
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag, true);
|
||||
const char* const value_str = ParseGoogleMockFlagValue(str, flag_name, true);
|
||||
|
||||
// Aborts if the parsing failed.
|
||||
if (value_str == nullptr) return false;
|
||||
|
||||
// Sets *value to the value of the flag.
|
||||
return ParseInt32(Message() << "The value of flag --" << flag,
|
||||
value_str, value);
|
||||
return ParseInt32(Message() << "The value of flag --" << flag_name, value_str,
|
||||
value);
|
||||
}
|
||||
|
||||
// The internal implementation of InitGoogleMock().
|
||||
@@ -152,11 +153,22 @@ void InitGoogleMockImpl(int* argc, CharType** argv) {
|
||||
const char* const arg = arg_string.c_str();
|
||||
|
||||
// Do we see a Google Mock flag?
|
||||
if (ParseGoogleMockBoolFlag(arg, "catch_leaked_mocks",
|
||||
&GMOCK_FLAG(catch_leaked_mocks)) ||
|
||||
ParseGoogleMockStringFlag(arg, "verbose", &GMOCK_FLAG(verbose)) ||
|
||||
ParseGoogleMockIntFlag(arg, "default_mock_behavior",
|
||||
&GMOCK_FLAG(default_mock_behavior))) {
|
||||
bool found_gmock_flag = false;
|
||||
|
||||
#define GMOCK_INTERNAL_PARSE_FLAG(flag_name) \
|
||||
if (!found_gmock_flag) { \
|
||||
auto value = GMOCK_FLAG_GET(flag_name); \
|
||||
if (ParseGoogleMockFlag(arg, #flag_name, &value)) { \
|
||||
GMOCK_FLAG_SET(flag_name, value); \
|
||||
found_gmock_flag = true; \
|
||||
} \
|
||||
}
|
||||
|
||||
GMOCK_INTERNAL_PARSE_FLAG(catch_leaked_mocks)
|
||||
GMOCK_INTERNAL_PARSE_FLAG(verbose)
|
||||
GMOCK_INTERNAL_PARSE_FLAG(default_mock_behavior)
|
||||
|
||||
if (found_gmock_flag) {
|
||||
// Yes. Shift the remainder of the argv list left by one. Note
|
||||
// that argv has (*argc + 1) elements, the last one always being
|
||||
// NULL. The following loop moves the trailing NULL element as
|
||||
|
||||
@@ -27,13 +27,14 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
#include <iostream>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
#if GTEST_OS_ESP8266 || GTEST_OS_ESP32
|
||||
#if GTEST_OS_ESP8266
|
||||
#if defined(GTEST_OS_ESP8266) || defined(GTEST_OS_ESP32) || \
|
||||
(defined(GTEST_OS_NRF52) && defined(ARDUINO))
|
||||
#ifdef GTEST_OS_ESP8266
|
||||
extern "C" {
|
||||
#endif
|
||||
void setup() {
|
||||
@@ -43,7 +44,7 @@ void setup() {
|
||||
testing::InitGoogleMock();
|
||||
}
|
||||
void loop() { RUN_ALL_TESTS(); }
|
||||
#if GTEST_OS_ESP8266
|
||||
#ifdef GTEST_OS_ESP8266
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -55,8 +56,8 @@ void loop() { RUN_ALL_TESTS(); }
|
||||
// Windows. See the following link to track the current status of this bug:
|
||||
// https://web.archive.org/web/20170912203238/connect.microsoft.com/VisualStudio/feedback/details/394464/wmain-link-error-in-the-static-library
|
||||
// // NOLINT
|
||||
#if GTEST_OS_WINDOWS_MOBILE
|
||||
# include <tchar.h> // NOLINT
|
||||
#ifdef GTEST_OS_WINDOWS_MOBILE
|
||||
#include <tchar.h> // NOLINT
|
||||
|
||||
GTEST_API_ int _tmain(int argc, TCHAR** argv) {
|
||||
#else
|
||||
|
||||
@@ -39,8 +39,9 @@ licenses(["notice"])
|
||||
cc_test(
|
||||
name = "gmock_all_test",
|
||||
size = "small",
|
||||
srcs = glob(include = ["gmock-*.cc"]),
|
||||
srcs = glob(include = ["gmock-*.cc"]) + ["gmock-matchers_test.h"],
|
||||
linkopts = select({
|
||||
"//:qnx": [],
|
||||
"//:windows": [],
|
||||
"//conditions:default": ["-pthread"],
|
||||
}),
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -27,14 +27,15 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests the built-in cardinalities.
|
||||
|
||||
#include <ostream>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
#include "gtest/gtest-spi.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
namespace {
|
||||
|
||||
@@ -51,17 +52,16 @@ using testing::MakeCardinality;
|
||||
|
||||
class MockFoo {
|
||||
public:
|
||||
MockFoo() {}
|
||||
MockFoo() = default;
|
||||
MOCK_METHOD0(Bar, int()); // NOLINT
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockFoo);
|
||||
MockFoo(const MockFoo&) = delete;
|
||||
MockFoo& operator=(const MockFoo&) = delete;
|
||||
};
|
||||
|
||||
// Tests that Cardinality objects can be default constructed.
|
||||
TEST(CardinalityTest, IsDefaultConstructable) {
|
||||
Cardinality c;
|
||||
}
|
||||
TEST(CardinalityTest, IsDefaultConstructable) { Cardinality c; }
|
||||
|
||||
// Tests that Cardinality objects are copyable.
|
||||
TEST(CardinalityTest, IsCopyable) {
|
||||
@@ -119,8 +119,7 @@ TEST(AnyNumber, Works) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called any number of times",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called any number of times", ss.str());
|
||||
}
|
||||
|
||||
TEST(AnyNumberTest, HasCorrectBounds) {
|
||||
@@ -132,9 +131,11 @@ TEST(AnyNumberTest, HasCorrectBounds) {
|
||||
// Tests AtLeast(n).
|
||||
|
||||
TEST(AtLeastTest, OnNegativeNumber) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
AtLeast(-1);
|
||||
}, "The invocation lower bound must be >= 0");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)AtLeast(-1);
|
||||
},
|
||||
"The invocation lower bound must be >= 0");
|
||||
}
|
||||
|
||||
TEST(AtLeastTest, OnZero) {
|
||||
@@ -147,8 +148,7 @@ TEST(AtLeastTest, OnZero) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "any number of times",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "any number of times", ss.str());
|
||||
}
|
||||
|
||||
TEST(AtLeastTest, OnPositiveNumber) {
|
||||
@@ -164,18 +164,15 @@ TEST(AtLeastTest, OnPositiveNumber) {
|
||||
|
||||
stringstream ss1;
|
||||
AtLeast(1).DescribeTo(&ss1);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least once",
|
||||
ss1.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least once", ss1.str());
|
||||
|
||||
stringstream ss2;
|
||||
c.DescribeTo(&ss2);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least twice",
|
||||
ss2.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least twice", ss2.str());
|
||||
|
||||
stringstream ss3;
|
||||
AtLeast(3).DescribeTo(&ss3);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least 3 times",
|
||||
ss3.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "at least 3 times", ss3.str());
|
||||
}
|
||||
|
||||
TEST(AtLeastTest, HasCorrectBounds) {
|
||||
@@ -187,9 +184,11 @@ TEST(AtLeastTest, HasCorrectBounds) {
|
||||
// Tests AtMost(n).
|
||||
|
||||
TEST(AtMostTest, OnNegativeNumber) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
AtMost(-1);
|
||||
}, "The invocation upper bound must be >= 0");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)AtMost(-1);
|
||||
},
|
||||
"The invocation upper bound must be >= 0");
|
||||
}
|
||||
|
||||
TEST(AtMostTest, OnZero) {
|
||||
@@ -202,8 +201,7 @@ TEST(AtMostTest, OnZero) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called", ss.str());
|
||||
}
|
||||
|
||||
TEST(AtMostTest, OnPositiveNumber) {
|
||||
@@ -219,18 +217,15 @@ TEST(AtMostTest, OnPositiveNumber) {
|
||||
|
||||
stringstream ss1;
|
||||
AtMost(1).DescribeTo(&ss1);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most once",
|
||||
ss1.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most once", ss1.str());
|
||||
|
||||
stringstream ss2;
|
||||
c.DescribeTo(&ss2);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most twice",
|
||||
ss2.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most twice", ss2.str());
|
||||
|
||||
stringstream ss3;
|
||||
AtMost(3).DescribeTo(&ss3);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most 3 times",
|
||||
ss3.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most 3 times", ss3.str());
|
||||
}
|
||||
|
||||
TEST(AtMostTest, HasCorrectBounds) {
|
||||
@@ -242,22 +237,28 @@ TEST(AtMostTest, HasCorrectBounds) {
|
||||
// Tests Between(m, n).
|
||||
|
||||
TEST(BetweenTest, OnNegativeStart) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Between(-1, 2);
|
||||
}, "The invocation lower bound must be >= 0, but is actually -1");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)Between(-1, 2);
|
||||
},
|
||||
"The invocation lower bound must be >= 0, but is actually -1");
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnNegativeEnd) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Between(1, -2);
|
||||
}, "The invocation upper bound must be >= 0, but is actually -2");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)Between(1, -2);
|
||||
},
|
||||
"The invocation upper bound must be >= 0, but is actually -2");
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnStartBiggerThanEnd) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Between(2, 1);
|
||||
}, "The invocation upper bound (1) must be >= "
|
||||
"the invocation lower bound (2)");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)Between(2, 1);
|
||||
},
|
||||
"The invocation upper bound (1) must be >= "
|
||||
"the invocation lower bound (2)");
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnZeroStartAndZeroEnd) {
|
||||
@@ -271,8 +272,7 @@ TEST(BetweenTest, OnZeroStartAndZeroEnd) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called", ss.str());
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnZeroStartAndNonZeroEnd) {
|
||||
@@ -289,8 +289,7 @@ TEST(BetweenTest, OnZeroStartAndNonZeroEnd) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most twice",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called at most twice", ss.str());
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnSameStartAndEnd) {
|
||||
@@ -307,8 +306,7 @@ TEST(BetweenTest, OnSameStartAndEnd) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called 3 times",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called 3 times", ss.str());
|
||||
}
|
||||
|
||||
TEST(BetweenTest, OnDifferentStartAndEnd) {
|
||||
@@ -328,8 +326,7 @@ TEST(BetweenTest, OnDifferentStartAndEnd) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called between 3 and 5 times",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called between 3 and 5 times", ss.str());
|
||||
}
|
||||
|
||||
TEST(BetweenTest, HasCorrectBounds) {
|
||||
@@ -341,9 +338,11 @@ TEST(BetweenTest, HasCorrectBounds) {
|
||||
// Tests Exactly(n).
|
||||
|
||||
TEST(ExactlyTest, OnNegativeNumber) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Exactly(-1);
|
||||
}, "The invocation lower bound must be >= 0");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
(void)Exactly(-1);
|
||||
},
|
||||
"The invocation lower bound must be >= 0");
|
||||
}
|
||||
|
||||
TEST(ExactlyTest, OnZero) {
|
||||
@@ -356,8 +355,7 @@ TEST(ExactlyTest, OnZero) {
|
||||
|
||||
stringstream ss;
|
||||
c.DescribeTo(&ss);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called",
|
||||
ss.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "never called", ss.str());
|
||||
}
|
||||
|
||||
TEST(ExactlyTest, OnPositiveNumber) {
|
||||
@@ -370,18 +368,15 @@ TEST(ExactlyTest, OnPositiveNumber) {
|
||||
|
||||
stringstream ss1;
|
||||
Exactly(1).DescribeTo(&ss1);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called once",
|
||||
ss1.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called once", ss1.str());
|
||||
|
||||
stringstream ss2;
|
||||
c.DescribeTo(&ss2);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called twice",
|
||||
ss2.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called twice", ss2.str());
|
||||
|
||||
stringstream ss3;
|
||||
Exactly(3).DescribeTo(&ss3);
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called 3 times",
|
||||
ss3.str());
|
||||
EXPECT_PRED_FORMAT2(IsSubstring, "called 3 times", ss3.str());
|
||||
}
|
||||
|
||||
TEST(ExactlyTest, HasCorrectBounds) {
|
||||
|
||||
@@ -27,17 +27,26 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests the function mocker classes.
|
||||
#include "gmock/gmock-function-mocker.h"
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
// Silence C4503 (decorated name length exceeded) for MSVC.
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4503)
|
||||
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic push
|
||||
// This file intentionally tests many ways of writing Mock classes, including
|
||||
// with and without the override keyword.
|
||||
#pragma clang diagnostic ignored "-Winconsistent-missing-override"
|
||||
#endif
|
||||
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
// MSDN says the header file to be included for STDMETHOD is BaseTyps.h but
|
||||
// we are getting compiler errors if we use basetyps.h, hence including
|
||||
// objbase.h for definition of STDMETHOD.
|
||||
# include <objbase.h>
|
||||
#include <objbase.h>
|
||||
#endif // GTEST_OS_WINDOWS
|
||||
|
||||
#include <functional>
|
||||
@@ -65,10 +74,10 @@ using testing::Return;
|
||||
using testing::ReturnRef;
|
||||
using testing::TypedEq;
|
||||
|
||||
template<typename T>
|
||||
template <typename T>
|
||||
class TemplatedCopyable {
|
||||
public:
|
||||
TemplatedCopyable() {}
|
||||
TemplatedCopyable() = default;
|
||||
|
||||
template <typename U>
|
||||
TemplatedCopyable(const U& other) {} // NOLINT
|
||||
@@ -76,20 +85,20 @@ class TemplatedCopyable {
|
||||
|
||||
class FooInterface {
|
||||
public:
|
||||
virtual ~FooInterface() {}
|
||||
virtual ~FooInterface() = default;
|
||||
|
||||
virtual void VoidReturning(int x) = 0;
|
||||
|
||||
virtual int Nullary() = 0;
|
||||
virtual bool Unary(int x) = 0;
|
||||
virtual long Binary(short x, int y) = 0; // NOLINT
|
||||
virtual long Binary(short x, int y) = 0; // NOLINT
|
||||
virtual int Decimal(bool b, char c, short d, int e, long f, // NOLINT
|
||||
float g, double h, unsigned i, char* j,
|
||||
const std::string& k) = 0;
|
||||
|
||||
virtual bool TakesNonConstReference(int& n) = 0; // NOLINT
|
||||
virtual std::string TakesConstReference(const int& n) = 0;
|
||||
virtual bool TakesConst(const int x) = 0;
|
||||
virtual bool TakesConst(int x) = 0;
|
||||
|
||||
virtual int OverloadedOnArgumentNumber() = 0;
|
||||
virtual int OverloadedOnArgumentNumber(int n) = 0;
|
||||
@@ -118,7 +127,7 @@ class FooInterface {
|
||||
virtual int RefQualifiedOverloaded() & = 0;
|
||||
virtual int RefQualifiedOverloaded() && = 0;
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
STDMETHOD_(int, CTNullary)() = 0;
|
||||
STDMETHOD_(bool, CTUnary)(int x) = 0;
|
||||
STDMETHOD_(int, CTDecimal)
|
||||
@@ -132,13 +141,10 @@ class FooInterface {
|
||||
// significant in determining whether two virtual functions had the same
|
||||
// signature. This was fixed in Visual Studio 2008. However, the compiler
|
||||
// still emits a warning that alerts about this change in behavior.
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable : 4373)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4373)
|
||||
class MockFoo : public FooInterface {
|
||||
public:
|
||||
MockFoo() {}
|
||||
MockFoo() = default;
|
||||
|
||||
// Makes sure that a mock function parameter can be named.
|
||||
MOCK_METHOD(void, VoidReturning, (int n)); // NOLINT
|
||||
@@ -179,7 +185,7 @@ class MockFoo : public FooInterface {
|
||||
MOCK_METHOD(int (*)(bool), ReturnsFunctionPointer1, (int), ());
|
||||
MOCK_METHOD(fn_ptr, ReturnsFunctionPointer2, (int), ());
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
MOCK_METHOD(int, CTNullary, (), (Calltype(STDMETHODCALLTYPE)));
|
||||
MOCK_METHOD(bool, CTUnary, (int), (Calltype(STDMETHODCALLTYPE)));
|
||||
MOCK_METHOD(int, CTDecimal,
|
||||
@@ -203,12 +209,13 @@ class MockFoo : public FooInterface {
|
||||
MOCK_METHOD(int, RefQualifiedOverloaded, (), (ref(&&), override));
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockFoo);
|
||||
MockFoo(const MockFoo&) = delete;
|
||||
MockFoo& operator=(const MockFoo&) = delete;
|
||||
};
|
||||
|
||||
class LegacyMockFoo : public FooInterface {
|
||||
public:
|
||||
LegacyMockFoo() {}
|
||||
LegacyMockFoo() = default;
|
||||
|
||||
// Makes sure that a mock function parameter can be named.
|
||||
MOCK_METHOD1(VoidReturning, void(int n)); // NOLINT
|
||||
@@ -248,7 +255,7 @@ class LegacyMockFoo : public FooInterface {
|
||||
MOCK_METHOD1(ReturnsFunctionPointer1, int (*(int))(bool));
|
||||
MOCK_METHOD1(ReturnsFunctionPointer2, fn_ptr(int));
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
MOCK_METHOD0_WITH_CALLTYPE(STDMETHODCALLTYPE, CTNullary, int());
|
||||
MOCK_METHOD1_WITH_CALLTYPE(STDMETHODCALLTYPE, CTUnary, bool(int)); // NOLINT
|
||||
MOCK_METHOD10_WITH_CALLTYPE(STDMETHODCALLTYPE, CTDecimal,
|
||||
@@ -275,12 +282,11 @@ class LegacyMockFoo : public FooInterface {
|
||||
int RefQualifiedOverloaded() && override { return 0; }
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(LegacyMockFoo);
|
||||
LegacyMockFoo(const LegacyMockFoo&) = delete;
|
||||
LegacyMockFoo& operator=(const LegacyMockFoo&) = delete;
|
||||
};
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4373
|
||||
|
||||
template <class T>
|
||||
class FunctionMockerTest : public testing::Test {
|
||||
@@ -326,8 +332,8 @@ TYPED_TEST(FunctionMockerTest, MocksBinaryFunction) {
|
||||
|
||||
// Tests mocking a decimal function.
|
||||
TYPED_TEST(FunctionMockerTest, MocksDecimalFunction) {
|
||||
EXPECT_CALL(this->mock_foo_,
|
||||
Decimal(true, 'a', 0, 0, 1L, A<float>(), Lt(100), 5U, NULL, "hi"))
|
||||
EXPECT_CALL(this->mock_foo_, Decimal(true, 'a', 0, 0, 1L, A<float>(), Lt(100),
|
||||
5U, nullptr, "hi"))
|
||||
.WillOnce(Return(5));
|
||||
|
||||
EXPECT_EQ(5, this->foo_->Decimal(true, 'a', 0, 0, 1, 0, 0, 5, nullptr, "hi"));
|
||||
@@ -405,7 +411,7 @@ TYPED_TEST(FunctionMockerTest, MocksTypeWithTemplatedCopyCtor) {
|
||||
EXPECT_TRUE(this->foo_->TypeWithTemplatedCopyCtor(TemplatedCopyable<int>()));
|
||||
}
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
// Tests mocking a nullary function with calltype.
|
||||
TYPED_TEST(FunctionMockerTest, MocksNullaryFunctionWithCallType) {
|
||||
EXPECT_CALL(this->mock_foo_, CTNullary())
|
||||
@@ -452,6 +458,87 @@ TYPED_TEST(FunctionMockerTest, MocksReturnTypeWithCommaAndCallType) {
|
||||
|
||||
#endif // GTEST_OS_WINDOWS
|
||||
|
||||
// Compilability test, to ensure macros expand to all the arguments they're
|
||||
// supposed to.
|
||||
class MockManyArgs {
|
||||
using T = int;
|
||||
|
||||
public:
|
||||
MockManyArgs() = default;
|
||||
|
||||
MOCK_METHOD(void, F, (), ());
|
||||
MOCK_METHOD(void, F, (T), ());
|
||||
MOCK_METHOD(void, F, (T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F, (T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T), ());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T, T, T, T, T),
|
||||
());
|
||||
MOCK_METHOD(void, F,
|
||||
(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,
|
||||
T, T, T, T, T, T, T, T, T),
|
||||
());
|
||||
|
||||
private:
|
||||
MockManyArgs(const MockManyArgs&) = delete;
|
||||
MockManyArgs& operator=(const MockManyArgs&) = delete;
|
||||
};
|
||||
|
||||
TEST(FunctionMockerTest, RefQualified) {
|
||||
MockFoo mock_foo;
|
||||
|
||||
@@ -488,22 +575,24 @@ TEST(FunctionMockerTest, RefQualified) {
|
||||
|
||||
class MockB {
|
||||
public:
|
||||
MockB() {}
|
||||
MockB() = default;
|
||||
|
||||
MOCK_METHOD(void, DoB, ());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockB);
|
||||
MockB(const MockB&) = delete;
|
||||
MockB& operator=(const MockB&) = delete;
|
||||
};
|
||||
|
||||
class LegacyMockB {
|
||||
public:
|
||||
LegacyMockB() {}
|
||||
LegacyMockB() = default;
|
||||
|
||||
MOCK_METHOD0(DoB, void());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(LegacyMockB);
|
||||
LegacyMockB(const LegacyMockB&) = delete;
|
||||
LegacyMockB& operator=(const LegacyMockB&) = delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
@@ -533,7 +622,7 @@ TYPED_TEST(ExpectCallTest, UnmentionedFunctionCanBeCalledAnyNumberOfTimes) {
|
||||
template <typename T>
|
||||
class StackInterface {
|
||||
public:
|
||||
virtual ~StackInterface() {}
|
||||
virtual ~StackInterface() = default;
|
||||
|
||||
// Template parameter appears in function parameter.
|
||||
virtual void Push(const T& value) = 0;
|
||||
@@ -546,7 +635,7 @@ class StackInterface {
|
||||
template <typename T>
|
||||
class MockStack : public StackInterface<T> {
|
||||
public:
|
||||
MockStack() {}
|
||||
MockStack() = default;
|
||||
|
||||
MOCK_METHOD(void, Push, (const T& elem), ());
|
||||
MOCK_METHOD(void, Pop, (), (final));
|
||||
@@ -558,13 +647,14 @@ class MockStack : public StackInterface<T> {
|
||||
MOCK_METHOD((std::map<int, int>), ReturnTypeWithComma, (int), (const));
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockStack);
|
||||
MockStack(const MockStack&) = delete;
|
||||
MockStack& operator=(const MockStack&) = delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
class LegacyMockStack : public StackInterface<T> {
|
||||
public:
|
||||
LegacyMockStack() {}
|
||||
LegacyMockStack() = default;
|
||||
|
||||
MOCK_METHOD1_T(Push, void(const T& elem));
|
||||
MOCK_METHOD0_T(Pop, void());
|
||||
@@ -576,7 +666,8 @@ class LegacyMockStack : public StackInterface<T> {
|
||||
MOCK_CONST_METHOD1_T(ReturnTypeWithComma, std::map<int, int>(int)); // NOLINT
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(LegacyMockStack);
|
||||
LegacyMockStack(const LegacyMockStack&) = delete;
|
||||
LegacyMockStack& operator=(const LegacyMockStack&) = delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
@@ -595,10 +686,8 @@ TYPED_TEST(TemplateMockTest, Works) {
|
||||
.WillOnce(Return(0));
|
||||
EXPECT_CALL(mock, Push(_));
|
||||
int n = 5;
|
||||
EXPECT_CALL(mock, GetTop())
|
||||
.WillOnce(ReturnRef(n));
|
||||
EXPECT_CALL(mock, Pop())
|
||||
.Times(AnyNumber());
|
||||
EXPECT_CALL(mock, GetTop()).WillOnce(ReturnRef(n));
|
||||
EXPECT_CALL(mock, Pop()).Times(AnyNumber());
|
||||
|
||||
EXPECT_EQ(0, mock.GetSize());
|
||||
mock.Push(5);
|
||||
@@ -612,16 +701,14 @@ TYPED_TEST(TemplateMockTest, MethodWithCommaInReturnTypeWorks) {
|
||||
TypeParam mock;
|
||||
|
||||
const std::map<int, int> a_map;
|
||||
EXPECT_CALL(mock, ReturnTypeWithComma())
|
||||
.WillOnce(Return(a_map));
|
||||
EXPECT_CALL(mock, ReturnTypeWithComma(1))
|
||||
.WillOnce(Return(a_map));
|
||||
EXPECT_CALL(mock, ReturnTypeWithComma()).WillOnce(Return(a_map));
|
||||
EXPECT_CALL(mock, ReturnTypeWithComma(1)).WillOnce(Return(a_map));
|
||||
|
||||
EXPECT_EQ(a_map, mock.ReturnTypeWithComma());
|
||||
EXPECT_EQ(a_map, mock.ReturnTypeWithComma(1));
|
||||
}
|
||||
|
||||
#if GTEST_OS_WINDOWS
|
||||
#ifdef GTEST_OS_WINDOWS
|
||||
// Tests mocking template interfaces with calltype.
|
||||
|
||||
template <typename T>
|
||||
@@ -650,7 +737,8 @@ class MockStackWithCallType : public StackInterfaceWithCallType<T> {
|
||||
(Calltype(STDMETHODCALLTYPE), override, const));
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockStackWithCallType);
|
||||
MockStackWithCallType(const MockStackWithCallType&) = delete;
|
||||
MockStackWithCallType& operator=(const MockStackWithCallType&) = delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
@@ -664,7 +752,9 @@ class LegacyMockStackWithCallType : public StackInterfaceWithCallType<T> {
|
||||
MOCK_CONST_METHOD0_T_WITH_CALLTYPE(STDMETHODCALLTYPE, GetTop, const T&());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(LegacyMockStackWithCallType);
|
||||
LegacyMockStackWithCallType(const LegacyMockStackWithCallType&) = delete;
|
||||
LegacyMockStackWithCallType& operator=(const LegacyMockStackWithCallType&) =
|
||||
delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
@@ -685,10 +775,8 @@ TYPED_TEST(TemplateMockTestWithCallType, Works) {
|
||||
.WillOnce(Return(0));
|
||||
EXPECT_CALL(mock, Push(_));
|
||||
int n = 5;
|
||||
EXPECT_CALL(mock, GetTop())
|
||||
.WillOnce(ReturnRef(n));
|
||||
EXPECT_CALL(mock, Pop())
|
||||
.Times(AnyNumber());
|
||||
EXPECT_CALL(mock, GetTop()).WillOnce(ReturnRef(n));
|
||||
EXPECT_CALL(mock, Pop()).Times(AnyNumber());
|
||||
|
||||
EXPECT_EQ(0, mock.GetSize());
|
||||
mock.Push(5);
|
||||
@@ -711,22 +799,27 @@ TYPED_TEST(TemplateMockTestWithCallType, Works) {
|
||||
|
||||
class MockOverloadedOnArgNumber {
|
||||
public:
|
||||
MockOverloadedOnArgNumber() {}
|
||||
MockOverloadedOnArgNumber() = default;
|
||||
|
||||
MY_MOCK_METHODS1_;
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockOverloadedOnArgNumber);
|
||||
MockOverloadedOnArgNumber(const MockOverloadedOnArgNumber&) = delete;
|
||||
MockOverloadedOnArgNumber& operator=(const MockOverloadedOnArgNumber&) =
|
||||
delete;
|
||||
};
|
||||
|
||||
class LegacyMockOverloadedOnArgNumber {
|
||||
public:
|
||||
LegacyMockOverloadedOnArgNumber() {}
|
||||
LegacyMockOverloadedOnArgNumber() = default;
|
||||
|
||||
LEGACY_MY_MOCK_METHODS1_;
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(LegacyMockOverloadedOnArgNumber);
|
||||
LegacyMockOverloadedOnArgNumber(const LegacyMockOverloadedOnArgNumber&) =
|
||||
delete;
|
||||
LegacyMockOverloadedOnArgNumber& operator=(
|
||||
const LegacyMockOverloadedOnArgNumber&) = delete;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
@@ -747,18 +840,20 @@ TYPED_TEST(OverloadedMockMethodTest, CanOverloadOnArgNumberInMacroBody) {
|
||||
EXPECT_TRUE(mock.Overloaded(true, 1));
|
||||
}
|
||||
|
||||
#define MY_MOCK_METHODS2_ \
|
||||
MOCK_CONST_METHOD1(Overloaded, int(int n)); \
|
||||
MOCK_METHOD1(Overloaded, int(int n))
|
||||
#define MY_MOCK_METHODS2_ \
|
||||
MOCK_CONST_METHOD1(Overloaded, int(int n)); \
|
||||
MOCK_METHOD1(Overloaded, int(int n))
|
||||
|
||||
class MockOverloadedOnConstness {
|
||||
public:
|
||||
MockOverloadedOnConstness() {}
|
||||
MockOverloadedOnConstness() = default;
|
||||
|
||||
MY_MOCK_METHODS2_;
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockOverloadedOnConstness);
|
||||
MockOverloadedOnConstness(const MockOverloadedOnConstness&) = delete;
|
||||
MockOverloadedOnConstness& operator=(const MockOverloadedOnConstness&) =
|
||||
delete;
|
||||
};
|
||||
|
||||
TEST(MockMethodOverloadedMockMethodTest, CanOverloadOnConstnessInMacroBody) {
|
||||
@@ -779,9 +874,7 @@ TEST(MockMethodMockFunctionTest, WorksForVoidNullary) {
|
||||
|
||||
TEST(MockMethodMockFunctionTest, WorksForNonVoidNullary) {
|
||||
MockFunction<int()> foo;
|
||||
EXPECT_CALL(foo, Call())
|
||||
.WillOnce(Return(1))
|
||||
.WillOnce(Return(2));
|
||||
EXPECT_CALL(foo, Call()).WillOnce(Return(1)).WillOnce(Return(2));
|
||||
EXPECT_EQ(1, foo.Call());
|
||||
EXPECT_EQ(2, foo.Call());
|
||||
}
|
||||
@@ -794,19 +887,17 @@ TEST(MockMethodMockFunctionTest, WorksForVoidUnary) {
|
||||
|
||||
TEST(MockMethodMockFunctionTest, WorksForNonVoidBinary) {
|
||||
MockFunction<int(bool, int)> foo;
|
||||
EXPECT_CALL(foo, Call(false, 42))
|
||||
.WillOnce(Return(1))
|
||||
.WillOnce(Return(2));
|
||||
EXPECT_CALL(foo, Call(true, Ge(100)))
|
||||
.WillOnce(Return(3));
|
||||
EXPECT_CALL(foo, Call(false, 42)).WillOnce(Return(1)).WillOnce(Return(2));
|
||||
EXPECT_CALL(foo, Call(true, Ge(100))).WillOnce(Return(3));
|
||||
EXPECT_EQ(1, foo.Call(false, 42));
|
||||
EXPECT_EQ(2, foo.Call(false, 42));
|
||||
EXPECT_EQ(3, foo.Call(true, 120));
|
||||
}
|
||||
|
||||
TEST(MockMethodMockFunctionTest, WorksFor10Arguments) {
|
||||
MockFunction<int(bool a0, char a1, int a2, int a3, int a4,
|
||||
int a5, int a6, char a7, int a8, bool a9)> foo;
|
||||
MockFunction<int(bool a0, char a1, int a2, int a3, int a4, int a5, int a6,
|
||||
char a7, int a8, bool a9)>
|
||||
foo;
|
||||
EXPECT_CALL(foo, Call(_, 'a', _, _, _, _, _, _, _, _))
|
||||
.WillOnce(Return(1))
|
||||
.WillOnce(Return(2));
|
||||
@@ -816,9 +907,7 @@ TEST(MockMethodMockFunctionTest, WorksFor10Arguments) {
|
||||
|
||||
TEST(MockMethodMockFunctionTest, AsStdFunction) {
|
||||
MockFunction<int(int)> foo;
|
||||
auto call = [](const std::function<int(int)> &f, int i) {
|
||||
return f(i);
|
||||
};
|
||||
auto call = [](const std::function<int(int)>& f, int i) { return f(i); };
|
||||
EXPECT_CALL(foo, Call(1)).WillOnce(Return(-1));
|
||||
EXPECT_CALL(foo, Call(2)).WillOnce(Return(-2));
|
||||
EXPECT_EQ(-1, call(foo.AsStdFunction(), 1));
|
||||
@@ -836,10 +925,8 @@ TEST(MockMethodMockFunctionTest, AsStdFunctionReturnsReference) {
|
||||
}
|
||||
|
||||
TEST(MockMethodMockFunctionTest, AsStdFunctionWithReferenceParameter) {
|
||||
MockFunction<int(int &)> foo;
|
||||
auto call = [](const std::function<int(int& )> &f, int &i) {
|
||||
return f(i);
|
||||
};
|
||||
MockFunction<int(int&)> foo;
|
||||
auto call = [](const std::function<int(int&)>& f, int& i) { return f(i); };
|
||||
int i = 42;
|
||||
EXPECT_CALL(foo, Call(i)).WillOnce(Return(-1));
|
||||
EXPECT_EQ(-1, call(foo.AsStdFunction(), i));
|
||||
@@ -850,11 +937,20 @@ namespace {
|
||||
template <typename Expected, typename F>
|
||||
static constexpr bool IsMockFunctionTemplateArgumentDeducedTo(
|
||||
const internal::MockFunction<F>&) {
|
||||
return std::is_same<F, Expected>::value;
|
||||
return std::is_same_v<F, Expected>;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
// Like std::add_const, but for function types.
|
||||
template <typename F>
|
||||
struct AddConstToFunction;
|
||||
|
||||
template <typename R, typename... Args>
|
||||
struct AddConstToFunction<R(Args...)> {
|
||||
using type = R(Args...) const;
|
||||
};
|
||||
|
||||
template <typename F>
|
||||
class MockMethodMockFunctionSignatureTest : public Test {};
|
||||
|
||||
@@ -866,30 +962,73 @@ TYPED_TEST_SUITE(MockMethodMockFunctionSignatureTest,
|
||||
|
||||
TYPED_TEST(MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionTemplateArgumentDeducedForRawSignature) {
|
||||
using Argument = TypeParam;
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
// Non-const
|
||||
{
|
||||
using Argument = TypeParam;
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
}
|
||||
|
||||
// Const
|
||||
{
|
||||
using Argument = typename AddConstToFunction<TypeParam>::type;
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
}
|
||||
}
|
||||
|
||||
TYPED_TEST(MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionTemplateArgumentDeducedForStdFunction) {
|
||||
using Argument = std::function<TypeParam>;
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
// Non-const
|
||||
{
|
||||
using Argument = std::function<TypeParam>;
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
}
|
||||
|
||||
// As of 2026-05 MSVC doesn't know how to deal with this, providing pages of
|
||||
// inscrutable errors about std::_Get_function_impl. But this is fine, since
|
||||
// std::function<R(Args...) const> doesn't apply the const qualifier correctly
|
||||
// anyway.
|
||||
#if !defined(_MSC_VER)
|
||||
|
||||
// Const
|
||||
{
|
||||
using Argument =
|
||||
std::function<typename AddConstToFunction<TypeParam>::type>;
|
||||
|
||||
MockFunction<Argument> foo;
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
}
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
TYPED_TEST(
|
||||
MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionCallMethodSignatureTheSameForRawSignatureAndStdFunction) {
|
||||
using ForRawSignature = decltype(&MockFunction<TypeParam>::Call);
|
||||
using ForStdFunction =
|
||||
decltype(&MockFunction<std::function<TypeParam>>::Call);
|
||||
EXPECT_TRUE((std::is_same<ForRawSignature, ForStdFunction>::value));
|
||||
// Non-const
|
||||
{
|
||||
using ForRawSignature = decltype(&MockFunction<TypeParam>::Call);
|
||||
using ForStdFunction =
|
||||
decltype(&MockFunction<std::function<TypeParam>>::Call);
|
||||
EXPECT_TRUE((std::is_same<ForRawSignature, ForStdFunction>::value));
|
||||
}
|
||||
|
||||
// Const
|
||||
{
|
||||
using ConstTypeParam = typename AddConstToFunction<TypeParam>::type;
|
||||
using ForRawSignature = decltype(&MockFunction<ConstTypeParam>::Call);
|
||||
|
||||
using ForStdFunction =
|
||||
decltype(&MockFunction<std::function<ConstTypeParam>>::Call);
|
||||
|
||||
EXPECT_TRUE((std::is_same<ForRawSignature, ForStdFunction>::value));
|
||||
}
|
||||
}
|
||||
|
||||
template <typename F>
|
||||
struct AlternateCallable {
|
||||
};
|
||||
struct AlternateCallable {};
|
||||
|
||||
TYPED_TEST(MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionTemplateArgumentDeducedForAlternateCallable) {
|
||||
@@ -898,16 +1037,14 @@ TYPED_TEST(MockMethodMockFunctionSignatureTest,
|
||||
EXPECT_TRUE(IsMockFunctionTemplateArgumentDeducedTo<TypeParam>(foo));
|
||||
}
|
||||
|
||||
TYPED_TEST(
|
||||
MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionCallMethodSignatureTheSameForAlternateCallable) {
|
||||
TYPED_TEST(MockMethodMockFunctionSignatureTest,
|
||||
IsMockFunctionCallMethodSignatureTheSameForAlternateCallable) {
|
||||
using ForRawSignature = decltype(&MockFunction<TypeParam>::Call);
|
||||
using ForStdFunction =
|
||||
decltype(&MockFunction<std::function<TypeParam>>::Call);
|
||||
EXPECT_TRUE((std::is_same<ForRawSignature, ForStdFunction>::value));
|
||||
}
|
||||
|
||||
|
||||
struct MockMethodSizes0 {
|
||||
MOCK_METHOD(void, func, ());
|
||||
};
|
||||
@@ -925,22 +1062,21 @@ struct MockMethodSizes4 {
|
||||
};
|
||||
|
||||
struct LegacyMockMethodSizes0 {
|
||||
MOCK_METHOD0(func, void());
|
||||
MOCK_METHOD0(func, void());
|
||||
};
|
||||
struct LegacyMockMethodSizes1 {
|
||||
MOCK_METHOD1(func, void(int));
|
||||
MOCK_METHOD1(func, void(int));
|
||||
};
|
||||
struct LegacyMockMethodSizes2 {
|
||||
MOCK_METHOD2(func, void(int, int));
|
||||
MOCK_METHOD2(func, void(int, int));
|
||||
};
|
||||
struct LegacyMockMethodSizes3 {
|
||||
MOCK_METHOD3(func, void(int, int, int));
|
||||
MOCK_METHOD3(func, void(int, int, int));
|
||||
};
|
||||
struct LegacyMockMethodSizes4 {
|
||||
MOCK_METHOD4(func, void(int, int, int, int));
|
||||
MOCK_METHOD4(func, void(int, int, int, int));
|
||||
};
|
||||
|
||||
|
||||
TEST(MockMethodMockFunctionTest, MockMethodSizeOverhead) {
|
||||
EXPECT_EQ(sizeof(MockMethodSizes0), sizeof(MockMethodSizes1));
|
||||
EXPECT_EQ(sizeof(MockMethodSizes0), sizeof(MockMethodSizes2));
|
||||
@@ -955,6 +1091,21 @@ TEST(MockMethodMockFunctionTest, MockMethodSizeOverhead) {
|
||||
EXPECT_EQ(sizeof(LegacyMockMethodSizes0), sizeof(MockMethodSizes0));
|
||||
}
|
||||
|
||||
TEST(MockMethodMockFunctionTest, EnsureNoUnusedMemberFunction) {
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic error "-Wunused-member-function"
|
||||
#endif
|
||||
// https://github.com/google/googletest/issues/4052
|
||||
struct Foo {
|
||||
MOCK_METHOD(void, foo, ());
|
||||
};
|
||||
EXPECT_CALL(Foo(), foo()).Times(0);
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic pop
|
||||
#endif
|
||||
}
|
||||
|
||||
void hasTwoParams(int, int);
|
||||
void MaybeThrows();
|
||||
void DoesntThrow() noexcept;
|
||||
@@ -984,3 +1135,5 @@ TEST(MockMethodMockFunctionTest, NoexceptSpecifierPreserved) {
|
||||
|
||||
} // namespace gmock_function_mocker_test
|
||||
} // namespace testing
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4503
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests the internal utilities.
|
||||
@@ -41,6 +40,7 @@
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <tuple>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
@@ -57,8 +57,8 @@
|
||||
#include "src/gtest-internal-inl.h"
|
||||
#undef GTEST_IMPLEMENTATION_
|
||||
|
||||
#if GTEST_OS_CYGWIN
|
||||
# include <sys/types.h> // For ssize_t. NOLINT
|
||||
#ifdef GTEST_OS_CYGWIN
|
||||
#include <sys/types.h> // For ssize_t. NOLINT
|
||||
#endif
|
||||
|
||||
namespace proto2 {
|
||||
@@ -70,24 +70,23 @@ namespace internal {
|
||||
|
||||
namespace {
|
||||
|
||||
TEST(JoinAsTupleTest, JoinsEmptyTuple) {
|
||||
EXPECT_EQ("", JoinAsTuple(Strings()));
|
||||
TEST(JoinAsKeyValueTupleTest, JoinsEmptyTuple) {
|
||||
EXPECT_EQ("", JoinAsKeyValueTuple({}, Strings()));
|
||||
}
|
||||
|
||||
TEST(JoinAsTupleTest, JoinsOneTuple) {
|
||||
const char* fields[] = {"1"};
|
||||
EXPECT_EQ("1", JoinAsTuple(Strings(fields, fields + 1)));
|
||||
TEST(JoinAsKeyValueTupleTest, JoinsOneTuple) {
|
||||
EXPECT_EQ("(a: 1)", JoinAsKeyValueTuple({"a"}, {"1"}));
|
||||
}
|
||||
|
||||
TEST(JoinAsTupleTest, JoinsTwoTuple) {
|
||||
const char* fields[] = {"1", "a"};
|
||||
EXPECT_EQ("(1, a)", JoinAsTuple(Strings(fields, fields + 2)));
|
||||
TEST(JoinAsKeyValueTupleTest, JoinsTwoTuple) {
|
||||
EXPECT_EQ("(a: 1, b: 2)", JoinAsKeyValueTuple({"a", "b"}, {"1", "2"}));
|
||||
}
|
||||
|
||||
TEST(JoinAsTupleTest, JoinsTenTuple) {
|
||||
const char* fields[] = {"1", "2", "3", "4", "5", "6", "7", "8", "9", "10"};
|
||||
EXPECT_EQ("(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)",
|
||||
JoinAsTuple(Strings(fields, fields + 10)));
|
||||
TEST(JoinAsKeyValueTupleTest, JoinsTenTuple) {
|
||||
EXPECT_EQ(
|
||||
"(a: 1, b: 2, c: 3, d: 4, e: 5, f: 6, g: 7, h: 8, i: 9, j: 10)",
|
||||
JoinAsKeyValueTuple({"a", "b", "c", "d", "e", "f", "g", "h", "i", "j"},
|
||||
{"1", "2", "3", "4", "5", "6", "7", "8", "9", "10"}));
|
||||
}
|
||||
|
||||
TEST(ConvertIdentifierNameToWordsTest, WorksWhenNameContainsNoWord) {
|
||||
@@ -140,6 +139,12 @@ TEST(GetRawPointerTest, WorksForRawPointers) {
|
||||
EXPECT_EQ(&n, GetRawPointer(&n));
|
||||
}
|
||||
|
||||
TEST(GetRawPointerTest, WorksForStdReferenceWrapper) {
|
||||
int n = 1;
|
||||
EXPECT_EQ(&n, GetRawPointer(std::ref(n)));
|
||||
EXPECT_EQ(&n, GetRawPointer(std::cref(n)));
|
||||
}
|
||||
|
||||
// Tests KindOf<T>.
|
||||
|
||||
class Base {};
|
||||
@@ -150,35 +155,35 @@ TEST(KindOfTest, Bool) {
|
||||
}
|
||||
|
||||
TEST(KindOfTest, Integer) {
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(signed char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(short)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned short)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(int)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned int)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(long long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(signed char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned char)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(short)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned short)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(int)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned int)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(long long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(unsigned long long)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(wchar_t)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(size_t)); // NOLINT
|
||||
#if GTEST_OS_LINUX || GTEST_OS_MAC || GTEST_OS_CYGWIN
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(wchar_t)); // NOLINT
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(size_t)); // NOLINT
|
||||
#if defined(GTEST_OS_LINUX) || defined(GTEST_OS_MAC) || defined(GTEST_OS_CYGWIN)
|
||||
// ssize_t is not defined on Windows and possibly some other OSes.
|
||||
EXPECT_EQ(kInteger, GMOCK_KIND_OF_(ssize_t)); // NOLINT
|
||||
#endif
|
||||
}
|
||||
|
||||
TEST(KindOfTest, FloatingPoint) {
|
||||
EXPECT_EQ(kFloatingPoint, GMOCK_KIND_OF_(float)); // NOLINT
|
||||
EXPECT_EQ(kFloatingPoint, GMOCK_KIND_OF_(double)); // NOLINT
|
||||
EXPECT_EQ(kFloatingPoint, GMOCK_KIND_OF_(float)); // NOLINT
|
||||
EXPECT_EQ(kFloatingPoint, GMOCK_KIND_OF_(double)); // NOLINT
|
||||
EXPECT_EQ(kFloatingPoint, GMOCK_KIND_OF_(long double)); // NOLINT
|
||||
}
|
||||
|
||||
TEST(KindOfTest, Other) {
|
||||
EXPECT_EQ(kOther, GMOCK_KIND_OF_(void*)); // NOLINT
|
||||
EXPECT_EQ(kOther, GMOCK_KIND_OF_(void*)); // NOLINT
|
||||
EXPECT_EQ(kOther, GMOCK_KIND_OF_(char**)); // NOLINT
|
||||
EXPECT_EQ(kOther, GMOCK_KIND_OF_(Base)); // NOLINT
|
||||
EXPECT_EQ(kOther, GMOCK_KIND_OF_(Base)); // NOLINT
|
||||
}
|
||||
|
||||
// Tests LosslessArithmeticConvertible<T, U>.
|
||||
@@ -209,26 +214,26 @@ TEST(LosslessArithmeticConvertibleTest, IntegerToInteger) {
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<unsigned char, int>::value));
|
||||
|
||||
// Unsigned => larger unsigned is fine.
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<
|
||||
unsigned short, uint64_t>::value)); // NOLINT
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<unsigned short,
|
||||
uint64_t>::value)); // NOLINT
|
||||
|
||||
// Signed => unsigned is not fine.
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<
|
||||
short, uint64_t>::value)); // NOLINT
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<
|
||||
signed char, unsigned int>::value)); // NOLINT
|
||||
EXPECT_FALSE(
|
||||
(LosslessArithmeticConvertible<short, uint64_t>::value)); // NOLINT
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<signed char,
|
||||
unsigned int>::value)); // NOLINT
|
||||
|
||||
// Same size and same signedness: fine too.
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<
|
||||
unsigned char, unsigned char>::value));
|
||||
EXPECT_TRUE(
|
||||
(LosslessArithmeticConvertible<unsigned char, unsigned char>::value));
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<int, int>::value));
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<wchar_t, wchar_t>::value));
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<
|
||||
unsigned long, unsigned long>::value)); // NOLINT
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<unsigned long,
|
||||
unsigned long>::value)); // NOLINT
|
||||
|
||||
// Same size, different signedness: not fine.
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<
|
||||
unsigned char, signed char>::value));
|
||||
EXPECT_FALSE(
|
||||
(LosslessArithmeticConvertible<unsigned char, signed char>::value));
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<int, unsigned int>::value));
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<uint64_t, int64_t>::value));
|
||||
|
||||
@@ -243,8 +248,8 @@ TEST(LosslessArithmeticConvertibleTest, IntegerToFloatingPoint) {
|
||||
// the format of the latter is implementation-defined.
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<char, float>::value));
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<int, double>::value));
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<
|
||||
short, long double>::value)); // NOLINT
|
||||
EXPECT_FALSE(
|
||||
(LosslessArithmeticConvertible<short, long double>::value)); // NOLINT
|
||||
}
|
||||
|
||||
TEST(LosslessArithmeticConvertibleTest, FloatingPointToBool) {
|
||||
@@ -272,7 +277,7 @@ TEST(LosslessArithmeticConvertibleTest, FloatingPointToFloatingPoint) {
|
||||
EXPECT_FALSE((LosslessArithmeticConvertible<double, float>::value));
|
||||
GTEST_INTENTIONAL_CONST_COND_PUSH_()
|
||||
if (sizeof(double) == sizeof(long double)) { // NOLINT
|
||||
GTEST_INTENTIONAL_CONST_COND_POP_()
|
||||
GTEST_INTENTIONAL_CONST_COND_POP_()
|
||||
// In some implementations (e.g. MSVC), double and long double
|
||||
// have the same size.
|
||||
EXPECT_TRUE((LosslessArithmeticConvertible<long double, double>::value));
|
||||
@@ -291,7 +296,7 @@ TEST(TupleMatchesTest, WorksForSize0) {
|
||||
}
|
||||
|
||||
TEST(TupleMatchesTest, WorksForSize1) {
|
||||
std::tuple<Matcher<int> > matchers(Eq(1));
|
||||
std::tuple<Matcher<int>> matchers(Eq(1));
|
||||
std::tuple<int> values1(1), values2(2);
|
||||
|
||||
EXPECT_TRUE(TupleMatches(matchers, values1));
|
||||
@@ -299,7 +304,7 @@ TEST(TupleMatchesTest, WorksForSize1) {
|
||||
}
|
||||
|
||||
TEST(TupleMatchesTest, WorksForSize2) {
|
||||
std::tuple<Matcher<int>, Matcher<char> > matchers(Eq(1), Eq('a'));
|
||||
std::tuple<Matcher<int>, Matcher<char>> matchers(Eq(1), Eq('a'));
|
||||
std::tuple<int, char> values1(1, 'a'), values2(1, 'b'), values3(2, 'a'),
|
||||
values4(2, 'b');
|
||||
|
||||
@@ -312,7 +317,7 @@ TEST(TupleMatchesTest, WorksForSize2) {
|
||||
TEST(TupleMatchesTest, WorksForSize5) {
|
||||
std::tuple<Matcher<int>, Matcher<char>, Matcher<bool>,
|
||||
Matcher<long>, // NOLINT
|
||||
Matcher<std::string> >
|
||||
Matcher<std::string>>
|
||||
matchers(Eq(1), Eq('a'), Eq(true), Eq(2L), Eq("hi"));
|
||||
std::tuple<int, char, bool, long, std::string> // NOLINT
|
||||
values1(1, 'a', true, 2L, "hi"), values2(1, 'a', true, 2L, "hello"),
|
||||
@@ -331,13 +336,10 @@ TEST(AssertTest, SucceedsOnTrue) {
|
||||
|
||||
// Tests that Assert(false, ...) generates a fatal failure.
|
||||
TEST(AssertTest, FailsFatallyOnFalse) {
|
||||
EXPECT_DEATH_IF_SUPPORTED({
|
||||
Assert(false, __FILE__, __LINE__, "This should fail.");
|
||||
}, "");
|
||||
EXPECT_DEATH_IF_SUPPORTED(
|
||||
{ Assert(false, __FILE__, __LINE__, "This should fail."); }, "");
|
||||
|
||||
EXPECT_DEATH_IF_SUPPORTED({
|
||||
Assert(false, __FILE__, __LINE__);
|
||||
}, "");
|
||||
EXPECT_DEATH_IF_SUPPORTED({ Assert(false, __FILE__, __LINE__); }, "");
|
||||
}
|
||||
|
||||
// Tests that Expect(true, ...) succeeds.
|
||||
@@ -348,40 +350,44 @@ TEST(ExpectTest, SucceedsOnTrue) {
|
||||
|
||||
// Tests that Expect(false, ...) generates a non-fatal failure.
|
||||
TEST(ExpectTest, FailsNonfatallyOnFalse) {
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Expect(false, __FILE__, __LINE__, "This should fail.");
|
||||
}, "This should fail");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
Expect(false, __FILE__, __LINE__, "This should fail.");
|
||||
},
|
||||
"This should fail");
|
||||
|
||||
EXPECT_NONFATAL_FAILURE({ // NOLINT
|
||||
Expect(false, __FILE__, __LINE__);
|
||||
}, "Expectation failed");
|
||||
EXPECT_NONFATAL_FAILURE(
|
||||
{ // NOLINT
|
||||
Expect(false, __FILE__, __LINE__);
|
||||
},
|
||||
"Expectation failed");
|
||||
}
|
||||
|
||||
// Tests LogIsVisible().
|
||||
|
||||
class LogIsVisibleTest : public ::testing::Test {
|
||||
protected:
|
||||
void SetUp() override { original_verbose_ = GMOCK_FLAG(verbose); }
|
||||
void SetUp() override { original_verbose_ = GMOCK_FLAG_GET(verbose); }
|
||||
|
||||
void TearDown() override { GMOCK_FLAG(verbose) = original_verbose_; }
|
||||
void TearDown() override { GMOCK_FLAG_SET(verbose, original_verbose_); }
|
||||
|
||||
std::string original_verbose_;
|
||||
};
|
||||
|
||||
TEST_F(LogIsVisibleTest, AlwaysReturnsTrueIfVerbosityIsInfo) {
|
||||
GMOCK_FLAG(verbose) = kInfoVerbosity;
|
||||
GMOCK_FLAG_SET(verbose, kInfoVerbosity);
|
||||
EXPECT_TRUE(LogIsVisible(kInfo));
|
||||
EXPECT_TRUE(LogIsVisible(kWarning));
|
||||
}
|
||||
|
||||
TEST_F(LogIsVisibleTest, AlwaysReturnsFalseIfVerbosityIsError) {
|
||||
GMOCK_FLAG(verbose) = kErrorVerbosity;
|
||||
GMOCK_FLAG_SET(verbose, kErrorVerbosity);
|
||||
EXPECT_FALSE(LogIsVisible(kInfo));
|
||||
EXPECT_FALSE(LogIsVisible(kWarning));
|
||||
}
|
||||
|
||||
TEST_F(LogIsVisibleTest, WorksWhenVerbosityIsWarning) {
|
||||
GMOCK_FLAG(verbose) = kWarningVerbosity;
|
||||
GMOCK_FLAG_SET(verbose, kWarningVerbosity);
|
||||
EXPECT_FALSE(LogIsVisible(kInfo));
|
||||
EXPECT_TRUE(LogIsVisible(kWarning));
|
||||
}
|
||||
@@ -394,31 +400,31 @@ TEST_F(LogIsVisibleTest, WorksWhenVerbosityIsWarning) {
|
||||
// and log severity.
|
||||
void TestLogWithSeverity(const std::string& verbosity, LogSeverity severity,
|
||||
bool should_print) {
|
||||
const std::string old_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = verbosity;
|
||||
const std::string old_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, verbosity);
|
||||
CaptureStdout();
|
||||
Log(severity, "Test log.\n", 0);
|
||||
if (should_print) {
|
||||
EXPECT_THAT(GetCapturedStdout().c_str(),
|
||||
ContainsRegex(
|
||||
severity == kWarning ?
|
||||
"^\nGMOCK WARNING:\nTest log\\.\nStack trace:\n" :
|
||||
"^\nTest log\\.\nStack trace:\n"));
|
||||
EXPECT_THAT(
|
||||
GetCapturedStdout().c_str(),
|
||||
ContainsRegex(severity == kWarning
|
||||
? "^\nGMOCK WARNING:\nTest log\\.\nStack trace:\n"
|
||||
: "^\nTest log\\.\nStack trace:\n"));
|
||||
} else {
|
||||
EXPECT_STREQ("", GetCapturedStdout().c_str());
|
||||
}
|
||||
GMOCK_FLAG(verbose) = old_flag;
|
||||
GMOCK_FLAG_SET(verbose, old_flag);
|
||||
}
|
||||
|
||||
// Tests that when the stack_frames_to_skip parameter is negative,
|
||||
// Log() doesn't include the stack trace in the output.
|
||||
TEST(LogTest, NoStackTraceWhenStackFramesToSkipIsNegative) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = kInfoVerbosity;
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, kInfoVerbosity);
|
||||
CaptureStdout();
|
||||
Log(kInfo, "Test log.\n", -1);
|
||||
EXPECT_STREQ("\nTest log.\n", GetCapturedStdout().c_str());
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
struct MockStackTraceGetter : testing::internal::OsStackTraceGetterInterface {
|
||||
@@ -440,7 +446,8 @@ TEST(LogTest, NoSkippingStackFrameInOptMode) {
|
||||
const std::string log = GetCapturedStdout();
|
||||
|
||||
std::string expected_trace =
|
||||
(testing::Message() << GTEST_FLAG(stack_trace_depth) << "::").GetString();
|
||||
(testing::Message() << GTEST_FLAG_GET(stack_trace_depth) << "::")
|
||||
.GetString();
|
||||
std::string expected_message =
|
||||
"\nGMOCK WARNING:\n"
|
||||
"Test log.\n"
|
||||
@@ -449,13 +456,13 @@ TEST(LogTest, NoSkippingStackFrameInOptMode) {
|
||||
EXPECT_THAT(log, HasSubstr(expected_message));
|
||||
int skip_count = atoi(log.substr(expected_message.size()).c_str());
|
||||
|
||||
# if defined(NDEBUG)
|
||||
#if defined(NDEBUG)
|
||||
// In opt mode, no stack frame should be skipped.
|
||||
const int expected_skip_count = 0;
|
||||
# else
|
||||
#else
|
||||
// In dbg mode, the stack frames should be skipped.
|
||||
const int expected_skip_count = 100;
|
||||
# endif
|
||||
#endif
|
||||
|
||||
// Note that each inner implementation layer will +1 the number to remove
|
||||
// itself from the trace. This means that the value is a little higher than
|
||||
@@ -497,12 +504,12 @@ TEST(LogTest, OnlyWarningsArePrintedWhenVerbosityIsInvalid) {
|
||||
|
||||
// Verifies that Log() behaves correctly for the given verbosity level
|
||||
// and log severity.
|
||||
std::string GrabOutput(void(*logger)(), const char* verbosity) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = verbosity;
|
||||
std::string GrabOutput(void (*logger)(), const char* verbosity) {
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, verbosity);
|
||||
CaptureStdout();
|
||||
logger();
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
return GetCapturedStdout();
|
||||
}
|
||||
|
||||
@@ -532,13 +539,13 @@ TEST(ExpectCallTest, DoesNotLogWhenVerbosityIsWarning) {
|
||||
|
||||
// Verifies that EXPECT_CALL doesn't log
|
||||
// if the --gmock_verbose flag is set to "error".
|
||||
TEST(ExpectCallTest, DoesNotLogWhenVerbosityIsError) {
|
||||
TEST(ExpectCallTest, DoesNotLogWhenVerbosityIsError) {
|
||||
EXPECT_STREQ("", GrabOutput(ExpectCallLogger, kErrorVerbosity).c_str());
|
||||
}
|
||||
|
||||
void OnCallLogger() {
|
||||
DummyMock mock;
|
||||
ON_CALL(mock, TestMethod());
|
||||
(void)ON_CALL(mock, TestMethod());
|
||||
}
|
||||
|
||||
// Verifies that ON_CALL logs if the --gmock_verbose flag is set to "info".
|
||||
@@ -561,7 +568,7 @@ TEST(OnCallTest, DoesNotLogWhenVerbosityIsError) {
|
||||
|
||||
void OnCallAnyArgumentLogger() {
|
||||
DummyMock mock;
|
||||
ON_CALL(mock, TestMethodArg(_));
|
||||
(void)ON_CALL(mock, TestMethodArg(_));
|
||||
}
|
||||
|
||||
// Verifies that ON_CALL prints provided _ argument.
|
||||
@@ -576,9 +583,9 @@ TEST(OnCallTest, LogsAnythingArgument) {
|
||||
|
||||
TEST(StlContainerViewTest, WorksForStlContainer) {
|
||||
StaticAssertTypeEq<std::vector<int>,
|
||||
StlContainerView<std::vector<int> >::type>();
|
||||
StlContainerView<std::vector<int>>::type>();
|
||||
StaticAssertTypeEq<const std::vector<double>&,
|
||||
StlContainerView<std::vector<double> >::const_reference>();
|
||||
StlContainerView<std::vector<double>>::const_reference>();
|
||||
|
||||
typedef std::vector<char> Chars;
|
||||
Chars v1;
|
||||
@@ -591,17 +598,16 @@ TEST(StlContainerViewTest, WorksForStlContainer) {
|
||||
}
|
||||
|
||||
TEST(StlContainerViewTest, WorksForStaticNativeArray) {
|
||||
StaticAssertTypeEq<NativeArray<int>,
|
||||
StlContainerView<int[3]>::type>();
|
||||
StaticAssertTypeEq<NativeArray<int>, StlContainerView<int[3]>::type>();
|
||||
StaticAssertTypeEq<NativeArray<double>,
|
||||
StlContainerView<const double[4]>::type>();
|
||||
StlContainerView<const double[4]>::type>();
|
||||
StaticAssertTypeEq<NativeArray<char[3]>,
|
||||
StlContainerView<const char[2][3]>::type>();
|
||||
StlContainerView<const char[2][3]>::type>();
|
||||
|
||||
StaticAssertTypeEq<const NativeArray<int>,
|
||||
StlContainerView<int[2]>::const_reference>();
|
||||
StlContainerView<int[2]>::const_reference>();
|
||||
|
||||
int a1[3] = { 0, 1, 2 };
|
||||
int a1[3] = {0, 1, 2};
|
||||
NativeArray<int> a2 = StlContainerView<int[3]>::ConstReference(a1);
|
||||
EXPECT_EQ(3U, a2.size());
|
||||
EXPECT_EQ(a1, a2.begin());
|
||||
@@ -619,24 +625,24 @@ TEST(StlContainerViewTest, WorksForStaticNativeArray) {
|
||||
|
||||
TEST(StlContainerViewTest, WorksForDynamicNativeArray) {
|
||||
StaticAssertTypeEq<NativeArray<int>,
|
||||
StlContainerView<std::tuple<const int*, size_t> >::type>();
|
||||
StlContainerView<std::tuple<const int*, size_t>>::type>();
|
||||
StaticAssertTypeEq<
|
||||
NativeArray<double>,
|
||||
StlContainerView<std::tuple<std::shared_ptr<double>, int> >::type>();
|
||||
StlContainerView<std::tuple<std::shared_ptr<double>, int>>::type>();
|
||||
|
||||
StaticAssertTypeEq<
|
||||
const NativeArray<int>,
|
||||
StlContainerView<std::tuple<const int*, int> >::const_reference>();
|
||||
StlContainerView<std::tuple<const int*, int>>::const_reference>();
|
||||
|
||||
int a1[3] = { 0, 1, 2 };
|
||||
int a1[3] = {0, 1, 2};
|
||||
const int* const p1 = a1;
|
||||
NativeArray<int> a2 =
|
||||
StlContainerView<std::tuple<const int*, int> >::ConstReference(
|
||||
StlContainerView<std::tuple<const int*, int>>::ConstReference(
|
||||
std::make_tuple(p1, 3));
|
||||
EXPECT_EQ(3U, a2.size());
|
||||
EXPECT_EQ(a1, a2.begin());
|
||||
|
||||
const NativeArray<int> a3 = StlContainerView<std::tuple<int*, size_t> >::Copy(
|
||||
const NativeArray<int> a3 = StlContainerView<std::tuple<int*, size_t>>::Copy(
|
||||
std::make_tuple(static_cast<int*>(a1), 3));
|
||||
ASSERT_EQ(3U, a3.size());
|
||||
EXPECT_EQ(0, a3.begin()[0]);
|
||||
@@ -715,6 +721,46 @@ TEST(FunctionTest, LongArgumentList) {
|
||||
F::MakeResultIgnoredValue>::value));
|
||||
}
|
||||
|
||||
TEST(Base64Unescape, InvalidString) {
|
||||
std::string unescaped;
|
||||
EXPECT_FALSE(Base64Unescape("(invalid)", &unescaped));
|
||||
}
|
||||
|
||||
TEST(Base64Unescape, ShortString) {
|
||||
std::string unescaped;
|
||||
EXPECT_TRUE(Base64Unescape("SGVsbG8gd29ybGQh", &unescaped));
|
||||
EXPECT_EQ("Hello world!", unescaped);
|
||||
}
|
||||
|
||||
TEST(Base64Unescape, ShortStringWithPadding) {
|
||||
std::string unescaped;
|
||||
EXPECT_TRUE(Base64Unescape("SGVsbG8gd29ybGQ=", &unescaped));
|
||||
EXPECT_EQ("Hello world", unescaped);
|
||||
}
|
||||
|
||||
TEST(Base64Unescape, ShortStringWithoutPadding) {
|
||||
std::string unescaped;
|
||||
EXPECT_TRUE(Base64Unescape("SGVsbG8gd29ybGQ", &unescaped));
|
||||
EXPECT_EQ("Hello world", unescaped);
|
||||
}
|
||||
|
||||
TEST(Base64Unescape, LongStringWithWhiteSpaces) {
|
||||
std::string escaped =
|
||||
R"(TWFuIGlzIGRpc3Rpbmd1aXNoZWQsIG5vdCBvbmx5IGJ5IGhpcyByZWFzb24sIGJ1dCBieSB0aGlz
|
||||
IHNpbmd1bGFyIHBhc3Npb24gZnJvbSBvdGhlciBhbmltYWxzLCB3aGljaCBpcyBhIGx1c3Qgb2Yg
|
||||
dGhlIG1pbmQsIHRoYXQgYnkgYSBwZXJzZXZlcmFuY2Ugb2YgZGVsaWdodCBpbiB0aGUgY29udGlu
|
||||
dWVkIGFuZCBpbmRlZmF0aWdhYmxlIGdlbmVyYXRpb24gb2Yga25vd2xlZGdlLCBleGNlZWRzIHRo
|
||||
ZSBzaG9ydCB2ZWhlbWVuY2Ugb2YgYW55IGNhcm5hbCBwbGVhc3VyZS4=)";
|
||||
std::string expected =
|
||||
"Man is distinguished, not only by his reason, but by this singular "
|
||||
"passion from other animals, which is a lust of the mind, that by a "
|
||||
"perseverance of delight in the continued and indefatigable generation "
|
||||
"of knowledge, exceeds the short vehemence of any carnal pleasure.";
|
||||
std::string unescaped;
|
||||
EXPECT_TRUE(Base64Unescape(escaped, &unescaped));
|
||||
EXPECT_EQ(expected, unescaped);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
} // namespace internal
|
||||
} // namespace testing
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,191 @@
|
||||
// Copyright 2007, Google Inc.
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following disclaimer
|
||||
// in the documentation and/or other materials provided with the
|
||||
// distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived from
|
||||
// this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests some commonly used argument matchers.
|
||||
|
||||
#ifndef GOOGLEMOCK_TEST_GMOCK_MATCHERS_TEST_H_
|
||||
#define GOOGLEMOCK_TEST_GMOCK_MATCHERS_TEST_H_
|
||||
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include <array>
|
||||
#include <cstdint>
|
||||
#include <deque>
|
||||
#include <forward_list>
|
||||
#include <functional>
|
||||
#include <iostream>
|
||||
#include <iterator>
|
||||
#include <limits>
|
||||
#include <list>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <set>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <type_traits>
|
||||
#include <unordered_map>
|
||||
#include <unordered_set>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/gmock-matchers.h"
|
||||
#include "gmock/gmock-more-matchers.h"
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest-spi.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
namespace testing {
|
||||
namespace gmock_matchers_test {
|
||||
|
||||
using std::greater;
|
||||
using std::less;
|
||||
using std::list;
|
||||
using std::make_pair;
|
||||
using std::map;
|
||||
using std::multimap;
|
||||
using std::multiset;
|
||||
using std::ostream;
|
||||
using std::pair;
|
||||
using std::set;
|
||||
using std::stringstream;
|
||||
using std::vector;
|
||||
using testing::internal::DummyMatchResultListener;
|
||||
using testing::internal::ElementMatcherPair;
|
||||
using testing::internal::ElementMatcherPairs;
|
||||
using testing::internal::ElementsAreArrayMatcher;
|
||||
using testing::internal::ExplainMatchFailureTupleTo;
|
||||
using testing::internal::FloatingEqMatcher;
|
||||
using testing::internal::FormatMatcherDescription;
|
||||
using testing::internal::IsReadableTypeName;
|
||||
using testing::internal::MatchMatrix;
|
||||
using testing::internal::PredicateFormatterFromMatcher;
|
||||
using testing::internal::RE;
|
||||
using testing::internal::StreamMatchResultListener;
|
||||
using testing::internal::Strings;
|
||||
|
||||
// Helper for testing container-valued matchers in mock method context. It is
|
||||
// important to test matchers in this context, since it requires additional type
|
||||
// deduction beyond what EXPECT_THAT does, thus making it more restrictive.
|
||||
struct ContainerHelper {
|
||||
MOCK_METHOD1(Call, void(std::vector<std::unique_ptr<int>>));
|
||||
};
|
||||
|
||||
// For testing ExplainMatchResultTo().
|
||||
template <typename T>
|
||||
struct GtestGreaterThanMatcher {
|
||||
using is_gtest_matcher = void;
|
||||
|
||||
void DescribeTo(ostream* os) const { *os << "is > " << rhs; }
|
||||
void DescribeNegationTo(ostream* os) const { *os << "is <= " << rhs; }
|
||||
|
||||
bool MatchAndExplain(T lhs, MatchResultListener* listener) const {
|
||||
if (lhs > rhs) {
|
||||
*listener << "which is " << (lhs - rhs) << " more than " << rhs;
|
||||
} else if (lhs == rhs) {
|
||||
*listener << "which is the same as " << rhs;
|
||||
} else {
|
||||
*listener << "which is " << (rhs - lhs) << " less than " << rhs;
|
||||
}
|
||||
|
||||
return lhs > rhs;
|
||||
}
|
||||
|
||||
T rhs;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
GtestGreaterThanMatcher<std::decay_t<T>> GtestGreaterThan(T&& rhs) {
|
||||
return {rhs};
|
||||
}
|
||||
|
||||
// As the matcher above, but using the base class with virtual functions.
|
||||
template <typename T>
|
||||
class GreaterThanMatcher : public MatcherInterface<T> {
|
||||
public:
|
||||
explicit GreaterThanMatcher(T rhs) : impl_{rhs} {}
|
||||
|
||||
void DescribeTo(ostream* os) const override { impl_.DescribeTo(os); }
|
||||
void DescribeNegationTo(ostream* os) const override {
|
||||
impl_.DescribeNegationTo(os);
|
||||
}
|
||||
|
||||
bool MatchAndExplain(T lhs, MatchResultListener* listener) const override {
|
||||
return impl_.MatchAndExplain(lhs, listener);
|
||||
}
|
||||
|
||||
private:
|
||||
const GtestGreaterThanMatcher<T> impl_;
|
||||
};
|
||||
|
||||
// Names and instantiates a new instance of GTestMatcherTestP.
|
||||
#define INSTANTIATE_GTEST_MATCHER_TEST_P(TestSuite) \
|
||||
using TestSuite##P = GTestMatcherTestP; \
|
||||
INSTANTIATE_TEST_SUITE_P(MatcherInterface, TestSuite##P, Values(false)); \
|
||||
INSTANTIATE_TEST_SUITE_P(GtestMatcher, TestSuite##P, Values(true))
|
||||
|
||||
class GTestMatcherTestP : public testing::TestWithParam<bool> {
|
||||
public:
|
||||
template <typename T>
|
||||
Matcher<T> GreaterThan(T n) {
|
||||
if (use_gtest_matcher_) {
|
||||
return GtestGreaterThan(n);
|
||||
} else {
|
||||
return MakeMatcher(new GreaterThanMatcher<T>(n));
|
||||
}
|
||||
}
|
||||
const bool use_gtest_matcher_ = GetParam();
|
||||
};
|
||||
|
||||
// Returns the description of the given matcher.
|
||||
template <typename T>
|
||||
std::string Describe(const Matcher<T>& m) {
|
||||
return DescribeMatcher<T>(m);
|
||||
}
|
||||
|
||||
// Returns the description of the negation of the given matcher.
|
||||
template <typename T>
|
||||
std::string DescribeNegation(const Matcher<T>& m) {
|
||||
return DescribeMatcher<T>(m, true);
|
||||
}
|
||||
|
||||
// Returns the reason why x matches, or doesn't match, m.
|
||||
template <typename MatcherType, typename Value>
|
||||
std::string Explain(const MatcherType& m, const Value& x) {
|
||||
StringMatchResultListener listener;
|
||||
ExplainMatchResult(m, x, &listener);
|
||||
return listener.str();
|
||||
}
|
||||
|
||||
} // namespace gmock_matchers_test
|
||||
} // namespace testing
|
||||
|
||||
#endif // GOOGLEMOCK_TEST_GMOCK_MATCHERS_TEST_H_
|
||||
@@ -31,22 +31,23 @@
|
||||
//
|
||||
// This file tests the built-in actions in gmock-actions.h.
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable : 4577)
|
||||
#endif
|
||||
|
||||
#include "gmock/gmock-more-actions.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <functional>
|
||||
#include <iterator>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <tuple>
|
||||
#include <vector>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest-spi.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4577)
|
||||
|
||||
namespace testing {
|
||||
namespace gmock_more_actions_test {
|
||||
|
||||
@@ -58,6 +59,7 @@ using testing::Invoke;
|
||||
using testing::ReturnArg;
|
||||
using testing::ReturnPointee;
|
||||
using testing::SaveArg;
|
||||
using testing::SaveArgByMove;
|
||||
using testing::SaveArgPointee;
|
||||
using testing::SetArgReferee;
|
||||
using testing::Unused;
|
||||
@@ -84,6 +86,16 @@ struct UnaryFunctor {
|
||||
int operator()(bool x) { return x ? 1 : -1; }
|
||||
};
|
||||
|
||||
struct UnaryMoveOnlyFunctor : UnaryFunctor {
|
||||
UnaryMoveOnlyFunctor() = default;
|
||||
UnaryMoveOnlyFunctor(const UnaryMoveOnlyFunctor&) = delete;
|
||||
UnaryMoveOnlyFunctor(UnaryMoveOnlyFunctor&&) = default;
|
||||
};
|
||||
|
||||
struct OneShotUnaryFunctor {
|
||||
int operator()(bool x) && { return x ? 1 : -1; }
|
||||
};
|
||||
|
||||
const char* Binary(const char* input, short n) { return input + n; } // NOLINT
|
||||
|
||||
int Ternary(int x, char y, short z) { return x + y + z; } // NOLINT
|
||||
@@ -145,7 +157,7 @@ class Foo {
|
||||
|
||||
std::string Binary(const std::string& str, char c) const { return str + c; }
|
||||
|
||||
int Ternary(int x, bool y, char z) { return value_ + x + y*z; }
|
||||
int Ternary(int x, bool y, char z) { return value_ + x + y * z; }
|
||||
|
||||
int SumOf4(int a, int b, int c, int d) const {
|
||||
return a + b + c + d + value_;
|
||||
@@ -190,45 +202,45 @@ class Foo {
|
||||
|
||||
// Tests using Invoke() with a nullary function.
|
||||
TEST(InvokeTest, Nullary) {
|
||||
Action<int()> a = Invoke(Nullary); // NOLINT
|
||||
Action<int()> a = &Nullary;
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple()));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a unary function.
|
||||
TEST(InvokeTest, Unary) {
|
||||
Action<bool(int)> a = Invoke(Unary); // NOLINT
|
||||
Action<bool(int)> a = &Unary;
|
||||
EXPECT_FALSE(a.Perform(std::make_tuple(1)));
|
||||
EXPECT_TRUE(a.Perform(std::make_tuple(-1)));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a binary function.
|
||||
TEST(InvokeTest, Binary) {
|
||||
Action<const char*(const char*, short)> a = Invoke(Binary); // NOLINT
|
||||
Action<const char*(const char*, short)> a = &Binary; // NOLINT
|
||||
const char* p = "Hello";
|
||||
EXPECT_EQ(p + 2, a.Perform(std::make_tuple(p, Short(2))));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a ternary function.
|
||||
TEST(InvokeTest, Ternary) {
|
||||
Action<int(int, char, short)> a = Invoke(Ternary); // NOLINT
|
||||
Action<int(int, char, short)> a = &Ternary; // NOLINT
|
||||
EXPECT_EQ(6, a.Perform(std::make_tuple(1, '\2', Short(3))));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a 4-argument function.
|
||||
TEST(InvokeTest, FunctionThatTakes4Arguments) {
|
||||
Action<int(int, int, int, int)> a = Invoke(SumOf4); // NOLINT
|
||||
Action<int(int, int, int, int)> a = &SumOf4;
|
||||
EXPECT_EQ(1234, a.Perform(std::make_tuple(1000, 200, 30, 4)));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a 5-argument function.
|
||||
TEST(InvokeTest, FunctionThatTakes5Arguments) {
|
||||
Action<int(int, int, int, int, int)> a = Invoke(SumOf5); // NOLINT
|
||||
Action<int(int, int, int, int, int)> a = &SumOf5;
|
||||
EXPECT_EQ(12345, a.Perform(std::make_tuple(10000, 2000, 300, 40, 5)));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a 6-argument function.
|
||||
TEST(InvokeTest, FunctionThatTakes6Arguments) {
|
||||
Action<int(int, int, int, int, int, int)> a = Invoke(SumOf6); // NOLINT
|
||||
Action<int(int, int, int, int, int, int)> a = &SumOf6;
|
||||
EXPECT_EQ(123456,
|
||||
a.Perform(std::make_tuple(100000, 20000, 3000, 400, 50, 6)));
|
||||
}
|
||||
@@ -241,7 +253,7 @@ inline const char* CharPtr(const char* s) { return s; }
|
||||
TEST(InvokeTest, FunctionThatTakes7Arguments) {
|
||||
Action<std::string(const char*, const char*, const char*, const char*,
|
||||
const char*, const char*, const char*)>
|
||||
a = Invoke(Concat7);
|
||||
a = &Concat7;
|
||||
EXPECT_EQ("1234567",
|
||||
a.Perform(std::make_tuple(CharPtr("1"), CharPtr("2"), CharPtr("3"),
|
||||
CharPtr("4"), CharPtr("5"), CharPtr("6"),
|
||||
@@ -252,7 +264,7 @@ TEST(InvokeTest, FunctionThatTakes7Arguments) {
|
||||
TEST(InvokeTest, FunctionThatTakes8Arguments) {
|
||||
Action<std::string(const char*, const char*, const char*, const char*,
|
||||
const char*, const char*, const char*, const char*)>
|
||||
a = Invoke(Concat8);
|
||||
a = &Concat8;
|
||||
EXPECT_EQ("12345678",
|
||||
a.Perform(std::make_tuple(CharPtr("1"), CharPtr("2"), CharPtr("3"),
|
||||
CharPtr("4"), CharPtr("5"), CharPtr("6"),
|
||||
@@ -264,7 +276,7 @@ TEST(InvokeTest, FunctionThatTakes9Arguments) {
|
||||
Action<std::string(const char*, const char*, const char*, const char*,
|
||||
const char*, const char*, const char*, const char*,
|
||||
const char*)>
|
||||
a = Invoke(Concat9);
|
||||
a = &Concat9;
|
||||
EXPECT_EQ("123456789", a.Perform(std::make_tuple(
|
||||
CharPtr("1"), CharPtr("2"), CharPtr("3"),
|
||||
CharPtr("4"), CharPtr("5"), CharPtr("6"),
|
||||
@@ -276,7 +288,7 @@ TEST(InvokeTest, FunctionThatTakes10Arguments) {
|
||||
Action<std::string(const char*, const char*, const char*, const char*,
|
||||
const char*, const char*, const char*, const char*,
|
||||
const char*, const char*)>
|
||||
a = Invoke(Concat10);
|
||||
a = &Concat10;
|
||||
EXPECT_EQ("1234567890",
|
||||
a.Perform(std::make_tuple(CharPtr("1"), CharPtr("2"), CharPtr("3"),
|
||||
CharPtr("4"), CharPtr("5"), CharPtr("6"),
|
||||
@@ -286,13 +298,12 @@ TEST(InvokeTest, FunctionThatTakes10Arguments) {
|
||||
|
||||
// Tests using Invoke() with functions with parameters declared as Unused.
|
||||
TEST(InvokeTest, FunctionWithUnusedParameters) {
|
||||
Action<int(int, int, double, const std::string&)> a1 = Invoke(SumOfFirst2);
|
||||
Action<int(int, int, double, const std::string&)> a1 = &SumOfFirst2;
|
||||
std::tuple<int, int, double, std::string> dummy =
|
||||
std::make_tuple(10, 2, 5.6, std::string("hi"));
|
||||
EXPECT_EQ(12, a1.Perform(dummy));
|
||||
|
||||
Action<int(int, int, bool, int*)> a2 =
|
||||
Invoke(SumOfFirst2);
|
||||
Action<int(int, int, bool, int*)> a2 = &SumOfFirst2;
|
||||
EXPECT_EQ(
|
||||
23, a2.Perform(std::make_tuple(20, 3, true, static_cast<int*>(nullptr))));
|
||||
}
|
||||
@@ -303,20 +314,19 @@ TEST(InvokeTest, MethodWithUnusedParameters) {
|
||||
Action<int(std::string, bool, int, int)> a1 = Invoke(&foo, &Foo::SumOfLast2);
|
||||
EXPECT_EQ(12, a1.Perform(std::make_tuple(CharPtr("hi"), true, 10, 2)));
|
||||
|
||||
Action<int(char, double, int, int)> a2 =
|
||||
Invoke(&foo, &Foo::SumOfLast2);
|
||||
Action<int(char, double, int, int)> a2 = Invoke(&foo, &Foo::SumOfLast2);
|
||||
EXPECT_EQ(23, a2.Perform(std::make_tuple('a', 2.5, 20, 3)));
|
||||
}
|
||||
|
||||
// Tests using Invoke() with a functor.
|
||||
TEST(InvokeTest, Functor) {
|
||||
Action<long(long, int)> a = Invoke(plus<long>()); // NOLINT
|
||||
Action<long(long, int)> a = plus<long>(); // NOLINT
|
||||
EXPECT_EQ(3L, a.Perform(std::make_tuple(1, 2)));
|
||||
}
|
||||
|
||||
// Tests using Invoke(f) as an action of a compatible type.
|
||||
TEST(InvokeTest, FunctionWithCompatibleType) {
|
||||
Action<long(int, short, char, bool)> a = Invoke(SumOf4); // NOLINT
|
||||
Action<long(int, short, char, bool)> a = &SumOf4; // NOLINT
|
||||
EXPECT_EQ(4321, a.Perform(std::make_tuple(4000, Short(300), Char(20), true)));
|
||||
}
|
||||
|
||||
@@ -362,7 +372,8 @@ TEST(InvokeMethodTest, MethodThatTakes4Arguments) {
|
||||
// Tests using Invoke() with a 5-argument method.
|
||||
TEST(InvokeMethodTest, MethodThatTakes5Arguments) {
|
||||
Foo foo;
|
||||
Action<int(int, int, int, int, int)> a = Invoke(&foo, &Foo::SumOf5); // NOLINT
|
||||
Action<int(int, int, int, int, int)> a =
|
||||
Invoke(&foo, &Foo::SumOf5); // NOLINT
|
||||
EXPECT_EQ(12345, a.Perform(std::make_tuple(10000, 2000, 300, 40, 5)));
|
||||
}
|
||||
|
||||
@@ -436,13 +447,13 @@ TEST(InvokeMethodTest, MethodWithCompatibleType) {
|
||||
|
||||
// Tests using WithoutArgs with an action that takes no argument.
|
||||
TEST(WithoutArgsTest, NoArg) {
|
||||
Action<int(int n)> a = WithoutArgs(Invoke(Nullary)); // NOLINT
|
||||
Action<int(int n)> a = WithoutArgs(&Nullary); // NOLINT
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple(2)));
|
||||
}
|
||||
|
||||
// Tests using WithArg with an action that takes 1 argument.
|
||||
TEST(WithArgTest, OneArg) {
|
||||
Action<bool(double x, int n)> b = WithArg<1>(Invoke(Unary)); // NOLINT
|
||||
Action<bool(double x, int n)> b = WithArg<1>(&Unary); // NOLINT
|
||||
EXPECT_TRUE(b.Perform(std::make_tuple(1.5, -1)));
|
||||
EXPECT_FALSE(b.Perform(std::make_tuple(1.5, 1)));
|
||||
}
|
||||
@@ -462,6 +473,12 @@ TEST(ReturnArgActionTest, WorksForMultiArgStringArg2) {
|
||||
EXPECT_EQ("seven", a.Perform(std::make_tuple(5, 6, std::string("seven"), 8)));
|
||||
}
|
||||
|
||||
TEST(ReturnArgActionTest, WorksForNonConstRefArg0) {
|
||||
const Action<std::string&(std::string&)> a = ReturnArg<0>();
|
||||
std::string s = "12345";
|
||||
EXPECT_EQ(&s, &a.Perform(std::forward_as_tuple(s)));
|
||||
}
|
||||
|
||||
TEST(SaveArgActionTest, WorksForSameType) {
|
||||
int result = 0;
|
||||
const Action<void(int n)> a1 = SaveArg<0>(&result);
|
||||
@@ -476,6 +493,34 @@ TEST(SaveArgActionTest, WorksForCompatibleType) {
|
||||
EXPECT_EQ('a', result);
|
||||
}
|
||||
|
||||
struct MoveOnly {
|
||||
explicit MoveOnly(int v) : i(v) {}
|
||||
MoveOnly(MoveOnly&& o) {
|
||||
i = o.i;
|
||||
o.i = -1;
|
||||
}
|
||||
MoveOnly& operator=(MoveOnly&& o) {
|
||||
i = o.i;
|
||||
o.i = -1;
|
||||
return *this;
|
||||
}
|
||||
int i;
|
||||
};
|
||||
|
||||
TEST(SaveArgByMoveActionTest, WorksForSameType) {
|
||||
MoveOnly result{0};
|
||||
const Action<void(MoveOnly v)> a1 = SaveArgByMove<0>(&result);
|
||||
a1.Perform(std::make_tuple(MoveOnly{5}));
|
||||
EXPECT_EQ(5, result.i);
|
||||
}
|
||||
|
||||
TEST(SaveArgByMoveActionTest, WorksForCompatibleType) {
|
||||
MoveOnly result{0};
|
||||
const Action<void(bool, MoveOnly)> a1 = SaveArgByMove<1>(&result);
|
||||
a1.Perform(std::make_tuple(true, MoveOnly{7}));
|
||||
EXPECT_EQ(7, result.i);
|
||||
}
|
||||
|
||||
TEST(SaveArgPointeeActionTest, WorksForSameType) {
|
||||
int result = 0;
|
||||
const int value = 5;
|
||||
@@ -517,15 +562,12 @@ TEST(SetArgRefereeActionTest, WorksWithExtraArguments) {
|
||||
// the bool provided to the constructor to true when destroyed.
|
||||
class DeletionTester {
|
||||
public:
|
||||
explicit DeletionTester(bool* is_deleted)
|
||||
: is_deleted_(is_deleted) {
|
||||
explicit DeletionTester(bool* is_deleted) : is_deleted_(is_deleted) {
|
||||
// Make sure the bit is set to false.
|
||||
*is_deleted_ = false;
|
||||
}
|
||||
|
||||
~DeletionTester() {
|
||||
*is_deleted_ = true;
|
||||
}
|
||||
~DeletionTester() { *is_deleted_ = true; }
|
||||
|
||||
private:
|
||||
bool* is_deleted_;
|
||||
@@ -534,7 +576,7 @@ class DeletionTester {
|
||||
TEST(DeleteArgActionTest, OneArg) {
|
||||
bool is_deleted = false;
|
||||
DeletionTester* t = new DeletionTester(&is_deleted);
|
||||
const Action<void(DeletionTester*)> a1 = DeleteArg<0>(); // NOLINT
|
||||
const Action<void(DeletionTester*)> a1 = DeleteArg<0>(); // NOLINT
|
||||
EXPECT_FALSE(is_deleted);
|
||||
a1.Perform(std::make_tuple(t));
|
||||
EXPECT_TRUE(is_deleted);
|
||||
@@ -543,8 +585,9 @@ TEST(DeleteArgActionTest, OneArg) {
|
||||
TEST(DeleteArgActionTest, TenArgs) {
|
||||
bool is_deleted = false;
|
||||
DeletionTester* t = new DeletionTester(&is_deleted);
|
||||
const Action<void(bool, int, int, const char*, bool,
|
||||
int, int, int, int, DeletionTester*)> a1 = DeleteArg<9>();
|
||||
const Action<void(bool, int, int, const char*, bool, int, int, int, int,
|
||||
DeletionTester*)>
|
||||
a1 = DeleteArg<9>();
|
||||
EXPECT_FALSE(is_deleted);
|
||||
a1.Perform(std::make_tuple(true, 5, 6, CharPtr("hi"), false, 7, 8, 9, 10, t));
|
||||
EXPECT_TRUE(is_deleted);
|
||||
@@ -571,13 +614,13 @@ TEST(ThrowActionTest, ThrowsGivenExceptionInNullaryFunction) {
|
||||
|
||||
class Object {
|
||||
public:
|
||||
virtual ~Object() {}
|
||||
virtual ~Object() = default;
|
||||
virtual void Func() {}
|
||||
};
|
||||
|
||||
class MockObject : public Object {
|
||||
public:
|
||||
~MockObject() override {}
|
||||
~MockObject() override = default;
|
||||
MOCK_METHOD(void, Func, (), (override));
|
||||
};
|
||||
|
||||
@@ -602,7 +645,7 @@ TEST(ThrowActionTest, Times0) {
|
||||
// pointed to by the N-th (0-based) argument to values in range [first, last).
|
||||
TEST(SetArrayArgumentTest, SetsTheNthArray) {
|
||||
using MyFunction = void(bool, int*, char*);
|
||||
int numbers[] = { 1, 2, 3 };
|
||||
int numbers[] = {1, 2, 3};
|
||||
Action<MyFunction> a = SetArrayArgument<1>(numbers, numbers + 3);
|
||||
|
||||
int n[4] = {};
|
||||
@@ -638,7 +681,7 @@ TEST(SetArrayArgumentTest, SetsTheNthArray) {
|
||||
// Tests SetArrayArgument<N>(first, last) where first == last.
|
||||
TEST(SetArrayArgumentTest, SetsTheNthArrayWithEmptyRange) {
|
||||
using MyFunction = void(bool, int*);
|
||||
int numbers[] = { 1, 2, 3 };
|
||||
int numbers[] = {1, 2, 3};
|
||||
Action<MyFunction> a = SetArrayArgument<1>(numbers, numbers);
|
||||
|
||||
int n[4] = {};
|
||||
@@ -654,10 +697,10 @@ TEST(SetArrayArgumentTest, SetsTheNthArrayWithEmptyRange) {
|
||||
// (but not equal) to the argument type.
|
||||
TEST(SetArrayArgumentTest, SetsTheNthArrayWithConvertibleType) {
|
||||
using MyFunction = void(bool, int*);
|
||||
char chars[] = { 97, 98, 99 };
|
||||
char chars[] = {97, 98, 99};
|
||||
Action<MyFunction> a = SetArrayArgument<1>(chars, chars + 3);
|
||||
|
||||
int codes[4] = { 111, 222, 333, 444 };
|
||||
int codes[4] = {111, 222, 333, 444};
|
||||
int* pcodes = codes;
|
||||
a.Perform(std::make_tuple(true, pcodes));
|
||||
EXPECT_EQ(97, codes[0]);
|
||||
@@ -673,7 +716,7 @@ TEST(SetArrayArgumentTest, SetsTheNthArrayWithIteratorArgument) {
|
||||
Action<MyFunction> a = SetArrayArgument<1>(letters.begin(), letters.end());
|
||||
|
||||
std::string s;
|
||||
a.Perform(std::make_tuple(true, back_inserter(s)));
|
||||
a.Perform(std::make_tuple(true, std::back_inserter(s)));
|
||||
EXPECT_EQ(letters, s);
|
||||
}
|
||||
|
||||
@@ -694,12 +737,24 @@ TEST(InvokeArgumentTest, Function0) {
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple(2, &Nullary)));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a unary function.
|
||||
// Tests using InvokeArgument with a unary functor.
|
||||
TEST(InvokeArgumentTest, Functor1) {
|
||||
Action<int(UnaryFunctor)> a = InvokeArgument<0>(true); // NOLINT
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple(UnaryFunctor())));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a unary move-only functor.
|
||||
TEST(InvokeArgumentTest, Functor1MoveOnly) {
|
||||
Action<int(UnaryMoveOnlyFunctor)> a = InvokeArgument<0>(true); // NOLINT
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple(UnaryMoveOnlyFunctor())));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a one-shot unary functor.
|
||||
TEST(InvokeArgumentTest, OneShotFunctor1) {
|
||||
Action<int(OneShotUnaryFunctor)> a = InvokeArgument<0>(true); // NOLINT
|
||||
EXPECT_EQ(1, a.Perform(std::make_tuple(OneShotUnaryFunctor())));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a 5-ary function.
|
||||
TEST(InvokeArgumentTest, Function5) {
|
||||
Action<int(int (*)(int, int, int, int, int))> a = // NOLINT
|
||||
@@ -730,34 +785,34 @@ TEST(InvokeArgumentTest, Functor6) {
|
||||
|
||||
// Tests using InvokeArgument with a 7-ary function.
|
||||
TEST(InvokeArgumentTest, Function7) {
|
||||
Action<std::string(std::string(*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*))>
|
||||
Action<std::string(std::string (*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*))>
|
||||
a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7");
|
||||
EXPECT_EQ("1234567", a.Perform(std::make_tuple(&Concat7)));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a 8-ary function.
|
||||
TEST(InvokeArgumentTest, Function8) {
|
||||
Action<std::string(std::string(*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*, const char*))>
|
||||
Action<std::string(std::string (*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*, const char*))>
|
||||
a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8");
|
||||
EXPECT_EQ("12345678", a.Perform(std::make_tuple(&Concat8)));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a 9-ary function.
|
||||
TEST(InvokeArgumentTest, Function9) {
|
||||
Action<std::string(std::string(*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*, const char*, const char*))>
|
||||
Action<std::string(std::string (*)(const char*, const char*, const char*,
|
||||
const char*, const char*, const char*,
|
||||
const char*, const char*, const char*))>
|
||||
a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8", "9");
|
||||
EXPECT_EQ("123456789", a.Perform(std::make_tuple(&Concat9)));
|
||||
}
|
||||
|
||||
// Tests using InvokeArgument with a 10-ary function.
|
||||
TEST(InvokeArgumentTest, Function10) {
|
||||
Action<std::string(std::string(*)(
|
||||
Action<std::string(std::string (*)(
|
||||
const char*, const char*, const char*, const char*, const char*,
|
||||
const char*, const char*, const char*, const char*, const char*))>
|
||||
a = InvokeArgument<0>("1", "2", "3", "4", "5", "6", "7", "8", "9", "0");
|
||||
@@ -802,6 +857,22 @@ TEST(InvokeArgumentTest, ByExplicitConstReferenceFunction) {
|
||||
EXPECT_FALSE(a.Perform(std::make_tuple(&ReferencesGlobalDouble)));
|
||||
}
|
||||
|
||||
TEST(InvokeArgumentTest, MoveOnlyType) {
|
||||
struct Marker {};
|
||||
struct {
|
||||
// Method takes a unique_ptr (to a type we don't care about), and an
|
||||
// invocable type.
|
||||
MOCK_METHOD(bool, MockMethod,
|
||||
(std::unique_ptr<Marker>, std::function<int()>), ());
|
||||
} mock;
|
||||
|
||||
ON_CALL(mock, MockMethod(_, _)).WillByDefault(InvokeArgument<1>());
|
||||
|
||||
// This compiles, but is a little opaque as a workaround:
|
||||
ON_CALL(mock, MockMethod(_, _))
|
||||
.WillByDefault(WithArg<1>(InvokeArgument<0>()));
|
||||
}
|
||||
|
||||
// Tests DoAll(a1, a2).
|
||||
TEST(DoAllTest, TwoActions) {
|
||||
int n = 0;
|
||||
@@ -955,9 +1026,8 @@ TEST(DoAllTest, NoArgs) {
|
||||
|
||||
TEST(DoAllTest, MoveOnlyArgs) {
|
||||
bool ran_first = false;
|
||||
Action<int(std::unique_ptr<int>)> a =
|
||||
DoAll(InvokeWithoutArgs([&] { ran_first = true; }),
|
||||
[](std::unique_ptr<int> p) { return *p; });
|
||||
Action<int(std::unique_ptr<int>)> a = DoAll(
|
||||
[&] { ran_first = true; }, [](std::unique_ptr<int> p) { return *p; });
|
||||
EXPECT_EQ(7, a.Perform(std::make_tuple(std::unique_ptr<int>(new int(7)))));
|
||||
EXPECT_TRUE(ran_first);
|
||||
}
|
||||
@@ -979,11 +1049,7 @@ TEST(DoAllTest, ImplicitlyConvertsActionArguments) {
|
||||
// is expanded and macro expansion cannot contain #pragma. Therefore
|
||||
// we suppress them here.
|
||||
// Also suppress C4503 decorated name length exceeded, name was truncated
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable : 4100)
|
||||
#pragma warning(disable : 4503)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100 4503)
|
||||
// Tests the ACTION*() macro family.
|
||||
|
||||
// Tests that ACTION() can define an action that doesn't reference the
|
||||
@@ -1545,3 +1611,6 @@ TEST(ActionTemplateTest, CanBeOverloadedOnNumberOfValueParameters) {
|
||||
|
||||
} // namespace gmock_more_actions_test
|
||||
} // namespace testing
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100 4503
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4577
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
|
||||
#include <string>
|
||||
#include <utility>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest-spi.h"
|
||||
#include "gtest/gtest.h"
|
||||
@@ -39,18 +40,18 @@
|
||||
// clash with ::testing::Mock.
|
||||
class Mock {
|
||||
public:
|
||||
Mock() {}
|
||||
Mock() = default;
|
||||
|
||||
MOCK_METHOD0(DoThis, void());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(Mock);
|
||||
Mock(const Mock&) = delete;
|
||||
Mock& operator=(const Mock&) = delete;
|
||||
};
|
||||
|
||||
namespace testing {
|
||||
namespace gmock_nice_strict_test {
|
||||
|
||||
using testing::GMOCK_FLAG(verbose);
|
||||
using testing::HasSubstr;
|
||||
using testing::NaggyMock;
|
||||
using testing::NiceMock;
|
||||
@@ -77,7 +78,7 @@ class CallsMockMethodInDestructor {
|
||||
|
||||
class Foo {
|
||||
public:
|
||||
virtual ~Foo() {}
|
||||
virtual ~Foo() = default;
|
||||
|
||||
virtual void DoThis() = 0;
|
||||
virtual int DoThat(bool flag) = 0;
|
||||
@@ -85,7 +86,7 @@ class Foo {
|
||||
|
||||
class MockFoo : public Foo {
|
||||
public:
|
||||
MockFoo() {}
|
||||
MockFoo() = default;
|
||||
void Delete() { delete this; }
|
||||
|
||||
MOCK_METHOD0(DoThis, void());
|
||||
@@ -93,7 +94,8 @@ class MockFoo : public Foo {
|
||||
MOCK_METHOD0(ReturnNonDefaultConstructible, NotDefaultConstructible());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockFoo);
|
||||
MockFoo(const MockFoo&) = delete;
|
||||
MockFoo& operator=(const MockFoo&) = delete;
|
||||
};
|
||||
|
||||
class MockBar {
|
||||
@@ -103,10 +105,11 @@ class MockBar {
|
||||
MockBar(char a1, char a2, std::string a3, std::string a4, int a5, int a6,
|
||||
const std::string& a7, const std::string& a8, bool a9, bool a10) {
|
||||
str_ = std::string() + a1 + a2 + a3 + a4 + static_cast<char>(a5) +
|
||||
static_cast<char>(a6) + a7 + a8 + (a9 ? 'T' : 'F') + (a10 ? 'T' : 'F');
|
||||
static_cast<char>(a6) + a7 + a8 + (a9 ? 'T' : 'F') +
|
||||
(a10 ? 'T' : 'F');
|
||||
}
|
||||
|
||||
virtual ~MockBar() {}
|
||||
virtual ~MockBar() = default;
|
||||
|
||||
const std::string& str() const { return str_; }
|
||||
|
||||
@@ -116,10 +119,10 @@ class MockBar {
|
||||
private:
|
||||
std::string str_;
|
||||
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockBar);
|
||||
MockBar(const MockBar&) = delete;
|
||||
MockBar& operator=(const MockBar&) = delete;
|
||||
};
|
||||
|
||||
|
||||
class MockBaz {
|
||||
public:
|
||||
class MoveOnly {
|
||||
@@ -140,8 +143,8 @@ class MockBaz {
|
||||
|
||||
// Tests that a raw mock generates warnings for uninteresting calls.
|
||||
TEST(RawMockTest, WarningForUninterestingCall) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "warning";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
|
||||
MockFoo raw_foo;
|
||||
|
||||
@@ -151,26 +154,25 @@ TEST(RawMockTest, WarningForUninterestingCall) {
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
// Tests that a raw mock generates warnings for uninteresting calls
|
||||
// that delete the mock object.
|
||||
TEST(RawMockTest, WarningForUninterestingCallAfterDeath) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "warning";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
|
||||
MockFoo* const raw_foo = new MockFoo;
|
||||
|
||||
ON_CALL(*raw_foo, DoThis())
|
||||
.WillByDefault(Invoke(raw_foo, &MockFoo::Delete));
|
||||
ON_CALL(*raw_foo, DoThis()).WillByDefault(Invoke(raw_foo, &MockFoo::Delete));
|
||||
|
||||
CaptureStdout();
|
||||
raw_foo->DoThis();
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
// Tests that a raw mock generates informational logs for
|
||||
@@ -178,14 +180,14 @@ TEST(RawMockTest, WarningForUninterestingCallAfterDeath) {
|
||||
TEST(RawMockTest, InfoForUninterestingCall) {
|
||||
MockFoo raw_foo;
|
||||
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "info";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "info");
|
||||
CaptureStdout();
|
||||
raw_foo.DoThis();
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
TEST(RawMockTest, IsNaggy_IsNice_IsStrict) {
|
||||
@@ -223,14 +225,14 @@ TEST(NiceMockTest, NoWarningForUninterestingCallAfterDeath) {
|
||||
TEST(NiceMockTest, InfoForUninterestingCall) {
|
||||
NiceMock<MockFoo> nice_foo;
|
||||
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "info";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "info");
|
||||
CaptureStdout();
|
||||
nice_foo.DoThis();
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
#endif // GTEST_HAS_STREAM_REDIRECTION
|
||||
@@ -281,8 +283,8 @@ TEST(NiceMockTest, NonDefaultConstructor) {
|
||||
// Tests that NiceMock works with a mock class that has a 10-ary
|
||||
// non-default constructor.
|
||||
TEST(NiceMockTest, NonDefaultConstructor10) {
|
||||
NiceMock<MockBar> nice_bar('a', 'b', "c", "d", 'e', 'f',
|
||||
"g", "h", true, false);
|
||||
NiceMock<MockBar> nice_bar('a', 'b', "c", "d", 'e', 'f', "g", "h", true,
|
||||
false);
|
||||
EXPECT_EQ("abcdefghTF", nice_bar.str());
|
||||
|
||||
nice_bar.This();
|
||||
@@ -326,8 +328,8 @@ TEST(NiceMockTest, IsNaggy_IsNice_IsStrict) {
|
||||
|
||||
// Tests that a naggy mock generates warnings for uninteresting calls.
|
||||
TEST(NaggyMockTest, WarningForUninterestingCall) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "warning";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
|
||||
NaggyMock<MockFoo> naggy_foo;
|
||||
|
||||
@@ -337,14 +339,14 @@ TEST(NaggyMockTest, WarningForUninterestingCall) {
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
// Tests that a naggy mock generates a warning for an uninteresting call
|
||||
// that deletes the mock object.
|
||||
TEST(NaggyMockTest, WarningForUninterestingCallAfterDeath) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "warning";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
|
||||
NaggyMock<MockFoo>* const naggy_foo = new NaggyMock<MockFoo>;
|
||||
|
||||
@@ -356,7 +358,7 @@ TEST(NaggyMockTest, WarningForUninterestingCallAfterDeath) {
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
#endif // GTEST_HAS_STREAM_REDIRECTION
|
||||
@@ -391,8 +393,8 @@ TEST(NaggyMockTest, NonDefaultConstructor) {
|
||||
// Tests that NaggyMock works with a mock class that has a 10-ary
|
||||
// non-default constructor.
|
||||
TEST(NaggyMockTest, NonDefaultConstructor10) {
|
||||
NaggyMock<MockBar> naggy_bar('0', '1', "2", "3", '4', '5',
|
||||
"6", "7", true, false);
|
||||
NaggyMock<MockBar> naggy_bar('0', '1', "2", "3", '4', '5', "6", "7", true,
|
||||
false);
|
||||
EXPECT_EQ("01234567TF", naggy_bar.str());
|
||||
|
||||
naggy_bar.This();
|
||||
@@ -419,8 +421,8 @@ TEST(NaggyMockTest, AcceptsClassNamedMock) {
|
||||
}
|
||||
|
||||
TEST(NaggyMockTest, IsNaggyInDestructor) {
|
||||
const std::string saved_flag = GMOCK_FLAG(verbose);
|
||||
GMOCK_FLAG(verbose) = "warning";
|
||||
const std::string saved_flag = GMOCK_FLAG_GET(verbose);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
CaptureStdout();
|
||||
|
||||
{
|
||||
@@ -431,7 +433,7 @@ TEST(NaggyMockTest, IsNaggyInDestructor) {
|
||||
EXPECT_THAT(GetCapturedStdout(),
|
||||
HasSubstr("Uninteresting mock function call"));
|
||||
|
||||
GMOCK_FLAG(verbose) = saved_flag;
|
||||
GMOCK_FLAG_SET(verbose, saved_flag);
|
||||
}
|
||||
|
||||
TEST(NaggyMockTest, IsNaggy_IsNice_IsStrict) {
|
||||
@@ -491,8 +493,8 @@ TEST(StrictMockTest, NonDefaultConstructor) {
|
||||
// Tests that StrictMock works with a mock class that has a 10-ary
|
||||
// non-default constructor.
|
||||
TEST(StrictMockTest, NonDefaultConstructor10) {
|
||||
StrictMock<MockBar> strict_bar('a', 'b', "c", "d", 'e', 'f',
|
||||
"g", "h", true, false);
|
||||
StrictMock<MockBar> strict_bar('a', 'b', "c", "d", 'e', 'f', "g", "h", true,
|
||||
false);
|
||||
EXPECT_EQ("abcdefghTF", strict_bar.str());
|
||||
|
||||
EXPECT_NONFATAL_FAILURE(strict_bar.That(5, true),
|
||||
|
||||
@@ -27,12 +27,12 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests the internal cross-platform support utilities.
|
||||
|
||||
#include "gmock/internal/gmock-port.h"
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
// NOTE: if this file is left without tests for some reason, put a dummy
|
||||
|
||||
@@ -30,11 +30,10 @@
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests the internal preprocessor macro library.
|
||||
#include "gmock/internal/gmock-pp.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gmock/internal/gmock-pp.h"
|
||||
|
||||
namespace testing {
|
||||
namespace {
|
||||
|
||||
@@ -11,8 +11,10 @@ namespace internal {
|
||||
namespace gmockpp {
|
||||
|
||||
static_assert(GMOCK_PP_CAT(1, 4) == 14, "");
|
||||
static_assert(GMOCK_PP_INTERNAL_INTERNAL_16TH(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
|
||||
12, 13, 14, 15, 16, 17, 18) == 16,
|
||||
static_assert(GMOCK_PP_INTERNAL_INTERNAL_32ND(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
|
||||
12, 13, 14, 15, 16, 17, 18, 19,
|
||||
20, 21, 22, 23, 24, 25, 26, 27,
|
||||
28, 29, 30, 31, 32, 33, 34) == 32,
|
||||
"");
|
||||
static_assert(GMOCK_PP_NARG() == 1, "");
|
||||
static_assert(GMOCK_PP_NARG(x) == 1, "");
|
||||
@@ -70,7 +72,7 @@ static_assert(GMOCK_PP_INTERNAL_VAR_TEST(x, y) == 2, "");
|
||||
static_assert(GMOCK_PP_INTERNAL_VAR_TEST(silly) == 1, "");
|
||||
static_assert(GMOCK_PP_INTERNAL_VAR_TEST(x, y, z) == 3, "");
|
||||
|
||||
// TODO(iserna): The following asserts fail in --config=lexan.
|
||||
// TODO(iserna): The following asserts fail in --config=windows.
|
||||
#define GMOCK_PP_INTERNAL_IS_EMPTY_TEST_1
|
||||
static_assert(GMOCK_PP_IS_EMPTY(GMOCK_PP_INTERNAL_IS_EMPTY_TEST_1), "");
|
||||
static_assert(GMOCK_PP_IS_EMPTY(), "");
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -38,7 +38,10 @@
|
||||
#include "test/gmock-actions_test.cc"
|
||||
#include "test/gmock-cardinalities_test.cc"
|
||||
#include "test/gmock-internal-utils_test.cc"
|
||||
#include "test/gmock-matchers_test.cc"
|
||||
#include "test/gmock-matchers-arithmetic_test.cc"
|
||||
#include "test/gmock-matchers-comparisons_test.cc"
|
||||
#include "test/gmock-matchers-containers_test.cc"
|
||||
#include "test/gmock-matchers-misc_test.cc"
|
||||
#include "test/gmock-more-actions_test.cc"
|
||||
#include "test/gmock-nice-strict_test.cc"
|
||||
#include "test/gmock-port_test.cc"
|
||||
|
||||
@@ -27,9 +27,10 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Tests Google Mock's functionality that depends on exceptions.
|
||||
|
||||
#include <exception>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
@@ -75,6 +76,5 @@ TEST(DefaultValueTest, ThrowsRuntimeErrorWhenNoDefaultValue) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
} // unnamed namespace
|
||||
#endif
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
|
||||
"""Tests that leaked mock objects can be caught be Google Mock."""
|
||||
|
||||
import gmock_test_utils
|
||||
from googlemock.test import gmock_test_utils
|
||||
|
||||
PROGRAM_PATH = gmock_test_utils.GetTestExecutablePath('gmock_leak_test_')
|
||||
TEST_WITH_EXPECT_CALL = [PROGRAM_PATH, '--gtest_filter=*ExpectCall*']
|
||||
@@ -54,50 +54,59 @@ class GMockLeakTest(gmock_test_utils.TestCase):
|
||||
def testCatchesLeakedMockByDefault(self):
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_EXPECT_CALL,
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_EXPECT_CALL, env=environ
|
||||
).exit_code,
|
||||
)
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_ON_CALL,
|
||||
env=environ).exit_code)
|
||||
0, gmock_test_utils.Subprocess(TEST_WITH_ON_CALL, env=environ).exit_code
|
||||
)
|
||||
|
||||
def testDoesNotCatchLeakedMockWhenDisabled(self):
|
||||
self.assertEquals(
|
||||
self.assertEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_EXPECT_CALL +
|
||||
['--gmock_catch_leaked_mocks=0'],
|
||||
env=environ).exit_code)
|
||||
self.assertEquals(
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_EXPECT_CALL + ['--gmock_catch_leaked_mocks=0'],
|
||||
env=environ,
|
||||
).exit_code,
|
||||
)
|
||||
self.assertEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_ON_CALL +
|
||||
['--gmock_catch_leaked_mocks=0'],
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_ON_CALL + ['--gmock_catch_leaked_mocks=0'], env=environ
|
||||
).exit_code,
|
||||
)
|
||||
|
||||
def testCatchesLeakedMockWhenEnabled(self):
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_EXPECT_CALL +
|
||||
['--gmock_catch_leaked_mocks'],
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_EXPECT_CALL + ['--gmock_catch_leaked_mocks'], env=environ
|
||||
).exit_code,
|
||||
)
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_ON_CALL +
|
||||
['--gmock_catch_leaked_mocks'],
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_ON_CALL + ['--gmock_catch_leaked_mocks'], env=environ
|
||||
).exit_code,
|
||||
)
|
||||
|
||||
def testCatchesLeakedMockWhenEnabledWithExplictFlagValue(self):
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_WITH_EXPECT_CALL +
|
||||
['--gmock_catch_leaked_mocks=1'],
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_WITH_EXPECT_CALL + ['--gmock_catch_leaked_mocks=1'],
|
||||
env=environ,
|
||||
).exit_code,
|
||||
)
|
||||
|
||||
def testCatchesMultipleLeakedMocks(self):
|
||||
self.assertNotEqual(
|
||||
0,
|
||||
gmock_test_utils.Subprocess(TEST_MULTIPLE_LEAKS +
|
||||
['--gmock_catch_leaked_mocks'],
|
||||
env=environ).exit_code)
|
||||
gmock_test_utils.Subprocess(
|
||||
TEST_MULTIPLE_LEAKS + ['--gmock_catch_leaked_mocks'], env=environ
|
||||
).exit_code,
|
||||
)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This program is for verifying that a leaked mock object can be
|
||||
@@ -41,18 +40,19 @@ using ::testing::Return;
|
||||
|
||||
class FooInterface {
|
||||
public:
|
||||
virtual ~FooInterface() {}
|
||||
virtual ~FooInterface() = default;
|
||||
virtual void DoThis() = 0;
|
||||
};
|
||||
|
||||
class MockFoo : public FooInterface {
|
||||
public:
|
||||
MockFoo() {}
|
||||
MockFoo() = default;
|
||||
|
||||
MOCK_METHOD0(DoThis, void());
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockFoo);
|
||||
MockFoo(const MockFoo&) = delete;
|
||||
MockFoo& operator=(const MockFoo&) = delete;
|
||||
};
|
||||
|
||||
TEST(LeakTest, LeakedMockWithExpectCallCausesFailureWhenLeakCheckingIsEnabled) {
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file is for verifying that various Google Mock constructs do not
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file is for verifying that various Google Mock constructs do not
|
||||
|
||||
@@ -27,7 +27,6 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Google Mock - a framework for writing C++ mock classes.
|
||||
//
|
||||
// This file tests that:
|
||||
@@ -117,8 +116,8 @@
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
|
||||
#if !GTEST_OS_WINDOWS_MOBILE
|
||||
# include <errno.h>
|
||||
#ifndef GTEST_OS_WINDOWS_MOBILE
|
||||
#include <errno.h>
|
||||
#endif
|
||||
|
||||
#include <iostream>
|
||||
@@ -182,11 +181,12 @@ using testing::WithArg;
|
||||
using testing::WithArgs;
|
||||
using testing::WithoutArgs;
|
||||
|
||||
#if !GTEST_OS_WINDOWS_MOBILE
|
||||
#ifndef GTEST_OS_WINDOWS_MOBILE
|
||||
using testing::SetErrnoAndReturn;
|
||||
#endif
|
||||
|
||||
#if GTEST_HAS_EXCEPTIONS
|
||||
using testing::Rethrow;
|
||||
using testing::Throw;
|
||||
#endif
|
||||
|
||||
@@ -195,34 +195,35 @@ using testing::MatchesRegex;
|
||||
|
||||
class Interface {
|
||||
public:
|
||||
virtual ~Interface() {}
|
||||
virtual ~Interface() = default;
|
||||
virtual void VoidFromString(char* str) = 0;
|
||||
virtual char* StringFromString(char* str) = 0;
|
||||
virtual int IntFromString(char* str) = 0;
|
||||
virtual int& IntRefFromString(char* str) = 0;
|
||||
virtual void VoidFromFunc(void(*func)(char* str)) = 0;
|
||||
virtual void VoidFromFunc(void (*func)(char* str)) = 0;
|
||||
virtual void VoidFromIntRef(int& n) = 0; // NOLINT
|
||||
virtual void VoidFromFloat(float n) = 0;
|
||||
virtual void VoidFromDouble(double n) = 0;
|
||||
virtual void VoidFromVector(const std::vector<int>& v) = 0;
|
||||
};
|
||||
|
||||
class Mock: public Interface {
|
||||
class Mock : public Interface {
|
||||
public:
|
||||
Mock() {}
|
||||
Mock() = default;
|
||||
|
||||
MOCK_METHOD1(VoidFromString, void(char* str));
|
||||
MOCK_METHOD1(StringFromString, char*(char* str));
|
||||
MOCK_METHOD1(IntFromString, int(char* str));
|
||||
MOCK_METHOD1(IntRefFromString, int&(char* str));
|
||||
MOCK_METHOD1(VoidFromFunc, void(void(*func)(char* str)));
|
||||
MOCK_METHOD1(VoidFromFunc, void(void (*func)(char* str)));
|
||||
MOCK_METHOD1(VoidFromIntRef, void(int& n)); // NOLINT
|
||||
MOCK_METHOD1(VoidFromFloat, void(float n));
|
||||
MOCK_METHOD1(VoidFromDouble, void(double n));
|
||||
MOCK_METHOD1(VoidFromVector, void(const std::vector<int>& v));
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(Mock);
|
||||
Mock(const Mock&) = delete;
|
||||
Mock& operator=(const Mock&) = delete;
|
||||
};
|
||||
|
||||
class InvokeHelper {
|
||||
@@ -301,12 +302,12 @@ TEST(LinkTest, TestSetArrayArgument) {
|
||||
char ch = 'x';
|
||||
char ch2 = 'y';
|
||||
|
||||
EXPECT_CALL(mock, VoidFromString(_)).WillOnce(SetArrayArgument<0>(&ch2,
|
||||
&ch2 + 1));
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(SetArrayArgument<0>(&ch2, &ch2 + 1));
|
||||
mock.VoidFromString(&ch);
|
||||
}
|
||||
|
||||
#if !GTEST_OS_WINDOWS_MOBILE
|
||||
#ifndef GTEST_OS_WINDOWS_MOBILE
|
||||
|
||||
// Tests the linkage of the SetErrnoAndReturn action.
|
||||
TEST(LinkTest, TestSetErrnoAndReturn) {
|
||||
@@ -326,7 +327,7 @@ TEST(LinkTest, TestInvoke) {
|
||||
InvokeHelper test_invoke_helper;
|
||||
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(Invoke(&InvokeHelper::StaticVoidFromString))
|
||||
.WillOnce(&InvokeHelper::StaticVoidFromString)
|
||||
.WillOnce(Invoke(&test_invoke_helper, &InvokeHelper::VoidFromString));
|
||||
mock.VoidFromString(nullptr);
|
||||
mock.VoidFromString(nullptr);
|
||||
@@ -337,10 +338,12 @@ TEST(LinkTest, TestInvokeWithoutArgs) {
|
||||
Mock mock;
|
||||
InvokeHelper test_invoke_helper;
|
||||
|
||||
GTEST_DISABLE_DEPRECATED_PUSH_()
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(InvokeWithoutArgs(&InvokeHelper::StaticVoidFromVoid))
|
||||
.WillOnce(InvokeWithoutArgs(&test_invoke_helper,
|
||||
&InvokeHelper::VoidFromVoid));
|
||||
.WillOnce(&InvokeHelper::StaticVoidFromVoid)
|
||||
.WillOnce(
|
||||
InvokeWithoutArgs(&test_invoke_helper, &InvokeHelper::VoidFromVoid));
|
||||
GTEST_DISABLE_DEPRECATED_POP_()
|
||||
mock.VoidFromString(nullptr);
|
||||
mock.VoidFromString(nullptr);
|
||||
}
|
||||
@@ -359,7 +362,7 @@ TEST(LinkTest, TestWithArg) {
|
||||
Mock mock;
|
||||
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(WithArg<0>(Invoke(&InvokeHelper::StaticVoidFromString)));
|
||||
.WillOnce(WithArg<0>(&InvokeHelper::StaticVoidFromString));
|
||||
mock.VoidFromString(nullptr);
|
||||
}
|
||||
|
||||
@@ -368,7 +371,7 @@ TEST(LinkTest, TestWithArgs) {
|
||||
Mock mock;
|
||||
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(WithArgs<0>(Invoke(&InvokeHelper::StaticVoidFromString)));
|
||||
.WillOnce(WithArgs<0>(&InvokeHelper::StaticVoidFromString));
|
||||
mock.VoidFromString(nullptr);
|
||||
}
|
||||
|
||||
@@ -416,6 +419,14 @@ TEST(LinkTest, TestThrow) {
|
||||
EXPECT_CALL(mock, VoidFromString(_)).WillOnce(Throw(42));
|
||||
EXPECT_THROW(mock.VoidFromString(nullptr), int);
|
||||
}
|
||||
// Tests the linkage of the Rethrow action.
|
||||
TEST(LinkTest, TestRethrow) {
|
||||
Mock mock;
|
||||
|
||||
EXPECT_CALL(mock, VoidFromString(_))
|
||||
.WillOnce(Rethrow(std::make_exception_ptr(42)));
|
||||
EXPECT_THROW(mock.VoidFromString(nullptr), int);
|
||||
}
|
||||
#endif // GTEST_HAS_EXCEPTIONS
|
||||
|
||||
// The ACTION*() macros trigger warning C4100 (unreferenced formal
|
||||
@@ -423,15 +434,12 @@ TEST(LinkTest, TestThrow) {
|
||||
// the macro definition, as the warnings are generated when the macro
|
||||
// is expanded and macro expansion cannot contain #pragma. Therefore
|
||||
// we suppress them here.
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4100)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100)
|
||||
|
||||
// Tests the linkage of actions created using ACTION macro.
|
||||
namespace {
|
||||
ACTION(Return1) { return 1; }
|
||||
}
|
||||
} // namespace
|
||||
|
||||
TEST(LinkTest, TestActionMacro) {
|
||||
Mock mock;
|
||||
@@ -443,7 +451,7 @@ TEST(LinkTest, TestActionMacro) {
|
||||
// Tests the linkage of actions created using ACTION_P macro.
|
||||
namespace {
|
||||
ACTION_P(ReturnArgument, ret_value) { return ret_value; }
|
||||
}
|
||||
} // namespace
|
||||
|
||||
TEST(LinkTest, TestActionPMacro) {
|
||||
Mock mock;
|
||||
@@ -457,11 +465,9 @@ namespace {
|
||||
ACTION_P2(ReturnEqualsEitherOf, first, second) {
|
||||
return arg0 == first || arg0 == second;
|
||||
}
|
||||
}
|
||||
} // namespace
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100
|
||||
|
||||
TEST(LinkTest, TestActionP2Macro) {
|
||||
Mock mock;
|
||||
@@ -492,8 +498,7 @@ TEST(LinkTest, TestMatchersEq) {
|
||||
const char* p = "x";
|
||||
|
||||
ON_CALL(mock, VoidFromString(Eq(p))).WillByDefault(Return());
|
||||
ON_CALL(mock, VoidFromString(const_cast<char*>("y")))
|
||||
.WillByDefault(Return());
|
||||
ON_CALL(mock, VoidFromString(const_cast<char*>("y"))).WillByDefault(Return());
|
||||
}
|
||||
|
||||
// Tests the linkage of the Lt, Gt, Le, Ge, and Ne matchers.
|
||||
@@ -592,7 +597,7 @@ TEST(LinkTest, TestMatcherElementsAre) {
|
||||
// Tests the linkage of the ElementsAreArray matcher.
|
||||
TEST(LinkTest, TestMatcherElementsAreArray) {
|
||||
Mock mock;
|
||||
char arr[] = { 'a', 'b' };
|
||||
char arr[] = {'a', 'b'};
|
||||
|
||||
ON_CALL(mock, VoidFromVector(ElementsAreArray(arr))).WillByDefault(Return());
|
||||
}
|
||||
|
||||
@@ -39,11 +39,11 @@ gmock_output_test.py
|
||||
|
||||
"""
|
||||
|
||||
from io import open # pylint: disable=redefined-builtin, g-importing-member
|
||||
from io import open # pylint: disable=redefined-builtin, g-importing-member
|
||||
import os
|
||||
import re
|
||||
import sys
|
||||
import gmock_test_utils
|
||||
from googlemock.test import gmock_test_utils
|
||||
|
||||
|
||||
# The flag for generating the golden file
|
||||
@@ -159,15 +159,22 @@ class GMockOutputTest(gmock_test_utils.TestCase):
|
||||
golden_file = open(GOLDEN_PATH, 'rb')
|
||||
golden = golden_file.read().decode('utf-8')
|
||||
golden_file.close()
|
||||
# On Windows the repository might have been checked out with \r\n line
|
||||
# endings, so normalize it here.
|
||||
golden = ToUnixLineEnding(golden)
|
||||
|
||||
# The normalized output should match the golden file.
|
||||
self.assertEquals(golden, output)
|
||||
self.assertEqual(golden, output)
|
||||
|
||||
# The raw output should contain 2 leaked mock object errors for
|
||||
# test GMockOutputTest.CatchesLeakedMocks.
|
||||
self.assertEquals(['GMockOutputTest.CatchesLeakedMocks',
|
||||
'GMockOutputTest.CatchesLeakedMocks'],
|
||||
leaky_tests)
|
||||
self.assertEqual(
|
||||
[
|
||||
'GMockOutputTest.CatchesLeakedMocks',
|
||||
'GMockOutputTest.CatchesLeakedMocks',
|
||||
],
|
||||
leaky_tests,
|
||||
)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
@@ -27,22 +27,18 @@
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
|
||||
// Tests Google Mock's output in various scenarios. This ensures that
|
||||
// Google Mock's messages are readable and useful.
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "gmock/gmock.h"
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
// Silence C4100 (unreferenced formal parameter)
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(push)
|
||||
# pragma warning(disable:4100)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_PUSH_(4100)
|
||||
|
||||
using testing::_;
|
||||
using testing::AnyNumber;
|
||||
@@ -56,14 +52,15 @@ using testing::Value;
|
||||
|
||||
class MockFoo {
|
||||
public:
|
||||
MockFoo() {}
|
||||
MockFoo() = default;
|
||||
|
||||
MOCK_METHOD3(Bar, char(const std::string& s, int i, double x));
|
||||
MOCK_METHOD2(Bar2, bool(int x, int y));
|
||||
MOCK_METHOD2(Bar3, void(int x, int y));
|
||||
|
||||
private:
|
||||
GTEST_DISALLOW_COPY_AND_ASSIGN_(MockFoo);
|
||||
MockFoo(const MockFoo&) = delete;
|
||||
MockFoo& operator=(const MockFoo&) = delete;
|
||||
};
|
||||
|
||||
class GMockOutputTest : public testing::Test {
|
||||
@@ -72,27 +69,25 @@ class GMockOutputTest : public testing::Test {
|
||||
};
|
||||
|
||||
TEST_F(GMockOutputTest, ExpectedCall) {
|
||||
testing::GMOCK_FLAG(verbose) = "info";
|
||||
GMOCK_FLAG_SET(verbose, "info");
|
||||
|
||||
EXPECT_CALL(foo_, Bar2(0, _));
|
||||
foo_.Bar2(0, 0); // Expected call
|
||||
|
||||
testing::GMOCK_FLAG(verbose) = "warning";
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, ExpectedCallToVoidFunction) {
|
||||
testing::GMOCK_FLAG(verbose) = "info";
|
||||
GMOCK_FLAG_SET(verbose, "info");
|
||||
|
||||
EXPECT_CALL(foo_, Bar3(0, _));
|
||||
foo_.Bar3(0, 0); // Expected call
|
||||
|
||||
testing::GMOCK_FLAG(verbose) = "warning";
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, ExplicitActionsRunOut) {
|
||||
EXPECT_CALL(foo_, Bar2(_, _))
|
||||
.Times(2)
|
||||
.WillOnce(Return(false));
|
||||
EXPECT_CALL(foo_, Bar2(_, _)).Times(2).WillOnce(Return(false));
|
||||
foo_.Bar2(2, 2);
|
||||
foo_.Bar2(1, 1); // Explicit actions in EXPECT_CALL run out.
|
||||
}
|
||||
@@ -134,8 +129,7 @@ TEST_F(GMockOutputTest, UninterestingCallToVoidFunction) {
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, RetiredExpectation) {
|
||||
EXPECT_CALL(foo_, Bar2(_, _))
|
||||
.RetiresOnSaturation();
|
||||
EXPECT_CALL(foo_, Bar2(_, _)).RetiresOnSaturation();
|
||||
EXPECT_CALL(foo_, Bar2(0, 0));
|
||||
|
||||
foo_.Bar2(1, 1);
|
||||
@@ -160,12 +154,9 @@ TEST_F(GMockOutputTest, UnsatisfiedPrerequisite) {
|
||||
TEST_F(GMockOutputTest, UnsatisfiedPrerequisites) {
|
||||
Sequence s1, s2;
|
||||
|
||||
EXPECT_CALL(foo_, Bar(_, 0, _))
|
||||
.InSequence(s1);
|
||||
EXPECT_CALL(foo_, Bar2(0, 0))
|
||||
.InSequence(s2);
|
||||
EXPECT_CALL(foo_, Bar2(1, _))
|
||||
.InSequence(s1, s2);
|
||||
EXPECT_CALL(foo_, Bar(_, 0, _)).InSequence(s1);
|
||||
EXPECT_CALL(foo_, Bar2(0, 0)).InSequence(s2);
|
||||
EXPECT_CALL(foo_, Bar2(1, _)).InSequence(s1, s2);
|
||||
|
||||
foo_.Bar2(1, 0); // Has two immediate unsatisfied pre-requisites
|
||||
foo_.Bar("Hi", 0, 0);
|
||||
@@ -179,8 +170,7 @@ TEST_F(GMockOutputTest, UnsatisfiedWith) {
|
||||
|
||||
TEST_F(GMockOutputTest, UnsatisfiedExpectation) {
|
||||
EXPECT_CALL(foo_, Bar(_, _, _));
|
||||
EXPECT_CALL(foo_, Bar2(0, _))
|
||||
.Times(2);
|
||||
EXPECT_CALL(foo_, Bar2(0, _)).Times(2);
|
||||
|
||||
foo_.Bar2(0, 1);
|
||||
}
|
||||
@@ -194,26 +184,22 @@ TEST_F(GMockOutputTest, MismatchArguments) {
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, MismatchWith) {
|
||||
EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1)))
|
||||
.With(Ge());
|
||||
EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1))).With(Ge());
|
||||
|
||||
foo_.Bar2(2, 3); // Mismatch With()
|
||||
foo_.Bar2(2, 1);
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, MismatchArgumentsAndWith) {
|
||||
EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1)))
|
||||
.With(Ge());
|
||||
EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1))).With(Ge());
|
||||
|
||||
foo_.Bar2(1, 3); // Mismatch arguments and mismatch With()
|
||||
foo_.Bar2(2, 1);
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, UnexpectedCallWithDefaultAction) {
|
||||
ON_CALL(foo_, Bar2(_, _))
|
||||
.WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _))
|
||||
.WillByDefault(Return(false)); // Default action #2
|
||||
ON_CALL(foo_, Bar2(_, _)).WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _)).WillByDefault(Return(false)); // Default action #2
|
||||
|
||||
EXPECT_CALL(foo_, Bar2(2, 2));
|
||||
foo_.Bar2(1, 0); // Unexpected call, takes default action #2.
|
||||
@@ -222,10 +208,8 @@ TEST_F(GMockOutputTest, UnexpectedCallWithDefaultAction) {
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, ExcessiveCallWithDefaultAction) {
|
||||
ON_CALL(foo_, Bar2(_, _))
|
||||
.WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _))
|
||||
.WillByDefault(Return(false)); // Default action #2
|
||||
ON_CALL(foo_, Bar2(_, _)).WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _)).WillByDefault(Return(false)); // Default action #2
|
||||
|
||||
EXPECT_CALL(foo_, Bar2(2, 2));
|
||||
EXPECT_CALL(foo_, Bar2(1, 1));
|
||||
@@ -237,22 +221,17 @@ TEST_F(GMockOutputTest, ExcessiveCallWithDefaultAction) {
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, UninterestingCallWithDefaultAction) {
|
||||
ON_CALL(foo_, Bar2(_, _))
|
||||
.WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _))
|
||||
.WillByDefault(Return(false)); // Default action #2
|
||||
ON_CALL(foo_, Bar2(_, _)).WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(1, _)).WillByDefault(Return(false)); // Default action #2
|
||||
|
||||
foo_.Bar2(2, 2); // Uninteresting call, takes default action #1.
|
||||
foo_.Bar2(1, 1); // Uninteresting call, takes default action #2.
|
||||
}
|
||||
|
||||
TEST_F(GMockOutputTest, ExplicitActionsRunOutWithDefaultAction) {
|
||||
ON_CALL(foo_, Bar2(_, _))
|
||||
.WillByDefault(Return(true)); // Default action #1
|
||||
ON_CALL(foo_, Bar2(_, _)).WillByDefault(Return(true)); // Default action #1
|
||||
|
||||
EXPECT_CALL(foo_, Bar2(_, _))
|
||||
.Times(2)
|
||||
.WillOnce(Return(false));
|
||||
EXPECT_CALL(foo_, Bar2(_, _)).Times(2).WillOnce(Return(false));
|
||||
foo_.Bar2(2, 2);
|
||||
foo_.Bar2(1, 1); // Explicit actions in EXPECT_CALL run out.
|
||||
}
|
||||
@@ -293,17 +272,15 @@ void TestCatchesLeakedMocksInAdHocTests() {
|
||||
// foo is deliberately leaked.
|
||||
}
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
int main(int argc, char** argv) {
|
||||
testing::InitGoogleMock(&argc, argv);
|
||||
// Ensures that the tests pass no matter what value of
|
||||
// --gmock_catch_leaked_mocks and --gmock_verbose the user specifies.
|
||||
testing::GMOCK_FLAG(catch_leaked_mocks) = true;
|
||||
testing::GMOCK_FLAG(verbose) = "warning";
|
||||
GMOCK_FLAG_SET(catch_leaked_mocks, true);
|
||||
GMOCK_FLAG_SET(verbose, "warning");
|
||||
|
||||
TestCatchesLeakedMocksInAdHocTests();
|
||||
return RUN_ALL_TESTS();
|
||||
}
|
||||
|
||||
#ifdef _MSC_VER
|
||||
# pragma warning(pop)
|
||||
#endif
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4100
|
||||
|
||||
@@ -40,6 +40,7 @@ FILE:#: EXPECT_CALL(foo_, Bar2(0, _))...
|
||||
Actual: 1
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnexpectedCall
|
||||
[ RUN ] GMockOutputTest.UnexpectedCallToVoidFunction
|
||||
unknown file: Failure
|
||||
@@ -53,6 +54,7 @@ FILE:#: EXPECT_CALL(foo_, Bar3(0, _))...
|
||||
Actual: 1
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnexpectedCallToVoidFunction
|
||||
[ RUN ] GMockOutputTest.ExcessiveCall
|
||||
FILE:#: Failure
|
||||
@@ -61,6 +63,7 @@ Mock function called more times than expected - returning default value.
|
||||
Returns: false
|
||||
Expected: to be called once
|
||||
Actual: called twice - over-saturated and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.ExcessiveCall
|
||||
[ RUN ] GMockOutputTest.ExcessiveCallToVoidFunction
|
||||
FILE:#: Failure
|
||||
@@ -68,6 +71,7 @@ Mock function called more times than expected - returning directly.
|
||||
Function call: Bar3(0, 1)
|
||||
Expected: to be called once
|
||||
Actual: called twice - over-saturated and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.ExcessiveCallToVoidFunction
|
||||
[ RUN ] GMockOutputTest.UninterestingCall
|
||||
|
||||
@@ -75,14 +79,14 @@ GMOCK WARNING:
|
||||
Uninteresting mock function call - returning default value.
|
||||
Function call: Bar2(0, 1)
|
||||
Returns: false
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by blindly adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/master/docs/gmock_cook_book.md#knowing-when-to-expect for details.
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/main/docs/gmock_cook_book.md#knowing-when-to-expect-useoncall for details.
|
||||
[ OK ] GMockOutputTest.UninterestingCall
|
||||
[ RUN ] GMockOutputTest.UninterestingCallToVoidFunction
|
||||
|
||||
GMOCK WARNING:
|
||||
Uninteresting mock function call - returning directly.
|
||||
Function call: Bar3(0, 1)
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by blindly adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/master/docs/gmock_cook_book.md#knowing-when-to-expect for details.
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/main/docs/gmock_cook_book.md#knowing-when-to-expect-useoncall for details.
|
||||
[ OK ] GMockOutputTest.UninterestingCallToVoidFunction
|
||||
[ RUN ] GMockOutputTest.RetiredExpectation
|
||||
unknown file: Failure
|
||||
@@ -104,6 +108,7 @@ FILE:#: tried expectation #1: EXPECT_CALL(foo_, Bar2(0, 0))...
|
||||
Actual: 1
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.RetiredExpectation
|
||||
[ RUN ] GMockOutputTest.UnsatisfiedPrerequisite
|
||||
unknown file: Failure
|
||||
@@ -125,6 +130,7 @@ FILE:#: pre-requisite #0
|
||||
(end of pre-requisites)
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnsatisfiedPrerequisite
|
||||
[ RUN ] GMockOutputTest.UnsatisfiedPrerequisites
|
||||
unknown file: Failure
|
||||
@@ -147,6 +153,7 @@ FILE:#: pre-requisite #1
|
||||
(end of pre-requisites)
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnsatisfiedPrerequisites
|
||||
[ RUN ] GMockOutputTest.UnsatisfiedWith
|
||||
FILE:#: Failure
|
||||
@@ -154,16 +161,19 @@ Actual function call count doesn't match EXPECT_CALL(foo_, Bar2(_, _))...
|
||||
Expected args: are a pair where the first >= the second
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnsatisfiedWith
|
||||
[ RUN ] GMockOutputTest.UnsatisfiedExpectation
|
||||
FILE:#: Failure
|
||||
Actual function call count doesn't match EXPECT_CALL(foo_, Bar2(0, _))...
|
||||
Expected: to be called twice
|
||||
Actual: called once - unsatisfied and active
|
||||
|
||||
FILE:#: Failure
|
||||
Actual function call count doesn't match EXPECT_CALL(foo_, Bar(_, _, _))...
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnsatisfiedExpectation
|
||||
[ RUN ] GMockOutputTest.MismatchArguments
|
||||
unknown file: Failure
|
||||
@@ -180,6 +190,7 @@ FILE:#: EXPECT_CALL(foo_, Bar(Ref(s), _, Ge(0)))...
|
||||
Actual: -0.1
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.MismatchArguments
|
||||
[ RUN ] GMockOutputTest.MismatchWith
|
||||
unknown file: Failure
|
||||
@@ -194,6 +205,7 @@ FILE:#: EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1)))...
|
||||
Actual: don't match
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.MismatchWith
|
||||
[ RUN ] GMockOutputTest.MismatchArgumentsAndWith
|
||||
unknown file: Failure
|
||||
@@ -210,6 +222,7 @@ FILE:#: EXPECT_CALL(foo_, Bar2(Ge(2), Ge(1)))...
|
||||
Actual: don't match
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.MismatchArgumentsAndWith
|
||||
[ RUN ] GMockOutputTest.UnexpectedCallWithDefaultAction
|
||||
unknown file: Failure
|
||||
@@ -227,6 +240,7 @@ FILE:#: EXPECT_CALL(foo_, Bar2(2, 2))...
|
||||
Actual: 0
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
unknown file: Failure
|
||||
|
||||
Unexpected mock function call - taking default action specified at:
|
||||
@@ -242,6 +256,7 @@ FILE:#: EXPECT_CALL(foo_, Bar2(2, 2))...
|
||||
Actual: 0
|
||||
Expected: to be called once
|
||||
Actual: never called - unsatisfied and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.UnexpectedCallWithDefaultAction
|
||||
[ RUN ] GMockOutputTest.ExcessiveCallWithDefaultAction
|
||||
FILE:#: Failure
|
||||
@@ -251,6 +266,7 @@ FILE:#:
|
||||
Returns: true
|
||||
Expected: to be called once
|
||||
Actual: called twice - over-saturated and active
|
||||
|
||||
FILE:#: Failure
|
||||
Mock function called more times than expected - taking default action specified at:
|
||||
FILE:#:
|
||||
@@ -258,6 +274,7 @@ FILE:#:
|
||||
Returns: false
|
||||
Expected: to be called once
|
||||
Actual: called twice - over-saturated and active
|
||||
|
||||
[ FAILED ] GMockOutputTest.ExcessiveCallWithDefaultAction
|
||||
[ RUN ] GMockOutputTest.UninterestingCallWithDefaultAction
|
||||
|
||||
@@ -266,14 +283,14 @@ Uninteresting mock function call - taking default action specified at:
|
||||
FILE:#:
|
||||
Function call: Bar2(2, 2)
|
||||
Returns: true
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by blindly adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/master/docs/gmock_cook_book.md#knowing-when-to-expect for details.
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/main/docs/gmock_cook_book.md#knowing-when-to-expect-useoncall for details.
|
||||
|
||||
GMOCK WARNING:
|
||||
Uninteresting mock function call - taking default action specified at:
|
||||
FILE:#:
|
||||
Function call: Bar2(1, 1)
|
||||
Returns: false
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by blindly adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/master/docs/gmock_cook_book.md#knowing-when-to-expect for details.
|
||||
NOTE: You can safely ignore the above warning unless this call should not happen. Do not suppress it by adding an EXPECT_CALL() if you don't mean to enforce the call. See https://github.com/google/googletest/blob/main/docs/gmock_cook_book.md#knowing-when-to-expect-useoncall for details.
|
||||
[ OK ] GMockOutputTest.UninterestingCallWithDefaultAction
|
||||
[ RUN ] GMockOutputTest.ExplicitActionsRunOutWithDefaultAction
|
||||
|
||||
@@ -291,8 +308,9 @@ Stack trace:
|
||||
[ RUN ] GMockOutputTest.PrintsMatcher
|
||||
FILE:#: Failure
|
||||
Value of: (std::pair<int, bool>(42, true))
|
||||
Expected: is pair (is >= 48, true)
|
||||
Actual: (42, true) (of type std::pair<int, bool>)
|
||||
Expected: is pair (first: is >= 48, second: true)
|
||||
Actual: (42, true) (of type std::pair<int,bool>)
|
||||
|
||||
[ FAILED ] GMockOutputTest.PrintsMatcher
|
||||
[ FAILED ] GMockOutputTest.UnexpectedCall
|
||||
[ FAILED ] GMockOutputTest.UnexpectedCallToVoidFunction
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user