Skip to content

Commit 9645e1e

Browse files
committed
php#6: * Fixed GC behavior in the context of coroutines. Infinite garbage collection loop issue resolved.
1 parent 8fca959 commit 9645e1e

File tree

2 files changed

+25
-0
lines changed

2 files changed

+25
-0
lines changed

Zend/zend_async_API.h

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -294,6 +294,26 @@ struct _zend_async_microtask_s {
294294
uint32_t ref_count;
295295
};
296296

297+
#define ZEND_ASYNC_MICROTASK_ADD_REF(microtask) \
298+
do { \
299+
if (microtask != NULL) { \
300+
microtask->ref_count++; \
301+
} \
302+
} while (0)
303+
304+
#define ZEND_ASYNC_MICROTASK_RELEASE(microtask) \
305+
do { \
306+
if (microtask != NULL && microtask->ref_count > 1) { \
307+
microtask->ref_count--; \
308+
} else { \
309+
microtask->ref_count = 0; \
310+
if (microtask->dtor) { \
311+
microtask->dtor(microtask); \
312+
} \
313+
efree(microtask); \
314+
} \
315+
} while (0)
316+
297317
///////////////////////////////////////////////////////////////////
298318
/// Async iterator structures
299319
///////////////////////////////////////////////////////////////////

Zend/zend_gc.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1975,6 +1975,11 @@ static void zend_gc_collect_cycles_coroutine(void)
19751975

19761976
ZEND_ASYNC_ADD_MICROTASK(GC_G(microtask));
19771977
zend_gc_collect_cycles();
1978+
1979+
if (GC_G(microtask) != NULL) {
1980+
GC_G(microtask)->is_cancelled = true;
1981+
ZEND_ASYNC_MICROTASK_RELEASE(GC_G(microtask));
1982+
}
19781983
}
19791984

19801985
static zend_string* coroutine_info(zend_async_event_t *event)

0 commit comments

Comments
 (0)