Bug #77194 [Opn]: php7ts.dll crashing when running embed

From: Date: Sun, 09 Dec 2018 17:02:50 +0000
Subject: Bug #77194 [Opn]: php7ts.dll crashing when running embed
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-218353@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=77194&edit=1

 ID:                 77194
 Updated by:         ab@php.net
 Reported by:        svbussww at 126 dot com
 Summary:            php7ts.dll crashing when running embed
 Status:             Open
 Type:               Bug
 Package:            Reproducible crash
 Operating System:   Windows 7
 PHP Version:        7.2.12
 Block user comment: N
 Private report:     N

 New Comment:

@jr at concept-br dot de, please post a backtrace.

Thanks.


Previous Comments:
------------------------------------------------------------------------
[2018-12-07 11:01:55] jr at concept-br dot de

Same Problem here also in 7.2.13 on Windows Server 2012 R2. We restart the apache service every hour
to "workaround" until a bugfix is released

------------------------------------------------------------------------
[2018-11-29 16:49:12] svbussww at 126 dot com

I have uploaded a fix.
Use _aligned_malloc and _aligned_free instead of unreliable VirtualAlloc and VirtualFree

------------------------------------------------------------------------
[2018-11-27 13:41:27] svbussww at 126 dot com

Fix the temporary plan

static void *zend_mm_chunk_alloc_int(size_t size, size_t alignment)
{
	void *ptr = zend_mm_mmap(size);

	if (ptr == NULL) {
		return NULL;
	} else if (ZEND_MM_ALIGNED_OFFSET(ptr, alignment) == 0) {
#ifdef MADV_HUGEPAGE
	    madvise(ptr, size, MADV_HUGEPAGE);
#endif
		return ptr;
	} else {
		size_t offset;

		/* chunk has to be aligned */
		zend_mm_munmap(ptr, size);
		LOOP:;
		ptr = zend_mm_mmap(size + alignment - REAL_PAGE_SIZE);
		if (ptr == NULL) return NULL;
#ifdef _WIN32
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		zend_mm_munmap(ptr, size + alignment - REAL_PAGE_SIZE);
		ptr = zend_mm_mmap_fixed((void*)((char*)ptr + (alignment - offset)), size);
		if(ptr == NULL) goto LOOP;
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		if (offset != 0) {
			zend_mm_munmap(ptr, size);
			return NULL;
		}
		return ptr;
#else
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		if (offset != 0) {
			offset = alignment - offset;
			zend_mm_munmap(ptr, offset);
			ptr = (char*)ptr + offset;
			alignment -= offset;
		}
		if (alignment > REAL_PAGE_SIZE) {
			zend_mm_munmap((char*)ptr + size, alignment - REAL_PAGE_SIZE);
		}
# ifdef MADV_HUGEPAGE
	    madvise(ptr, size, MADV_HUGEPAGE);
# endif
#endif
		return ptr;
	}
}

------------------------------------------------------------------------
[2018-11-27 12:46:17] svbussww at 126 dot com

The bug has been found

file Zend/zend_alloc.c
function zend_mm_chunk_alloc_int
zend_mm_mmap After not aligned
zend_mm_mmap_fixed Call failed is return 0

The cause of the bug
zend_mm_mmap The allocated memory address is released. In the case of multithreading, it may be
preempted by other threads.
This causes the subsequent zend_mm_mmap_fixed function to allocate memory and cause the program to
crash.

Temporary solution

static void *zend_mm_chunk_alloc_int(size_t size, size_t alignment)
{
	LOOP:;
	void *ptr = zend_mm_mmap(size);

	if (ptr == NULL) {
		return NULL;
	} else if (ZEND_MM_ALIGNED_OFFSET(ptr, alignment) == 0) {
#ifdef MADV_HUGEPAGE
	    madvise(ptr, size, MADV_HUGEPAGE);
#endif
		return ptr;
	} else {
		size_t offset;

		/* chunk has to be aligned */
		zend_mm_munmap(ptr, size);
		ptr = zend_mm_mmap(size + alignment - REAL_PAGE_SIZE);
#ifdef _WIN32
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		zend_mm_munmap(ptr, size + alignment - REAL_PAGE_SIZE);
		ptr = zend_mm_mmap_fixed((void*)((char*)ptr + (alignment - offset)), size);
		if(ptr == NULL) goto LOOP;
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		if (offset != 0) {
			zend_mm_munmap(ptr, size);
			return NULL;
		}
		return ptr;
#else
		offset = ZEND_MM_ALIGNED_OFFSET(ptr, alignment);
		if (offset != 0) {
			offset = alignment - offset;
			zend_mm_munmap(ptr, offset);
			ptr = (char*)ptr + offset;
			alignment -= offset;
		}
		if (alignment > REAL_PAGE_SIZE) {
			zend_mm_munmap((char*)ptr + size, alignment - REAL_PAGE_SIZE);
		}
# ifdef MADV_HUGEPAGE
	    madvise(ptr, size, MADV_HUGEPAGE);
# endif
#endif
		return ptr;
	}
}

I hope the development team can solve this bug as soon as possible.

------------------------------------------------------------------------
[2018-11-27 12:03:08] svbussww at 126 dot com

Can't initialize heap: [0x000001e7] Attempt to access invalid address.

Tracking source code is generated from zend_alloc.c

in zend_mm_mmap_fixed
VirtualAlloc Error return NULL

------------------------------------------------------------------------


The remainder of the comments for this report are too long. To view
the rest of the comments, please view the bug report online at

    https://bugs.php.net/bug.php?id=77194


--
Edit this bug report at https://bugs.php.net/bug.php?id=77194&edit=1


Thread (22 messages)

« previous php.bugs (#218353) next »