OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "platform/heap/StackFrameDepth.h" | 5 #include "platform/heap/StackFrameDepth.h" |
6 | 6 |
7 #include "public/platform/Platform.h" | 7 #include "public/platform/Platform.h" |
8 | 8 |
9 #if OS(WIN) | 9 #if OS(WIN) |
10 #include <stddef.h> | 10 #include <stddef.h> |
11 #include <windows.h> | 11 #include <windows.h> |
12 #include <winnt.h> | 12 #include <winnt.h> |
13 #elif defined(__GLIBC__) | 13 #elif defined(__GLIBC__) |
14 extern "C" void* __libc_stack_end; // NOLINT | 14 extern "C" void* __libc_stack_end; // NOLINT |
15 #endif | 15 #endif |
16 | 16 |
17 namespace blink { | 17 namespace blink { |
18 | 18 |
19 static const char* s_avoidOptimization = nullptr; | 19 static const char* s_avoidOptimization = nullptr; |
20 | 20 |
21 // NEVER_INLINE ensures that |dummy| array on configureLimit() is not optimized
away, | 21 // NEVER_INLINE ensures that |dummy| array on configureLimit() is not optimized |
22 // and the stack frame base register is adjusted |kSafeStackFrameSize|. | 22 // away, and the stack frame base register is adjusted |kSafeStackFrameSize|. |
23 NEVER_INLINE static uintptr_t currentStackFrameBaseOnCallee(const char* dummy) { | 23 NEVER_INLINE static uintptr_t currentStackFrameBaseOnCallee(const char* dummy) { |
24 s_avoidOptimization = dummy; | 24 s_avoidOptimization = dummy; |
25 return StackFrameDepth::currentStackFrame(); | 25 return StackFrameDepth::currentStackFrame(); |
26 } | 26 } |
27 | 27 |
28 uintptr_t StackFrameDepth::getFallbackStackLimit() { | 28 uintptr_t StackFrameDepth::getFallbackStackLimit() { |
29 // Allocate an |kSafeStackFrameSize|-sized object on stack and query | 29 // Allocate an |kSafeStackFrameSize|-sized object on stack and query |
30 // stack frame base after it. | 30 // stack frame base after it. |
31 char dummy[kSafeStackFrameSize]; | 31 char dummy[kSafeStackFrameSize]; |
32 | 32 |
(...skipping 12 matching lines...) Expand all Loading... |
45 } | 45 } |
46 | 46 |
47 static const int kStackRoomSize = 1024; | 47 static const int kStackRoomSize = 1024; |
48 | 48 |
49 Address stackBase = reinterpret_cast<Address>(getStackStart()); | 49 Address stackBase = reinterpret_cast<Address>(getStackStart()); |
50 RELEASE_ASSERT(stackSize > static_cast<const size_t>(kStackRoomSize)); | 50 RELEASE_ASSERT(stackSize > static_cast<const size_t>(kStackRoomSize)); |
51 size_t stackRoom = stackSize - kStackRoomSize; | 51 size_t stackRoom = stackSize - kStackRoomSize; |
52 RELEASE_ASSERT(stackBase > reinterpret_cast<Address>(stackRoom)); | 52 RELEASE_ASSERT(stackBase > reinterpret_cast<Address>(stackRoom)); |
53 m_stackFrameLimit = reinterpret_cast<uintptr_t>(stackBase - stackRoom); | 53 m_stackFrameLimit = reinterpret_cast<uintptr_t>(stackBase - stackRoom); |
54 | 54 |
55 // If current stack use is already exceeding estimated limit, mark as disabled
. | 55 // If current stack use is already exceeding estimated limit, mark as |
| 56 // disabled. |
56 if (!isSafeToRecurse()) | 57 if (!isSafeToRecurse()) |
57 disableStackLimit(); | 58 disableStackLimit(); |
58 } | 59 } |
59 | 60 |
60 size_t StackFrameDepth::getUnderestimatedStackSize() { | 61 size_t StackFrameDepth::getUnderestimatedStackSize() { |
61 // FIXME: ASAN bot uses a fake stack as a thread stack frame, | 62 // FIXME: ASAN bot uses a fake stack as a thread stack frame, |
62 // and its size is different from the value which APIs tells us. | 63 // and its size is different from the value which APIs tells us. |
63 #if defined(ADDRESS_SANITIZER) | 64 #if defined(ADDRESS_SANITIZER) |
64 return 0; | 65 return 0; |
65 #endif | 66 #endif |
(...skipping 20 matching lines...) Expand all Loading... |
86 error = pthread_attr_getstack(&attr, &base, &size); | 87 error = pthread_attr_getstack(&attr, &base, &size); |
87 RELEASE_ASSERT(!error); | 88 RELEASE_ASSERT(!error); |
88 pthread_attr_destroy(&attr); | 89 pthread_attr_destroy(&attr); |
89 return size; | 90 return size; |
90 } | 91 } |
91 #if OS(FREEBSD) | 92 #if OS(FREEBSD) |
92 pthread_attr_destroy(&attr); | 93 pthread_attr_destroy(&attr); |
93 #endif | 94 #endif |
94 | 95 |
95 // Return a 512k stack size, (conservatively) assuming the following: | 96 // Return a 512k stack size, (conservatively) assuming the following: |
96 // - that size is much lower than the pthreads default (x86 pthreads has a 2M
default.) | 97 // - that size is much lower than the pthreads default (x86 pthreads has a 2M |
| 98 // default.) |
97 // - no one is running Blink with an RLIMIT_STACK override, let alone as | 99 // - no one is running Blink with an RLIMIT_STACK override, let alone as |
98 // low as 512k. | 100 // low as 512k. |
99 // | 101 // |
100 return 512 * 1024; | 102 return 512 * 1024; |
101 #elif OS(MACOSX) | 103 #elif OS(MACOSX) |
102 // pthread_get_stacksize_np() returns too low a value for the main thread on | 104 // pthread_get_stacksize_np() returns too low a value for the main thread on |
103 // OSX 10.9, http://mail.openjdk.java.net/pipermail/hotspot-dev/2013-October/0
11369.html | 105 // OSX 10.9, |
| 106 // http://mail.openjdk.java.net/pipermail/hotspot-dev/2013-October/011369.html |
104 // | 107 // |
105 // Multiple workarounds possible, adopt the one made by https://github.com/rob
ovm/robovm/issues/274 | 108 // Multiple workarounds possible, adopt the one made by |
106 // (cf. https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual
/Multithreading/CreatingThreads/CreatingThreads.html | 109 // https://github.com/robovm/robovm/issues/274 |
| 110 // (cf. |
| 111 // https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/Mult
ithreading/CreatingThreads/CreatingThreads.html |
107 // on why hardcoding sizes is reasonable.) | 112 // on why hardcoding sizes is reasonable.) |
108 if (pthread_main_np()) { | 113 if (pthread_main_np()) { |
109 #if defined(IOS) | 114 #if defined(IOS) |
110 pthread_attr_t attr; | 115 pthread_attr_t attr; |
111 pthread_attr_init(&attr); | 116 pthread_attr_init(&attr); |
112 size_t guardSize = 0; | 117 size_t guardSize = 0; |
113 pthread_attr_getguardsize(&attr, &guardSize); | 118 pthread_attr_getguardsize(&attr, &guardSize); |
114 // Stack size for the main thread is 1MB on iOS including the guard page siz
e. | 119 // Stack size for the main thread is 1MB on iOS including the guard page |
| 120 // size. |
115 return (1 * 1024 * 1024 - guardSize); | 121 return (1 * 1024 * 1024 - guardSize); |
116 #else | 122 #else |
117 // Stack size for the main thread is 8MB on OSX excluding the guard page siz
e. | 123 // Stack size for the main thread is 8MB on OSX excluding the guard page |
| 124 // size. |
118 return (8 * 1024 * 1024); | 125 return (8 * 1024 * 1024); |
119 #endif | 126 #endif |
120 } | 127 } |
121 return pthread_get_stacksize_np(pthread_self()); | 128 return pthread_get_stacksize_np(pthread_self()); |
122 #elif OS(WIN) && COMPILER(MSVC) | 129 #elif OS(WIN) && COMPILER(MSVC) |
123 return ThreadState::current()->threadStackSize(); | 130 return ThreadState::current()->threadStackSize(); |
124 #else | 131 #else |
125 #error "Stack frame size estimation not supported on this platform." | 132 #error "Stack frame size estimation not supported on this platform." |
126 return 0; | 133 return 0; |
127 #endif | 134 #endif |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
168 return reinterpret_cast<void*>(__readgsqword(offsetof(NT_TIB64, StackBase))); | 175 return reinterpret_cast<void*>(__readgsqword(offsetof(NT_TIB64, StackBase))); |
169 #else | 176 #else |
170 return reinterpret_cast<void*>(__readfsdword(offsetof(NT_TIB, StackBase))); | 177 return reinterpret_cast<void*>(__readfsdword(offsetof(NT_TIB, StackBase))); |
171 #endif | 178 #endif |
172 #else | 179 #else |
173 #error Unsupported getStackStart on this platform. | 180 #error Unsupported getStackStart on this platform. |
174 #endif | 181 #endif |
175 } | 182 } |
176 | 183 |
177 } // namespace blink | 184 } // namespace blink |
OLD | NEW |