Array Placement-New: Understanding the Impact of Unspecified Overhead
The C standard mandates that array placement-new expressions may incur unspecified overhead in the buffer allocated. This overhead, represented by variables x and y, can vary between different invocations of new.
Consider the example code:
void* buffer = malloc(sizeof(std::string) * 10); std::string* p = ::new (buffer) std::string[10];
According to the standard, the placement-new expression new (buffer) std::string[10] will internally call operator new[](sizeof(std::string) * 10 y, buffer).
However, this raises a concern: if y is greater than 0, the pre-allocated buffer buffer may be too small, leading to a runtime error.
How to Determine the Required Buffer Size
The standard does not guarantee that y will always be 0. To ensure that the pre-allocated buffer is sufficient, you can manually calculate the additional overhead required. Unfortunately, this requires knowledge of the platform-specific implementation details.
Alternative: Implementation-Agnostic Approach
To avoid relying on implementation-specific knowledge, you can use your own placement array new implementation that checks the overhead at runtime:
inline void* operator new[](std::size_t n, void* p, std::size_t limit) { if (n <= limit) std::cout << "life is good\n"; else throw std::bad_alloc(); return p; }
By varying the array size and inspecting n in the example above, you can deduce the value of y for your specific platform.
Update: Elimination of Overhead
Nicol Bolas has highlighted that as of November 2019, a defect report fixed this issue, ensuring that y is always 0 for operator new[](std::size_t, void* p). This change applies retroactively to all versions of C . Therefore, the overhead estimation is no longer necessary.
The above is the detailed content of How Much Buffer Space is Really Needed for C Placement-New Arrays?. For more information, please follow other related articles on the PHP Chinese website!