|
Lines 749-756
size_t VM::updateReservedZoneSize(size_t
Source/JavaScriptCore/runtime/VM.cpp_sec1
|
| 749 |
return oldReservedZoneSize; |
749 |
return oldReservedZoneSize; |
| 750 |
} |
750 |
} |
| 751 |
|
751 |
|
|
|
752 |
#if PLATFORM(WIN) |
| 753 |
// On Windows the reserved stack space consists of committed memory, a guard page, and uncommitted memory, |
| 754 |
// where the guard page is a barrier between committed and uncommitted memory. |
| 755 |
// When data from the guard page is read or written, the guard page is moved, and memory is committed. |
| 756 |
// This is how the system grows the stack. |
| 757 |
// When using the C stack on Windows we need to precommit the needed stack space. |
| 758 |
// Otherwise we might crash later if we access uncommitted stack memory. |
| 759 |
// This can happen if we allocate stack space larger than the page guard size (4K). |
| 760 |
// The system does not get the chance to move the guard page, and commit more memory, |
| 761 |
// and we crash if uncommitted memory is accessed. |
| 762 |
// The MSVC compiler fixes this by inserting a call to the _chkstk() function, |
| 763 |
// when needed, see http://support.microsoft.com/kb/100775. |
| 764 |
|
| 765 |
static void preCommitStackMemory(void* stackLimit) |
| 766 |
{ |
| 767 |
MEMORY_BASIC_INFORMATION uncommittedMemory; |
| 768 |
if (VirtualQuery(stackLimit, &uncommittedMemory, sizeof(uncommittedMemory)) > 0) |
| 769 |
if (uncommittedMemory.State == MEM_RESERVE) { |
| 770 |
int size = uncommittedMemory.RegionSize; |
| 771 |
// Commit memory |
| 772 |
OSAllocator::commit(stackLimit, size, true, false); |
| 773 |
|
| 774 |
// Move guard page |
| 775 |
MEMORY_BASIC_INFORMATION guardPage; |
| 776 |
char* guardPagePointer = reinterpret_cast<char*>(stackLimit) + size; |
| 777 |
if (VirtualQuery(guardPagePointer, &guardPage, sizeof(guardPage)) > 0) { |
| 778 |
ASSERT(guardPage.Protect & PAGE_GUARD); |
| 779 |
DWORD oldProtect; |
| 780 |
// Remove guard flag from old guard page |
| 781 |
BOOL retval = VirtualProtect(guardPagePointer, guardPage.RegionSize, PAGE_READWRITE, &oldProtect); |
| 782 |
ASSERT(retval); |
| 783 |
char* newGuardPagePointer = reinterpret_cast<char*>(stackLimit) - guardPage.RegionSize; |
| 784 |
// Commit new guard page |
| 785 |
OSAllocator::commit(newGuardPagePointer, guardPage.RegionSize, true, false); |
| 786 |
// Set guard flag on new guard page |
| 787 |
retval = VirtualProtect(newGuardPagePointer, guardPage.RegionSize, PAGE_READWRITE | PAGE_GUARD, &oldProtect); |
| 788 |
ASSERT(retval); |
| 789 |
} |
| 790 |
} |
| 791 |
} |
| 792 |
#endif |
| 793 |
|
| 752 |
inline void VM::updateStackLimit() |
794 |
inline void VM::updateStackLimit() |
| 753 |
{ |
795 |
{ |
|
|
796 |
#if PLATFORM(WIN) |
| 797 |
void* lastStackLimit = m_stackLimit; |
| 798 |
#endif |
| 799 |
|
| 754 |
if (m_stackPointerAtVMEntry) { |
800 |
if (m_stackPointerAtVMEntry) { |
| 755 |
ASSERT(wtfThreadData().stack().isGrowingDownward()); |
801 |
ASSERT(wtfThreadData().stack().isGrowingDownward()); |
| 756 |
char* startOfStack = reinterpret_cast<char*>(m_stackPointerAtVMEntry); |
802 |
char* startOfStack = reinterpret_cast<char*>(m_stackPointerAtVMEntry); |
|
Lines 769-774
inline void VM::updateStackLimit()
Source/JavaScriptCore/runtime/VM.cpp_sec2
|
| 769 |
#endif |
815 |
#endif |
| 770 |
} |
816 |
} |
| 771 |
|
817 |
|
|
|
818 |
#if PLATFORM(WIN) |
| 819 |
if (lastStackLimit != m_stackLimit) |
| 820 |
preCommitStackMemory(m_stackLimit); |
| 821 |
#endif |
| 772 |
} |
822 |
} |
| 773 |
|
823 |
|
| 774 |
#if ENABLE(FTL_JIT) |
824 |
#if ENABLE(FTL_JIT) |