/Zc:alignedNew
(C++17 over-aligned allocation)
Enable support for C++17 over-aligned new
, dynamic memory allocation aligned on boundaries greater than the default for the maximum-sized standard aligned type, max_align_t
.
Syntax
/Zc:alignedNew
[-
]
Remarks
The MSVC compiler and library support C++17 standard over-aligned dynamic memory allocation. When the /Zc:alignedNew
option is specified, a dynamic allocation such as new Example;
respects the alignment of Example
even when it's greater than max_align_t
, the largest alignment required for any fundamental type. When the alignment of the allocated type is no more than the alignment guaranteed by the original operator new
, available as the value of the predefined macro __STDCPP_DEFAULT_NEW_ALIGNMENT__
, the statement new Example;
results in a call to ::operator new(size_t)
as it did in C++14. When the alignment is greater than __STDCPP_DEFAULT_NEW_ALIGNMENT__
, the implementation instead obtains the memory by using ::operator new(size_t, align_val_t)
. Similarly, deletion of over-aligned types invokes ::operator delete(void*, align_val_t)
or the sized delete signature ::operator delete(void*, size_t, align_val_t)
.
The /Zc:alignedNew
option is only available when /std:c++17
or later is enabled. Under /std:c++17
or later, /Zc:alignedNew
is enabled by default to conform to the C++ standard. If the only reason you implement operator new
and delete
is to support over-aligned allocations, you may no longer need this code in C++17 or later modes. To turn off this option and revert to the C++14 behavior of new
and delete
when you use /std::c++17
or later, specify /Zc:alignedNew-
. If you implement operator new
and delete
but you're not ready to implement the over-aligned operator new
and delete
overloads that have the align_val_t
parameter, use the /Zc:alignedNew-
option to prevent the compiler and Standard Library from generating calls to the over-aligned overloads. The /permissive-
option doesn't change the default setting of /Zc:alignedNew
.
Support for /Zc:alignedNew
is available starting in Visual Studio 2017 version 15.5.
Example
This sample shows how operator new
and operator delete
behave when the /Zc:alignedNew
option is set.
// alignedNew.cpp
// Compile by using: cl /EHsc /std:c++17 /W4 alignedNew.cpp
#include <iostream>
#include <malloc.h>
#include <new>
// "old" unaligned overloads
void* operator new(std::size_t size) {
auto ptr = malloc(size);
std::cout << "unaligned new(" << size << ") = " << ptr << '\n';
return ptr ? ptr : throw std::bad_alloc{};
}
void operator delete(void* ptr, std::size_t size) {
std::cout << "unaligned sized delete(" << ptr << ", " << size << ")\n";
free(ptr);
}
void operator delete(void* ptr) {
std::cout << "unaligned unsized delete(" << ptr << ")\n";
free(ptr);
}
// "new" over-aligned overloads
void* operator new(std::size_t size, std::align_val_t align) {
auto ptr = _aligned_malloc(size, static_cast<std::size_t>(align));
std::cout << "aligned new(" << size << ", " <<
static_cast<std::size_t>(align) << ") = " << ptr << '\n';
return ptr ? ptr : throw std::bad_alloc{};
}
void operator delete(void* ptr, std::size_t size, std::align_val_t align) {
std::cout << "aligned sized delete(" << ptr << ", " << size <<
", " << static_cast<std::size_t>(align) << ")\n";
_aligned_free(ptr);
}
void operator delete(void* ptr, std::align_val_t align) {
std::cout << "aligned unsized delete(" << ptr <<
", " << static_cast<std::size_t>(align) << ")\n";
_aligned_free(ptr);
}
struct alignas(256) OverAligned {}; // warning C4324, structure is padded
int main() {
delete new int;
delete new OverAligned;
}
This output is typical for 32-bit builds. The pointer values vary based on where your application runs in memory.
unaligned new(4) = 009FD0D0
unaligned sized delete(009FD0D0, 4)
aligned new(256, 256) = 009FE800
aligned sized delete(009FE800, 256, 256)
For information about conformance issues in Visual C++, see Nonstandard Behavior.
To set this compiler option in the Visual Studio development environment
Open the project's Property Pages dialog box. For details, see Set C++ compiler and build properties in Visual Studio.
Select the Configuration Properties > C/C++ > Command Line property page.
Modify the Additional Options property to include
/Zc:alignedNew
or/Zc:alignedNew-
and then choose OK.