OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 "base/allocator/allocator_shim.h" | 5 #include "base/allocator/allocator_shim.h" |
6 | 6 |
7 #include <config.h> | 7 #include <config.h> |
8 #include "base/allocator/allocator_extension_thunks.h" | 8 #include "base/allocator/allocator_extension_thunks.h" |
9 #include "base/profiler/alternate_timer.h" | 9 #include "base/profiler/alternate_timer.h" |
10 #include "base/sysinfo.h" | 10 #include "base/sysinfo.h" |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
66 // Forward declarations from jemalloc. | 66 // Forward declarations from jemalloc. |
67 extern "C" { | 67 extern "C" { |
68 void* je_malloc(size_t s); | 68 void* je_malloc(size_t s); |
69 void* je_realloc(void* p, size_t s); | 69 void* je_realloc(void* p, size_t s); |
70 void je_free(void* s); | 70 void je_free(void* s); |
71 size_t je_msize(void* p); | 71 size_t je_msize(void* p); |
72 bool je_malloc_init_hard(); | 72 bool je_malloc_init_hard(); |
73 void* je_memalign(size_t a, size_t s); | 73 void* je_memalign(size_t a, size_t s); |
74 } | 74 } |
75 | 75 |
76 extern "C" { | |
77 | |
78 // Call the new handler, if one has been set. | 76 // Call the new handler, if one has been set. |
79 // Returns true on successfully calling the handler, false otherwise. | 77 // Returns true on successfully calling the handler, false otherwise. |
80 inline bool call_new_handler(bool nothrow) { | 78 inline bool call_new_handler(bool nothrow) { |
81 // Get the current new handler. NB: this function is not | 79 // Get the current new handler. NB: this function is not |
82 // thread-safe. We make a feeble stab at making it so here, but | 80 // thread-safe. We make a feeble stab at making it so here, but |
83 // this lock only protects against tcmalloc interfering with | 81 // this lock only protects against tcmalloc interfering with |
84 // itself, not with other libraries calling set_new_handler. | 82 // itself, not with other libraries calling set_new_handler. |
85 std::new_handler nh; | 83 std::new_handler nh; |
86 { | 84 { |
87 SpinLockHolder h(&set_new_handler_lock); | 85 SpinLockHolder h(&set_new_handler_lock); |
88 nh = std::set_new_handler(0); | 86 nh = std::set_new_handler(0); |
89 (void) std::set_new_handler(nh); | 87 (void) std::set_new_handler(nh); |
90 } | 88 } |
91 #if (defined(__GNUC__) && !defined(__EXCEPTIONS)) || (defined(_HAS_EXCEPTIONS) &
& !_HAS_EXCEPTIONS) | 89 #if (defined(__GNUC__) && !defined(__EXCEPTIONS)) || \ |
| 90 (defined(_HAS_EXCEPTIONS) && !_HAS_EXCEPTIONS) |
92 if (!nh) | 91 if (!nh) |
93 return false; | 92 return false; |
94 // Since exceptions are disabled, we don't really know if new_handler | 93 // Since exceptions are disabled, we don't really know if new_handler |
95 // failed. Assume it will abort if it fails. | 94 // failed. Assume it will abort if it fails. |
96 (*nh)(); | 95 (*nh)(); |
97 return false; // break out of the retry loop. | 96 return false; // break out of the retry loop. |
98 #else | 97 #else |
99 // If no new_handler is established, the allocation failed. | 98 // If no new_handler is established, the allocation failed. |
100 if (!nh) { | 99 if (!nh) { |
101 if (nothrow) | 100 if (nothrow) |
102 return 0; | 101 return false; |
103 throw std::bad_alloc(); | 102 throw std::bad_alloc(); |
104 } | 103 } |
105 // Otherwise, try the new_handler. If it returns, retry the | 104 // Otherwise, try the new_handler. If it returns, retry the |
106 // allocation. If it throws std::bad_alloc, fail the allocation. | 105 // allocation. If it throws std::bad_alloc, fail the allocation. |
107 // if it throws something else, don't interfere. | 106 // if it throws something else, don't interfere. |
108 try { | 107 try { |
109 (*nh)(); | 108 (*nh)(); |
110 } catch (const std::bad_alloc&) { | 109 } catch (const std::bad_alloc&) { |
111 if (!nothrow) | 110 if (!nothrow) |
112 throw; | 111 throw; |
113 return true; | 112 return true; |
114 } | 113 } |
115 #endif // (defined(__GNUC__) && !defined(__EXCEPTIONS)) || (defined(_HAS_EXCEPT
IONS) && !_HAS_EXCEPTIONS) | 114 #endif // (defined(__GNUC__) && !defined(__EXCEPTIONS)) || (defined(_HAS_EXCEPT
IONS) && !_HAS_EXCEPTIONS) |
| 115 return false; |
116 } | 116 } |
117 | 117 |
| 118 extern "C" { |
118 void* malloc(size_t size) __THROW { | 119 void* malloc(size_t size) __THROW { |
119 void* ptr; | 120 void* ptr; |
120 for (;;) { | 121 for (;;) { |
121 #ifdef ENABLE_DYNAMIC_ALLOCATOR_SWITCHING | 122 #ifdef ENABLE_DYNAMIC_ALLOCATOR_SWITCHING |
122 switch (allocator) { | 123 switch (allocator) { |
123 case JEMALLOC: | 124 case JEMALLOC: |
124 ptr = je_malloc(size); | 125 ptr = je_malloc(size); |
125 break; | 126 break; |
126 case WINHEAP: | 127 case WINHEAP: |
127 case WINLFH: | 128 case WINLFH: |
(...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
436 void TCMallocDoFreeForTest(void* ptr) { | 437 void TCMallocDoFreeForTest(void* ptr) { |
437 do_free(ptr); | 438 do_free(ptr); |
438 } | 439 } |
439 | 440 |
440 size_t ExcludeSpaceForMarkForTest(size_t size) { | 441 size_t ExcludeSpaceForMarkForTest(size_t size) { |
441 return ExcludeSpaceForMark(size); | 442 return ExcludeSpaceForMark(size); |
442 } | 443 } |
443 | 444 |
444 } // namespace allocator. | 445 } // namespace allocator. |
445 } // namespace base. | 446 } // namespace base. |
OLD | NEW |