Skip to content

Commit c035298

Browse files
committed
Free cached chunks when the requested memory limit is above real usage
1 parent 1d48da6 commit c035298

File tree

1 file changed

+14
-1
lines changed

1 file changed

+14
-1
lines changed

Zend/zend_alloc.c

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2660,10 +2660,23 @@ ZEND_API char* ZEND_FASTCALL zend_strndup(const char *s, size_t length)
26602660
ZEND_API zend_result zend_set_memory_limit_ex(size_t memory_limit)
26612661
{
26622662
#if ZEND_MM_LIMIT
2663+
zend_mm_heap *heap = AG(mm_heap);
2664+
26632665
if (memory_limit < ZEND_MM_CHUNK_SIZE) {
26642666
memory_limit = ZEND_MM_CHUNK_SIZE;
26652667
}
2666-
if (UNEXPECTED(memory_limit < AG(mm_heap)->real_size)) {
2668+
if (UNEXPECTED(memory_limit < heap->real_size)) {
2669+
if (memory_limit >= heap->real_size - heap->cached_chunks_count * ZEND_MM_CHUNK_SIZE) {
2670+
/* free some cached chunks to fit into new memory limit */
2671+
do {
2672+
zend_mm_chunk *p = heap->cached_chunks;
2673+
heap->cached_chunks = p->next;
2674+
zend_mm_chunk_free(heap, p, ZEND_MM_CHUNK_SIZE);
2675+
heap->cached_chunks_count--;
2676+
heap->real_size -= ZEND_MM_CHUNK_SIZE;
2677+
} while (memory_limit < heap->real_size);
2678+
return SUCCESS;
2679+
}
26672680
return FAILURE;
26682681
}
26692682
AG(mm_heap)->limit = memory_limit;

0 commit comments

Comments
 (0)