]> granicus.if.org Git - php/commitdiff
Add crude memory limit to tracked alloc
authorNikita Popov <nikita.ppv@gmail.com>
Tue, 28 Jan 2020 11:20:00 +0000 (12:20 +0100)
committerNikita Popov <nikita.ppv@gmail.com>
Tue, 21 Apr 2020 08:44:15 +0000 (10:44 +0200)
Check whether the requested allocation size exceeds limit (rather
than the cumulative size).

This is useful to prevent allocations triggering OOM during fuzzing.

Zend/zend_alloc.c

index 24cd4373449d27ad4e4f386c0fae882689b6a998..753a8b830d4e37eaca1e1f30053e5f747061b35f 100644 (file)
@@ -2698,10 +2698,23 @@ ZEND_API void shutdown_memory_manager(int silent, int full_shutdown)
 #if ZEND_MM_CUSTOM
 static void *tracked_malloc(size_t size)
 {
+       zend_mm_heap *heap = AG(mm_heap);
+       if (size > heap->limit) {
+#if ZEND_DEBUG
+               zend_mm_safe_error(heap,
+                       "Allowed memory size of %zu bytes exhausted at %s:%d (tried to allocate %zu bytes)",
+                       heap->limit, "file", 0, size);
+#else
+               zend_mm_safe_error(heap,
+                       "Allowed memory size of %zu bytes exhausted (tried to allocate %zu bytes)",
+                       heap->limit, size);
+#endif
+       }
+
        void *ptr = __zend_malloc(size);
        zend_ulong h = ((uintptr_t) ptr) >> ZEND_MM_ALIGNMENT_LOG2;
        ZEND_ASSERT((void *) (uintptr_t) (h << ZEND_MM_ALIGNMENT_LOG2) == ptr);
-       zend_hash_index_add_empty_element(AG(mm_heap)->tracked_allocs, h);
+       zend_hash_index_add_empty_element(heap->tracked_allocs, h);
        return ptr;
 }
 
@@ -2742,6 +2755,9 @@ static void alloc_globals_ctor(zend_alloc_globals *alloc_globals)
                zend_mm_heap *mm_heap = alloc_globals->mm_heap = malloc(sizeof(zend_mm_heap));
                memset(mm_heap, 0, sizeof(zend_mm_heap));
                mm_heap->use_custom_heap = ZEND_MM_CUSTOM_HEAP_STD;
+               mm_heap->limit = ((size_t)Z_L(-1) >> (size_t)Z_L(1));
+               mm_heap->overflow = 0;
+
                if (!tracked) {
                        /* Use system allocator. */
                        mm_heap->custom_heap.std._malloc = __zend_malloc;