@@ -39,6 +39,11 @@ class CoroTask_test : public beast::unit_test::suite
3939 }
4040 };
4141
42+ // NOTE: All coroutine lambdas passed to postCoroTask use explicit
43+ // pointer-by-value captures instead of [&] to work around a GCC 14
44+ // bug where reference captures in coroutine lambdas are corrupted
45+ // in the coroutine frame.
46+
4247 // Test: CoroTask<void> runs to completion
4348 void
4449 testVoidCompletion ()
@@ -55,8 +60,8 @@ class CoroTask_test : public beast::unit_test::suite
5560
5661 gate g;
5762 auto runner = env.app ().getJobQueue ().postCoroTask (
58- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > {
59- g. signal ();
63+ jtCLIENT, " CoroTaskTest" , [gp = &g ](auto ) -> CoroTask<void > {
64+ gp-> signal ();
6065 co_return ;
6166 });
6267 BEAST_EXPECT (runner);
@@ -83,11 +88,13 @@ class CoroTask_test : public beast::unit_test::suite
8388 gate g1, g2;
8489 std::shared_ptr<JobQueue::CoroTaskRunner> r;
8590 auto runner = env.app ().getJobQueue ().postCoroTask (
86- jtCLIENT, " CoroTaskTest" , [&](auto runner) -> CoroTask<void > {
87- r = runner;
88- g1.signal ();
91+ jtCLIENT,
92+ " CoroTaskTest" ,
93+ [rp = &r, g1p = &g1, g2p = &g2](auto runner) -> CoroTask<void > {
94+ *rp = runner;
95+ g1p->signal ();
8996 co_await runner->suspend ();
90- g2. signal ();
97+ g2p-> signal ();
9198 co_return ;
9299 });
93100 BEAST_EXPECT (runner);
@@ -115,10 +122,10 @@ class CoroTask_test : public beast::unit_test::suite
115122
116123 gate g;
117124 env.app ().getJobQueue ().postCoroTask (
118- jtCLIENT, " CoroTaskTest" , [& ](auto runner) -> CoroTask<void > {
125+ jtCLIENT, " CoroTaskTest" , [gp = &g ](auto runner) -> CoroTask<void > {
119126 runner->post ();
120127 co_await runner->suspend ();
121- g. signal ();
128+ gp-> signal ();
122129 co_return ;
123130 });
124131 BEAST_EXPECT (g.wait_for (5s));
@@ -141,13 +148,13 @@ class CoroTask_test : public beast::unit_test::suite
141148 gate g;
142149 int step = 0 ;
143150 env.app ().getJobQueue ().postCoroTask (
144- jtCLIENT, " CoroTaskTest" , [& ](auto runner) -> CoroTask<void > {
145- step = 1 ;
151+ jtCLIENT, " CoroTaskTest" , [sp = &step, gp = &g ](auto runner) -> CoroTask<void > {
152+ *sp = 1 ;
146153 co_await JobQueueAwaiter{runner};
147- step = 2 ;
154+ *sp = 2 ;
148155 co_await JobQueueAwaiter{runner};
149- step = 3 ;
150- g. signal ();
156+ *sp = 3 ;
157+ gp-> signal ();
151158 co_return ;
152159 });
153160 BEAST_EXPECT (g.wait_for (5s));
@@ -185,20 +192,23 @@ class CoroTask_test : public beast::unit_test::suite
185192
186193 for (int i = 0 ; i < N; ++i)
187194 {
188- jq.postCoroTask (jtCLIENT, " CoroTaskTest" , [&, id = i](auto runner) -> CoroTask<void > {
189- a[id] = runner;
190- g.signal ();
191- co_await runner->suspend ();
192-
193- this ->BEAST_EXPECT (*lv == -1 );
194- *lv = id;
195- this ->BEAST_EXPECT (*lv == id);
196- g.signal ();
197- co_await runner->suspend ();
198-
199- this ->BEAST_EXPECT (*lv == id);
200- co_return ;
201- });
195+ jq.postCoroTask (
196+ jtCLIENT,
197+ " CoroTaskTest" ,
198+ [this , ap = &a, gp = &g, lvp = &lv, id = i](auto runner) -> CoroTask<void > {
199+ (*ap)[id] = runner;
200+ gp->signal ();
201+ co_await runner->suspend ();
202+
203+ this ->BEAST_EXPECT (**lvp == -1 );
204+ **lvp = id;
205+ this ->BEAST_EXPECT (**lvp == id);
206+ gp->signal ();
207+ co_await runner->suspend ();
208+
209+ this ->BEAST_EXPECT (**lvp == id);
210+ co_return ;
211+ });
202212 BEAST_EXPECT (g.wait_for (5s));
203213 a[i]->join ();
204214 }
@@ -238,8 +248,8 @@ class CoroTask_test : public beast::unit_test::suite
238248
239249 gate g;
240250 auto runner = env.app ().getJobQueue ().postCoroTask (
241- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > {
242- g. signal ();
251+ jtCLIENT, " CoroTaskTest" , [gp = &g ](auto ) -> CoroTask<void > {
252+ gp-> signal ();
243253 throw std::runtime_error (" test exception" );
244254 co_return ;
245255 });
@@ -269,16 +279,18 @@ class CoroTask_test : public beast::unit_test::suite
269279 int counter = 0 ;
270280 std::shared_ptr<JobQueue::CoroTaskRunner> r;
271281 auto runner = env.app ().getJobQueue ().postCoroTask (
272- jtCLIENT, " CoroTaskTest" , [&](auto runner) -> CoroTask<void > {
273- r = runner;
274- ++counter;
275- g.signal ();
282+ jtCLIENT,
283+ " CoroTaskTest" ,
284+ [rp = &r, cp = &counter, gp = &g](auto runner) -> CoroTask<void > {
285+ *rp = runner;
286+ ++(*cp);
287+ gp->signal ();
276288 co_await runner->suspend ();
277- ++counter ;
278- g. signal ();
289+ ++(*cp) ;
290+ gp-> signal ();
279291 co_await runner->suspend ();
280- ++counter ;
281- g. signal ();
292+ ++(*cp) ;
293+ gp-> signal ();
282294 co_return ;
283295 });
284296 BEAST_EXPECT (runner);
@@ -316,10 +328,10 @@ class CoroTask_test : public beast::unit_test::suite
316328 gate g;
317329 int result = 0 ;
318330 auto runner = env.app ().getJobQueue ().postCoroTask (
319- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > {
331+ jtCLIENT, " CoroTaskTest" , [rp = &result, gp = &g ](auto ) -> CoroTask<void > {
320332 auto inner = []() -> CoroTask<int > { co_return 42 ; };
321- result = co_await inner ();
322- g. signal ();
333+ *rp = co_await inner ();
334+ gp-> signal ();
323335 co_return ;
324336 });
325337 BEAST_EXPECT (runner);
@@ -346,7 +358,7 @@ class CoroTask_test : public beast::unit_test::suite
346358 gate g;
347359 bool caught = false ;
348360 auto runner = env.app ().getJobQueue ().postCoroTask (
349- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > {
361+ jtCLIENT, " CoroTaskTest" , [cp = &caught, gp = &g ](auto ) -> CoroTask<void > {
350362 auto inner = []() -> CoroTask<int > {
351363 throw std::runtime_error (" inner error" );
352364 co_return 0 ;
@@ -357,9 +369,9 @@ class CoroTask_test : public beast::unit_test::suite
357369 }
358370 catch (std::runtime_error const & e)
359371 {
360- caught = true ;
372+ *cp = true ;
361373 }
362- g. signal ();
374+ gp-> signal ();
363375 co_return ;
364376 });
365377 BEAST_EXPECT (runner);
@@ -386,14 +398,14 @@ class CoroTask_test : public beast::unit_test::suite
386398 gate g;
387399 int result = 0 ;
388400 auto runner = env.app ().getJobQueue ().postCoroTask (
389- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > {
401+ jtCLIENT, " CoroTaskTest" , [rp = &result, gp = &g ](auto ) -> CoroTask<void > {
390402 auto add = [](int a, int b) -> CoroTask<int > { co_return a + b; };
391- auto mul = [& ](int a, int b) -> CoroTask<int > {
403+ auto mul = [add ](int a, int b) -> CoroTask<int > {
392404 int sum = co_await add (a, b);
393405 co_return sum * 2 ;
394406 };
395- result = co_await mul (3 , 4 );
396- g. signal ();
407+ *rp = co_await mul (3 , 4 );
408+ gp-> signal ();
397409 co_return ;
398410 });
399411 BEAST_EXPECT (runner);
@@ -421,7 +433,7 @@ class CoroTask_test : public beast::unit_test::suite
421433 env.app ().getJobQueue ().stop ();
422434
423435 auto runner = env.app ().getJobQueue ().postCoroTask (
424- jtCLIENT, " CoroTaskTest" , [& ](auto ) -> CoroTask<void > { co_return ; });
436+ jtCLIENT, " CoroTaskTest" , [](auto ) -> CoroTask<void > { co_return ; });
425437 BEAST_EXPECT (!runner);
426438 }
427439
0 commit comments