Skip to content

Commit 0de5e9f

Browse files
committed
added perfect-forwarding test on stack object.
1 parent b7a3d4f commit 0de5e9f

File tree

1 file changed

+152
-27
lines changed

1 file changed

+152
-27
lines changed

CxxRTLTestApplication/src/FunctionalityTests/PerfectForwardingTests.cpp

Lines changed: 152 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -30,12 +30,53 @@ using namespace test_mirror;
3030
namespace rtl_tests
3131
{
3232
/**
33-
* @brief Test that a non-const L-value reference binds only to the corresponding overload.
33+
* @brief Test that an R-value reference binds only to the corresponding overload.
3434
*
3535
* This test verifies that the reflection system correctly identifies and invokes the method
36-
* overload that accepts a non-const L-value reference (`std::string&`).
36+
* overload that accepts an R-value reference (`std::string&&`).
3737
*/
38-
TEST(PerfectForwardingTest, non_const_lvalue_ref_only_binds_to_non_const_lvaue_ref_overload_on_heap)
38+
TEST(PerfectForwardingTest, overload_resolution_with_rvalue_ref_on_heap_object)
39+
{
40+
{
41+
// Retrieve the metadata for the "Animal" class.
42+
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);
43+
ASSERT_TRUE(classAnimal);
44+
45+
// Retrieve the "setAnimalName" method.
46+
optional<Method> setAnimalName = classAnimal->getMethod(animal::str_setAnimalName);
47+
ASSERT_TRUE(setAnimalName);
48+
49+
// Create an instance of the "Animal" class.
50+
auto [err0, animal] = classAnimal->create<alloc::Heap>();
51+
EXPECT_TRUE(err0 == error::None);
52+
ASSERT_FALSE(animal.isEmpty());
53+
54+
// Verify that the method has the correct signature for an R-value reference.
55+
const auto& isValid = setAnimalName->hasSignature<std::string&&>();
56+
EXPECT_TRUE(isValid);
57+
58+
// Invoke the method with an R-value reference.
59+
auto [err1, ret1] = setAnimalName->bind<std::string&&>(animal).call(animal::NAME);
60+
61+
EXPECT_TRUE(err1 == error::None);
62+
ASSERT_TRUE(ret1.isEmpty());
63+
64+
// Validate the behavior of the method.
65+
EXPECT_TRUE(animal::test_method_setAnimalName_rvalue_args(animal));
66+
}
67+
68+
// Ensure that all instances are cleaned up.
69+
EXPECT_TRUE(animal::assert_zero_instance_count());
70+
ASSERT_TRUE(rtl::getRtlManagedHeapInstanceCount() == 0);
71+
}
72+
73+
74+
/**
75+
* @brief Test that a non-const L-value reference binds only to the corresponding overload.
76+
*
77+
* This test verifies that the reflection system correctly identifies and invokes the method
78+
* overload that accepts a non-const L-value reference (`std::string&`). */
79+
TEST(PerfectForwardingTest, overload_resolution_with_non_const_lvaue_ref_on_heap_object)
3980
{
4081
{
4182
// Retrieve the metadata for the "Animal" class.
@@ -72,13 +113,12 @@ namespace rtl_tests
72113
}
73114

74115

75-
/**
76-
* @brief Test that an R-value reference binds only to the corresponding overload.
77-
*
78-
* This test verifies that the reflection system correctly identifies and invokes the method
79-
* overload that accepts an R-value reference (`std::string&&`).
80-
*/
81-
TEST(PerfectForwardingTest, rvalue_ref_only_binds_to_rvalue_ref_overload_on_heap)
116+
/*
117+
* @brief Test that a const L-value reference binds only to the corresponding overload.
118+
*
119+
* This test verifies that the reflection system correctly identifies and invokes the method
120+
* overload that accepts a const L-value reference (`const std::string&`). */
121+
TEST(PerfectForwardingTest, overload_resolution_with_const_lvaue_ref_on_heap_object)
82122
{
83123
{
84124
// Retrieve the metadata for the "Animal" class.
@@ -94,6 +134,50 @@ namespace rtl_tests
94134
EXPECT_TRUE(err0 == error::None);
95135
ASSERT_FALSE(animal.isEmpty());
96136

137+
// Verify that the method has the correct signature for a const L-value reference.
138+
const auto& isValid = setAnimalName->hasSignature<const std::string&>();
139+
EXPECT_TRUE(isValid);
140+
141+
// Invoke the method with a const L-value reference.
142+
const auto nameStr = std::string(animal::NAME);
143+
auto [err1, ret1] = setAnimalName->bind<const std::string&>(animal).call(nameStr);
144+
145+
EXPECT_TRUE(err1 == error::None);
146+
EXPECT_TRUE(ret1.isEmpty());
147+
148+
// Validate the behavior of the method.
149+
EXPECT_TRUE(animal::test_method_setAnimalName_const_lvalue_ref_args(animal));
150+
}
151+
152+
// Ensure that all instances are cleaned up.
153+
EXPECT_TRUE(animal::assert_zero_instance_count());
154+
ASSERT_TRUE(rtl::getRtlManagedHeapInstanceCount() == 0);
155+
}
156+
157+
158+
159+
/**
160+
* @brief Test that an R-value reference binds only to the corresponding overload.
161+
*
162+
* This test verifies that the reflection system correctly identifies and invokes the method
163+
* overload that accepts an R-value reference (`std::string&&`).
164+
*/
165+
TEST(PerfectForwardingTest, overload_resolution_with_rvalue_ref_on_stack_object)
166+
{
167+
{
168+
// Retrieve the metadata for the "Animal" class.
169+
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);
170+
ASSERT_TRUE(classAnimal);
171+
172+
// Retrieve the "setAnimalName" method.
173+
optional<Method> setAnimalName = classAnimal->getMethod(animal::str_setAnimalName);
174+
ASSERT_TRUE(setAnimalName);
175+
176+
// Create an instance of the "Animal" class.
177+
auto [err0, animal] = classAnimal->create<alloc::Stack>();
178+
EXPECT_TRUE(err0 == error::None);
179+
ASSERT_FALSE(animal.isEmpty());
180+
97181
// Verify that the method has the correct signature for an R-value reference.
98182
const auto& isValid = setAnimalName->hasSignature<std::string&&>();
99183
EXPECT_TRUE(isValid);
@@ -115,12 +199,11 @@ namespace rtl_tests
115199

116200

117201
/**
118-
* @brief Test that a const L-value reference binds only to the corresponding overload.
119-
*
120-
* This test verifies that the reflection system correctly identifies and invokes the method
121-
* overload that accepts a const L-value reference (`const std::string&`).
122-
*/
123-
TEST(PerfectForwardingTest, const_lvalue_ref_only_binds_to_const_lvaue_ref_overload_on_heap)
202+
* @brief Test that a non-const L-value reference binds only to the corresponding overload.
203+
*
204+
* This test verifies that the reflection system correctly identifies and invokes the method
205+
* overload that accepts a non-const L-value reference (`std::string&`). */
206+
TEST(PerfectForwardingTest, overload_resolution_with_non_const_lvaue_ref_on_stack_object)
124207
{
125208
{
126209
// Retrieve the metadata for the "Animal" class.
@@ -132,7 +215,49 @@ namespace rtl_tests
132215
ASSERT_TRUE(setAnimalName);
133216

134217
// Create an instance of the "Animal" class.
135-
auto [err0, animal] = classAnimal->create<alloc::Heap>();
218+
auto [err0, animal] = classAnimal->create<alloc::Stack>();
219+
EXPECT_TRUE(err0 == error::None);
220+
ASSERT_FALSE(animal.isEmpty());
221+
222+
// Verify that the method has the correct signature for a non-const L-value reference.
223+
const auto& isValid = setAnimalName->hasSignature<std::string&>();
224+
EXPECT_TRUE(isValid);
225+
226+
// Invoke the method with a non-const L-value reference.
227+
auto nameStr = std::string(animal::NAME);
228+
auto [err1, ret1] = setAnimalName->bind<std::string&>(animal).call(nameStr);
229+
230+
EXPECT_TRUE(err1 == error::None);
231+
ASSERT_TRUE(ret1.isEmpty());
232+
233+
// Validate the behavior of the method.
234+
EXPECT_TRUE(animal::test_method_setAnimalName_non_const_lvalue_ref_args(animal));
235+
}
236+
237+
// Ensure that all instances are cleaned up.
238+
EXPECT_TRUE(animal::assert_zero_instance_count());
239+
ASSERT_TRUE(rtl::getRtlManagedHeapInstanceCount() == 0);
240+
}
241+
242+
243+
/*
244+
* @brief Test that a const L-value reference binds only to the corresponding overload.
245+
*
246+
* This test verifies that the reflection system correctly identifies and invokes the method
247+
* overload that accepts a const L-value reference (`const std::string&`). */
248+
TEST(PerfectForwardingTest, overload_resolution_with_const_lvaue_ref_on_stack_object)
249+
{
250+
{
251+
// Retrieve the metadata for the "Animal" class.
252+
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);
253+
ASSERT_TRUE(classAnimal);
254+
255+
// Retrieve the "setAnimalName" method.
256+
optional<Method> setAnimalName = classAnimal->getMethod(animal::str_setAnimalName);
257+
ASSERT_TRUE(setAnimalName);
258+
259+
// Create an instance of the "Animal" class.
260+
auto [err0, animal] = classAnimal->create<alloc::Stack>();
136261
EXPECT_TRUE(err0 == error::None);
137262
ASSERT_FALSE(animal.isEmpty());
138263

@@ -157,7 +282,7 @@ namespace rtl_tests
157282
}
158283

159284

160-
TEST(PerfectForwardingTest, static_fn_const_lvalue_ref_only_binds_to_const_lvaue_ref_overload)
285+
TEST(PerfectForwardingTest, static_fn_overload_resolution_with_rvalue_ref)
161286
{
162287
{
163288
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);
@@ -166,26 +291,25 @@ namespace rtl_tests
166291
optional<Method> updateZooKeeper = classAnimal->getMethod(animal::str_updateZooKeeper);
167292
ASSERT_TRUE(updateZooKeeper);
168293

169-
const auto& isValid = updateZooKeeper->hasSignature<const std::string&>();
294+
const auto& isValid = updateZooKeeper->hasSignature<std::string&&>();
170295
EXPECT_TRUE(isValid);
171296

172-
const auto zookeeper = std::string(animal::ZOO_KEEPER);
173-
auto [err, ret] = updateZooKeeper->bind<const std::string&>().call(zookeeper);
297+
auto [err, ret] = updateZooKeeper->bind<std::string&&>().call(animal::ZOO_KEEPER);
174298

175299
EXPECT_TRUE(err == error::None);
176300
ASSERT_FALSE(ret.isEmpty());
177301
EXPECT_TRUE(ret.canViewAs<string>());
178302

179303
const string& retStr = ret.view<string>()->get();
180-
EXPECT_TRUE(animal::test_method_updateZooKeeper<const std::string&>(retStr));
304+
EXPECT_TRUE(animal::test_method_updateZooKeeper<std::string&&>(retStr));
181305
}
182306

183307
EXPECT_TRUE(animal::assert_zero_instance_count());
184308
ASSERT_TRUE(rtl::getRtlManagedHeapInstanceCount() == 0);
185309
}
186310

187311

188-
TEST(PerfectForwardingTest, static_fn_rvalue_ref_only_binds_to_rvalue_ref_overload)
312+
TEST(PerfectForwardingTest, static_fn_overload_resolution_with_const_lvalue_ref)
189313
{
190314
{
191315
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);
@@ -194,25 +318,26 @@ namespace rtl_tests
194318
optional<Method> updateZooKeeper = classAnimal->getMethod(animal::str_updateZooKeeper);
195319
ASSERT_TRUE(updateZooKeeper);
196320

197-
const auto& isValid = updateZooKeeper->hasSignature<std::string&&>();
321+
const auto& isValid = updateZooKeeper->hasSignature<const std::string&>();
198322
EXPECT_TRUE(isValid);
199323

200-
auto [err, ret] = updateZooKeeper->bind<std::string&&>().call(animal::ZOO_KEEPER);
324+
const auto zookeeper = std::string(animal::ZOO_KEEPER);
325+
auto [err, ret] = updateZooKeeper->bind<const std::string&>().call(zookeeper);
201326

202327
EXPECT_TRUE(err == error::None);
203328
ASSERT_FALSE(ret.isEmpty());
204329
EXPECT_TRUE(ret.canViewAs<string>());
205330

206331
const string& retStr = ret.view<string>()->get();
207-
EXPECT_TRUE(animal::test_method_updateZooKeeper<std::string&&>(retStr));
332+
EXPECT_TRUE(animal::test_method_updateZooKeeper<const std::string&>(retStr));
208333
}
209334

210335
EXPECT_TRUE(animal::assert_zero_instance_count());
211336
ASSERT_TRUE(rtl::getRtlManagedHeapInstanceCount() == 0);
212337
}
213338

214339

215-
TEST(PerfectForwardingTest, static_fn_non_const_lvalue_ref_only_binds_to_non_const_lvaue_ref_overload)
340+
TEST(PerfectForwardingTest, static_fn_overload_resolution_with_non_const_lvalue_ref)
216341
{
217342
{
218343
optional<Record> classAnimal = cxx::mirror().getRecord(animal::class_);

0 commit comments

Comments
 (0)