xref: /llvm-project-15.0.7/libcxx/src/new.cpp (revision 24a2ebe6)
13e519524SHoward Hinnant //===--------------------------- new.cpp ----------------------------------===//
23e519524SHoward Hinnant //
35b08a8a4SHoward Hinnant //                     The LLVM Compiler Infrastructure
43e519524SHoward Hinnant //
5412dbebeSHoward Hinnant // This file is dual licensed under the MIT and the University of Illinois Open
6412dbebeSHoward Hinnant // Source Licenses. See LICENSE.TXT for details.
73e519524SHoward Hinnant //
83e519524SHoward Hinnant //===----------------------------------------------------------------------===//
93e519524SHoward Hinnant 
106e8ebb2cSMarshall Clow #define _LIBCPP_BUILDING_NEW
116e8ebb2cSMarshall Clow 
12111e0cbeSNick Kledzik #include <stdlib.h>
13111e0cbeSNick Kledzik 
143e519524SHoward Hinnant #include "new"
153e519524SHoward Hinnant 
161285e4d6SEric Fiselier #if defined(__APPLE__) && !defined(LIBCXXRT) && \
171285e4d6SEric Fiselier     !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY)
18128ba719SHoward Hinnant     #include <cxxabi.h>
192c9c6a57SHoward Hinnant 
202c9c6a57SHoward Hinnant     #ifndef _LIBCPPABI_VERSION
21111e0cbeSNick Kledzik         // On Darwin, there are two STL shared libraries and a lower level ABI
22c1cf9818SMarshall Clow         // shared library.  The global holding the current new handler is
23111e0cbeSNick Kledzik         // in the ABI library and named __cxa_new_handler.
24111e0cbeSNick Kledzik         #define __new_handler __cxxabiapple::__cxa_new_handler
252c9c6a57SHoward Hinnant     #endif
26940e211cSHoward Hinnant #else  // __APPLE__
27929df471SBenjamin Kramer     #if defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI)
28dce0696aSHoward Hinnant         #include <cxxabi.h>
29929df471SBenjamin Kramer     #endif  // defined(LIBCXX_BUILDING_LIBCXXABI)
301285e4d6SEric Fiselier     #if defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) || \
311285e4d6SEric Fiselier         (!defined(_LIBCPPABI_VERSION) && !defined(__GLIBCXX__))
32111e0cbeSNick Kledzik         static std::new_handler __new_handler;
33dce0696aSHoward Hinnant     #endif  // _LIBCPPABI_VERSION
34111e0cbeSNick Kledzik #endif
35111e0cbeSNick Kledzik 
36926aa5f4SPeter Collingbourne #ifndef __GLIBCXX__
37926aa5f4SPeter Collingbourne 
38111e0cbeSNick Kledzik // Implement all new and delete operators as weak definitions
3910fe4209SEric Fiselier // in this shared library, so that they can be overridden by programs
40111e0cbeSNick Kledzik // that define non-weak copies of the functions.
41111e0cbeSNick Kledzik 
42dce4218dSShoaib Meenai _LIBCPP_WEAK
43111e0cbeSNick Kledzik void *
440ae4f23fSEric Fiselier operator new(std::size_t size) _THROW_BAD_ALLOC
45111e0cbeSNick Kledzik {
46111e0cbeSNick Kledzik     if (size == 0)
47111e0cbeSNick Kledzik         size = 1;
48111e0cbeSNick Kledzik     void* p;
49111e0cbeSNick Kledzik     while ((p = ::malloc(size)) == 0)
50111e0cbeSNick Kledzik     {
51111e0cbeSNick Kledzik         // If malloc fails and there is a new_handler,
52111e0cbeSNick Kledzik         // call it to try free up memory.
5375357bcdSHoward Hinnant         std::new_handler nh = std::get_new_handler();
54816cb897SHoward Hinnant         if (nh)
55816cb897SHoward Hinnant             nh();
56111e0cbeSNick Kledzik         else
5754b409fdSHoward Hinnant #ifndef _LIBCPP_NO_EXCEPTIONS
58111e0cbeSNick Kledzik             throw std::bad_alloc();
5954b409fdSHoward Hinnant #else
6054b409fdSHoward Hinnant             break;
6154b409fdSHoward Hinnant #endif
62111e0cbeSNick Kledzik     }
63111e0cbeSNick Kledzik     return p;
64111e0cbeSNick Kledzik }
65111e0cbeSNick Kledzik 
66dce4218dSShoaib Meenai _LIBCPP_WEAK
67111e0cbeSNick Kledzik void*
68*24a2ebe6SEric Fiselier operator new(size_t size, const std::nothrow_t&) _NOEXCEPT
69*24a2ebe6SEric Fiselier {
70*24a2ebe6SEric Fiselier     void* p = 0;
71*24a2ebe6SEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
72*24a2ebe6SEric Fiselier     try
73*24a2ebe6SEric Fiselier     {
74*24a2ebe6SEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
75*24a2ebe6SEric Fiselier         p = ::operator new(size);
76*24a2ebe6SEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
77*24a2ebe6SEric Fiselier     }
78*24a2ebe6SEric Fiselier     catch (...)
79*24a2ebe6SEric Fiselier     {
80*24a2ebe6SEric Fiselier     }
81*24a2ebe6SEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
82*24a2ebe6SEric Fiselier     return p;
83*24a2ebe6SEric Fiselier }
84*24a2ebe6SEric Fiselier 
85*24a2ebe6SEric Fiselier _LIBCPP_WEAK
86*24a2ebe6SEric Fiselier void*
87*24a2ebe6SEric Fiselier operator new[](size_t size) _THROW_BAD_ALLOC
88*24a2ebe6SEric Fiselier {
89*24a2ebe6SEric Fiselier     return ::operator new(size);
90*24a2ebe6SEric Fiselier }
91*24a2ebe6SEric Fiselier 
92*24a2ebe6SEric Fiselier _LIBCPP_WEAK
93*24a2ebe6SEric Fiselier void*
94*24a2ebe6SEric Fiselier operator new[](size_t size, const std::nothrow_t&) _NOEXCEPT
95*24a2ebe6SEric Fiselier {
96*24a2ebe6SEric Fiselier     void* p = 0;
97*24a2ebe6SEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
98*24a2ebe6SEric Fiselier     try
99*24a2ebe6SEric Fiselier     {
100*24a2ebe6SEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
101*24a2ebe6SEric Fiselier         p = ::operator new[](size);
102*24a2ebe6SEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
103*24a2ebe6SEric Fiselier     }
104*24a2ebe6SEric Fiselier     catch (...)
105*24a2ebe6SEric Fiselier     {
106*24a2ebe6SEric Fiselier     }
107*24a2ebe6SEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
108*24a2ebe6SEric Fiselier     return p;
109*24a2ebe6SEric Fiselier }
110*24a2ebe6SEric Fiselier 
111*24a2ebe6SEric Fiselier _LIBCPP_WEAK
112*24a2ebe6SEric Fiselier void
113*24a2ebe6SEric Fiselier operator delete(void* ptr) _NOEXCEPT
114*24a2ebe6SEric Fiselier {
115*24a2ebe6SEric Fiselier     if (ptr)
116*24a2ebe6SEric Fiselier         ::free(ptr);
117*24a2ebe6SEric Fiselier }
118*24a2ebe6SEric Fiselier 
119*24a2ebe6SEric Fiselier _LIBCPP_WEAK
120*24a2ebe6SEric Fiselier void
121*24a2ebe6SEric Fiselier operator delete(void* ptr, const std::nothrow_t&) _NOEXCEPT
122*24a2ebe6SEric Fiselier {
123*24a2ebe6SEric Fiselier     ::operator delete(ptr);
124*24a2ebe6SEric Fiselier }
125*24a2ebe6SEric Fiselier 
126*24a2ebe6SEric Fiselier _LIBCPP_WEAK
127*24a2ebe6SEric Fiselier void
128*24a2ebe6SEric Fiselier operator delete(void* ptr, size_t) _NOEXCEPT
129*24a2ebe6SEric Fiselier {
130*24a2ebe6SEric Fiselier     ::operator delete(ptr);
131*24a2ebe6SEric Fiselier }
132*24a2ebe6SEric Fiselier 
133*24a2ebe6SEric Fiselier _LIBCPP_WEAK
134*24a2ebe6SEric Fiselier void
135*24a2ebe6SEric Fiselier operator delete[] (void* ptr) _NOEXCEPT
136*24a2ebe6SEric Fiselier {
137*24a2ebe6SEric Fiselier     ::operator delete(ptr);
138*24a2ebe6SEric Fiselier }
139*24a2ebe6SEric Fiselier 
140*24a2ebe6SEric Fiselier _LIBCPP_WEAK
141*24a2ebe6SEric Fiselier void
142*24a2ebe6SEric Fiselier operator delete[] (void* ptr, const std::nothrow_t&) _NOEXCEPT
143*24a2ebe6SEric Fiselier {
144*24a2ebe6SEric Fiselier     ::operator delete[](ptr);
145*24a2ebe6SEric Fiselier }
146*24a2ebe6SEric Fiselier 
147*24a2ebe6SEric Fiselier _LIBCPP_WEAK
148*24a2ebe6SEric Fiselier void
149*24a2ebe6SEric Fiselier operator delete[] (void* ptr, size_t) _NOEXCEPT
150*24a2ebe6SEric Fiselier {
151*24a2ebe6SEric Fiselier     ::operator delete[](ptr);
152*24a2ebe6SEric Fiselier }
153*24a2ebe6SEric Fiselier 
154*24a2ebe6SEric Fiselier _LIBCPP_WEAK
155*24a2ebe6SEric Fiselier void *
1560ae4f23fSEric Fiselier operator new(std::size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC
1570ae4f23fSEric Fiselier {
1580ae4f23fSEric Fiselier     if (size == 0)
1590ae4f23fSEric Fiselier         size = 1;
1600ae4f23fSEric Fiselier     if (static_cast<size_t>(alignment) < sizeof(void*))
1610ae4f23fSEric Fiselier       alignment = std::align_val_t(sizeof(void*));
1620ae4f23fSEric Fiselier     void* p;
163b2826a1dSSaleem Abdulrasool #if defined(_LIBCPP_MSVCRT)
1643e835372SEric Fiselier     while ((p = _aligned_malloc(size, static_cast<size_t>(alignment))) == nullptr)
1653e835372SEric Fiselier #else
1660ae4f23fSEric Fiselier     while (::posix_memalign(&p, static_cast<size_t>(alignment), size) != 0)
1673e835372SEric Fiselier #endif
1680ae4f23fSEric Fiselier     {
1690ae4f23fSEric Fiselier         // If posix_memalign fails and there is a new_handler,
1700ae4f23fSEric Fiselier         // call it to try free up memory.
1710ae4f23fSEric Fiselier         std::new_handler nh = std::get_new_handler();
1720ae4f23fSEric Fiselier         if (nh)
1730ae4f23fSEric Fiselier             nh();
1740ae4f23fSEric Fiselier         else {
1750ae4f23fSEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
1760ae4f23fSEric Fiselier             throw std::bad_alloc();
1770ae4f23fSEric Fiselier #else
1780ae4f23fSEric Fiselier             p = nullptr; // posix_memalign doesn't initialize 'p' on failure
1790ae4f23fSEric Fiselier             break;
1800ae4f23fSEric Fiselier #endif
1810ae4f23fSEric Fiselier         }
1820ae4f23fSEric Fiselier     }
1830ae4f23fSEric Fiselier     return p;
1840ae4f23fSEric Fiselier }
1850ae4f23fSEric Fiselier 
186dce4218dSShoaib Meenai _LIBCPP_WEAK
1870ae4f23fSEric Fiselier void*
1880ae4f23fSEric Fiselier operator new(size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
1890ae4f23fSEric Fiselier {
1900ae4f23fSEric Fiselier     void* p = 0;
1910ae4f23fSEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
1920ae4f23fSEric Fiselier     try
1930ae4f23fSEric Fiselier     {
1940ae4f23fSEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
1950ae4f23fSEric Fiselier         p = ::operator new(size, alignment);
1960ae4f23fSEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
1970ae4f23fSEric Fiselier     }
1980ae4f23fSEric Fiselier     catch (...)
1990ae4f23fSEric Fiselier     {
2000ae4f23fSEric Fiselier     }
2010ae4f23fSEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
2020ae4f23fSEric Fiselier     return p;
2030ae4f23fSEric Fiselier }
2040ae4f23fSEric Fiselier 
205dce4218dSShoaib Meenai _LIBCPP_WEAK
2060ae4f23fSEric Fiselier void*
2070ae4f23fSEric Fiselier operator new[](size_t size, std::align_val_t alignment) _THROW_BAD_ALLOC
2080ae4f23fSEric Fiselier {
2090ae4f23fSEric Fiselier     return ::operator new(size, alignment);
2100ae4f23fSEric Fiselier }
2110ae4f23fSEric Fiselier 
212dce4218dSShoaib Meenai _LIBCPP_WEAK
2130ae4f23fSEric Fiselier void*
2140ae4f23fSEric Fiselier operator new[](size_t size, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
2150ae4f23fSEric Fiselier {
2160ae4f23fSEric Fiselier     void* p = 0;
2170ae4f23fSEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
2180ae4f23fSEric Fiselier     try
2190ae4f23fSEric Fiselier     {
2200ae4f23fSEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
2210ae4f23fSEric Fiselier         p = ::operator new[](size, alignment);
2220ae4f23fSEric Fiselier #ifndef _LIBCPP_NO_EXCEPTIONS
2230ae4f23fSEric Fiselier     }
2240ae4f23fSEric Fiselier     catch (...)
2250ae4f23fSEric Fiselier     {
2260ae4f23fSEric Fiselier     }
2270ae4f23fSEric Fiselier #endif  // _LIBCPP_NO_EXCEPTIONS
2280ae4f23fSEric Fiselier     return p;
2290ae4f23fSEric Fiselier }
2300ae4f23fSEric Fiselier 
231dce4218dSShoaib Meenai _LIBCPP_WEAK
232111e0cbeSNick Kledzik void
2330ae4f23fSEric Fiselier operator delete(void* ptr, std::align_val_t) _NOEXCEPT
2340ae4f23fSEric Fiselier {
2350ae4f23fSEric Fiselier     if (ptr)
2367ce92f73SShoaib Meenai #if defined(_LIBCPP_MSVCRT)
2377ce92f73SShoaib Meenai         ::_aligned_free(ptr);
2387ce92f73SShoaib Meenai #else
2390ae4f23fSEric Fiselier         ::free(ptr);
2407ce92f73SShoaib Meenai #endif
2410ae4f23fSEric Fiselier }
2420ae4f23fSEric Fiselier 
243dce4218dSShoaib Meenai _LIBCPP_WEAK
2440ae4f23fSEric Fiselier void
2450ae4f23fSEric Fiselier operator delete(void* ptr, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
2460ae4f23fSEric Fiselier {
2470ae4f23fSEric Fiselier     ::operator delete(ptr, alignment);
2480ae4f23fSEric Fiselier }
2490ae4f23fSEric Fiselier 
250dce4218dSShoaib Meenai _LIBCPP_WEAK
2510ae4f23fSEric Fiselier void
2520ae4f23fSEric Fiselier operator delete(void* ptr, size_t, std::align_val_t alignment) _NOEXCEPT
2530ae4f23fSEric Fiselier {
2540ae4f23fSEric Fiselier     ::operator delete(ptr, alignment);
2550ae4f23fSEric Fiselier }
2560ae4f23fSEric Fiselier 
257dce4218dSShoaib Meenai _LIBCPP_WEAK
2580ae4f23fSEric Fiselier void
2590ae4f23fSEric Fiselier operator delete[] (void* ptr, std::align_val_t alignment) _NOEXCEPT
2600ae4f23fSEric Fiselier {
2610ae4f23fSEric Fiselier     ::operator delete(ptr, alignment);
2620ae4f23fSEric Fiselier }
2630ae4f23fSEric Fiselier 
264dce4218dSShoaib Meenai _LIBCPP_WEAK
2650ae4f23fSEric Fiselier void
2660ae4f23fSEric Fiselier operator delete[] (void* ptr, std::align_val_t alignment, const std::nothrow_t&) _NOEXCEPT
2670ae4f23fSEric Fiselier {
2680ae4f23fSEric Fiselier     ::operator delete[](ptr, alignment);
2690ae4f23fSEric Fiselier }
2700ae4f23fSEric Fiselier 
271dce4218dSShoaib Meenai _LIBCPP_WEAK
2720ae4f23fSEric Fiselier void
2730ae4f23fSEric Fiselier operator delete[] (void* ptr, size_t, std::align_val_t alignment) _NOEXCEPT
2740ae4f23fSEric Fiselier {
2750ae4f23fSEric Fiselier     ::operator delete[](ptr, alignment);
2760ae4f23fSEric Fiselier }
2770ae4f23fSEric Fiselier 
278926aa5f4SPeter Collingbourne #endif // !__GLIBCXX__
279926aa5f4SPeter Collingbourne 
2803e519524SHoward Hinnant namespace std
2813e519524SHoward Hinnant {
2823e519524SHoward Hinnant 
283926aa5f4SPeter Collingbourne #ifndef __GLIBCXX__
28462713dacSNick Kledzik const nothrow_t nothrow = {};
285926aa5f4SPeter Collingbourne #endif
28662713dacSNick Kledzik 
2872c9c6a57SHoward Hinnant #ifndef _LIBCPPABI_VERSION
2882c9c6a57SHoward Hinnant 
289926aa5f4SPeter Collingbourne #ifndef __GLIBCXX__
290926aa5f4SPeter Collingbourne 
29162713dacSNick Kledzik new_handler
292fafca58cSHoward Hinnant set_new_handler(new_handler handler) _NOEXCEPT
29362713dacSNick Kledzik {
2941596c453SHoward Hinnant     return __sync_lock_test_and_set(&__new_handler, handler);
2951596c453SHoward Hinnant }
2961596c453SHoward Hinnant 
2971596c453SHoward Hinnant new_handler
298fafca58cSHoward Hinnant get_new_handler() _NOEXCEPT
2991596c453SHoward Hinnant {
300634b9dd7SJoerg Sonnenberger     return __sync_fetch_and_add(&__new_handler, nullptr);
30162713dacSNick Kledzik }
30262713dacSNick Kledzik 
303926aa5f4SPeter Collingbourne #endif // !__GLIBCXX__
304926aa5f4SPeter Collingbourne 
305e1da544eSDavid Chisnall #ifndef LIBCXXRT
306e1da544eSDavid Chisnall 
307fafca58cSHoward Hinnant bad_alloc::bad_alloc() _NOEXCEPT
308111e0cbeSNick Kledzik {
309111e0cbeSNick Kledzik }
310111e0cbeSNick Kledzik 
311926aa5f4SPeter Collingbourne #ifndef __GLIBCXX__
312926aa5f4SPeter Collingbourne 
313fafca58cSHoward Hinnant bad_alloc::~bad_alloc() _NOEXCEPT
314111e0cbeSNick Kledzik {
315111e0cbeSNick Kledzik }
316111e0cbeSNick Kledzik 
317111e0cbeSNick Kledzik const char*
318fafca58cSHoward Hinnant bad_alloc::what() const _NOEXCEPT
319111e0cbeSNick Kledzik {
320111e0cbeSNick Kledzik     return "std::bad_alloc";
321111e0cbeSNick Kledzik }
322111e0cbeSNick Kledzik 
323926aa5f4SPeter Collingbourne #endif // !__GLIBCXX__
324926aa5f4SPeter Collingbourne 
325fafca58cSHoward Hinnant bad_array_new_length::bad_array_new_length() _NOEXCEPT
326111e0cbeSNick Kledzik {
327111e0cbeSNick Kledzik }
328111e0cbeSNick Kledzik 
329194e81f6SEric Fiselier #ifndef __GLIBCXX__
330194e81f6SEric Fiselier 
331fafca58cSHoward Hinnant bad_array_new_length::~bad_array_new_length() _NOEXCEPT
3323e519524SHoward Hinnant {
3333e519524SHoward Hinnant }
3343e519524SHoward Hinnant 
3351d558b84SEric Fiselier const char*
3361d558b84SEric Fiselier bad_array_new_length::what() const _NOEXCEPT
3371d558b84SEric Fiselier {
3381d558b84SEric Fiselier     return "bad_array_new_length";
3391d558b84SEric Fiselier }
3401d558b84SEric Fiselier 
341194e81f6SEric Fiselier #endif // !__GLIBCXX__
342194e81f6SEric Fiselier 
343fd465fe5SEric Fiselier #endif //LIBCXXRT
344fd465fe5SEric Fiselier 
345194e81f6SEric Fiselier bad_array_length::bad_array_length() _NOEXCEPT
346194e81f6SEric Fiselier {
347194e81f6SEric Fiselier }
348194e81f6SEric Fiselier 
349194e81f6SEric Fiselier #ifndef __GLIBCXX__
350194e81f6SEric Fiselier 
351194e81f6SEric Fiselier bad_array_length::~bad_array_length() _NOEXCEPT
352194e81f6SEric Fiselier {
353194e81f6SEric Fiselier }
354194e81f6SEric Fiselier 
3553e519524SHoward Hinnant const char*
3566e8ebb2cSMarshall Clow bad_array_length::what() const _NOEXCEPT
3576e8ebb2cSMarshall Clow {
3586e8ebb2cSMarshall Clow     return "bad_array_length";
3596e8ebb2cSMarshall Clow }
3606e8ebb2cSMarshall Clow 
361194e81f6SEric Fiselier #endif // !__GLIBCXX__
3626e8ebb2cSMarshall Clow 
3636e8ebb2cSMarshall Clow #endif // _LIBCPPABI_VERSION
3642c9c6a57SHoward Hinnant 
36526dd09e5SPeter Collingbourne #ifndef LIBSTDCXX
36626dd09e5SPeter Collingbourne 
3673e519524SHoward Hinnant void
3683e519524SHoward Hinnant __throw_bad_alloc()
3693e519524SHoward Hinnant {
37054b409fdSHoward Hinnant #ifndef _LIBCPP_NO_EXCEPTIONS
3713e519524SHoward Hinnant     throw bad_alloc();
372d437fa5cSMarshall Clow #else
373d437fa5cSMarshall Clow     _VSTD::abort();
37454b409fdSHoward Hinnant #endif
3753e519524SHoward Hinnant }
3763e519524SHoward Hinnant 
37726dd09e5SPeter Collingbourne #endif // !LIBSTDCXX
37826dd09e5SPeter Collingbourne 
3793e519524SHoward Hinnant }  // std
380