Skip to content

Commit 0467614

Browse files
committed
#19: * Memory leaks have been fixed in the await operator and its derivatives.
1 parent 34e87c0 commit 0467614

File tree

4 files changed

+67
-46
lines changed

4 files changed

+67
-46
lines changed

async_API.c

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -299,11 +299,10 @@ void async_waiting_callback_dispose(zend_async_event_callback_t *callback, zend_
299299

300300
await_callback->await_context = NULL;
301301

302-
if (await_context == NULL) {
303-
return;
302+
if (await_context != NULL) {
303+
await_context->dtor(await_context);
304304
}
305305

306-
await_context->dtor(await_context);
307306
await_callback->prev_dispose(callback, event);
308307
}
309308

@@ -322,9 +321,9 @@ void async_waiting_callback(
322321
// remove the callback from the event
323322
// We remove the callback because we treat all events
324323
// as FUTURE-type objects, where the trigger can be activated only once.
325-
callback->ref_count++;
324+
ZEND_ASYNC_EVENT_CALLBACK_ADD_REF(callback)
326325
event->del_callback(event, callback);
327-
callback->ref_count--;
326+
ZEND_ASYNC_EVENT_CALLBACK_DEC_REF(callback)
328327

329328
if (exception != NULL) {
330329
ZEND_ASYNC_EVENT_SET_EXCEPTION_HANDLED(event);
@@ -421,9 +420,9 @@ void async_waiting_cancellation_callback(
421420
async_await_context_t * await_context = await_callback->await_context;
422421

423422
await_context->resolved_count++;
424-
callback->ref_count++;
423+
ZEND_ASYNC_EVENT_CALLBACK_ADD_REF(callback)
425424
event->del_callback(event, callback);
426-
callback->ref_count--;
425+
ZEND_ASYNC_EVENT_CALLBACK_DEC_REF(callback)
427426

428427
if (exception != NULL) {
429428
ZEND_ASYNC_EVENT_SET_EXCEPTION_HANDLED(event);

tests/await/008-awaitFirstSuccess_basic.phpt

Lines changed: 2 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -25,36 +25,10 @@ $coroutines = [
2525
];
2626

2727
$result = awaitFirstSuccess($coroutines);
28-
var_dump($result);
29-
28+
echo "Result: {$result[0]}\n";
3029
echo "end\n";
3130
?>
3231
--EXPECTF--
3332
start
34-
array(2) {
35-
[0]=>
36-
string(7) "success"
37-
[1]=>
38-
array(1) {
39-
[0]=>
40-
object(RuntimeException)#%d (7) {
41-
["message":protected]=>
42-
string(11) "first error"
43-
["string":"Exception":private]=>
44-
string(0) ""
45-
["code":protected]=>
46-
int(0)
47-
["file":protected]=>
48-
string(%d) "%s"
49-
["line":protected]=>
50-
int(%d)
51-
["trace":"Exception":private]=>
52-
array(%d) {
53-
%a
54-
}
55-
["previous":"Exception":private]=>
56-
NULL
57-
}
58-
}
59-
}
33+
Result: success
6034
end

tests/curl/002-concurrent_requests.phpt

Lines changed: 32 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,6 @@ use function Async\awaitAll;
1212
$server = async_test_server_start();
1313

1414
function make_request($id, $server) {
15-
echo "Request $id: starting\n";
16-
1715
$ch = curl_init();
1816
curl_setopt($ch, CURLOPT_URL, "http://localhost:{$server->port}/");
1917
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
@@ -24,8 +22,14 @@ function make_request($id, $server) {
2422

2523
curl_close($ch);
2624

27-
echo "Request $id: completed (HTTP $http_code)\n";
28-
return "Request $id result: $response";
25+
return [
26+
'id' => $id,
27+
'response' => $response,
28+
'http_code' => $http_code,
29+
'start_msg' => "Request $id: starting",
30+
'complete_msg' => "Request $id: completed (HTTP $http_code)",
31+
'result_msg' => "Request $id result: $response"
32+
];
2933
}
3034

3135
echo "Test start\n";
@@ -39,8 +43,31 @@ $coroutines = [
3943

4044
$results = awaitAll($coroutines);
4145

46+
// Collect and sort messages
47+
$start_messages = [];
48+
$complete_messages = [];
49+
$result_messages = [];
50+
4251
foreach ($results as $result) {
43-
echo "Result: $result\n";
52+
$start_messages[] = $result['start_msg'];
53+
$complete_messages[] = $result['complete_msg'];
54+
$result_messages[] = "Result: " . $result['result_msg'];
55+
}
56+
57+
// Sort all messages by ID
58+
sort($start_messages);
59+
sort($complete_messages);
60+
sort($result_messages);
61+
62+
// Output in consistent order
63+
foreach ($start_messages as $msg) {
64+
echo $msg . "\n";
65+
}
66+
foreach ($complete_messages as $msg) {
67+
echo $msg . "\n";
68+
}
69+
foreach ($result_messages as $msg) {
70+
echo $msg . "\n";
4471
}
4572

4673
echo "Test end\n";

tests/curl/009-curl_with_coroutines.phpt

Lines changed: 27 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,6 @@ use function Async\awaitAll;
1313
$server = async_test_server_start();
1414

1515
function make_curl_request($server, $id) {
16-
echo "Coroutine $id: starting\n";
17-
1816
$ch = curl_init();
1917
curl_setopt($ch, CURLOPT_URL, "http://localhost:{$server->port}/");
2018
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
@@ -25,12 +23,12 @@ function make_curl_request($server, $id) {
2523

2624
curl_close($ch);
2725

28-
echo "Coroutine $id: completed (HTTP $http_code)\n";
29-
3026
return [
3127
'id' => $id,
3228
'response' => $response,
33-
'http_code' => $http_code
29+
'http_code' => $http_code,
30+
'start_msg' => "Coroutine $id: starting",
31+
'complete_msg' => "Coroutine $id: completed (HTTP $http_code)"
3432
];
3533
}
3634

@@ -45,8 +43,31 @@ $coroutines = [
4543

4644
$results = awaitAll($coroutines);
4745

46+
// Collect and sort messages
47+
$start_messages = [];
48+
$complete_messages = [];
49+
$result_messages = [];
50+
4851
foreach ($results as $result) {
49-
echo "Result {$result['id']}: {$result['response']}\n";
52+
$start_messages[] = $result['start_msg'];
53+
$complete_messages[] = $result['complete_msg'];
54+
$result_messages[] = "Result {$result['id']}: {$result['response']}";
55+
}
56+
57+
// Sort all messages by ID
58+
sort($start_messages);
59+
sort($complete_messages);
60+
sort($result_messages);
61+
62+
// Output in consistent order
63+
foreach ($start_messages as $msg) {
64+
echo $msg . "\n";
65+
}
66+
foreach ($complete_messages as $msg) {
67+
echo $msg . "\n";
68+
}
69+
foreach ($result_messages as $msg) {
70+
echo $msg . "\n";
5071
}
5172

5273
echo "Test end\n";

0 commit comments

Comments
 (0)