Using C++14 with AVR-GCC (Arduino Uno)

Viewed 399

I'm trying try get my Arduino code to compile with -std=c++14 instead of the default -std=gnu++11. To this end, I added to my platformio.ini:

build_flags = -std=c++14
build_unflags = -std=gnu++11

However, when I then try to compile, I get the following linker errors:

<artificial>:(.text+0x20a4): undefined reference to `operator delete(void*, unsigned int)'

(multiple times)

I seems that the delete operator is missing. I found some threads about adding it manually, which appears to be used to be necessary in the past with Arduino. However, this shouldn't be the case anymore, and with the default gnu++11 I do not have this issue. Why is this missing with c++14 (and later standards and their GNU extensions) and not with the default gnu++11?

I only have this problem with avr-gcc (for Arduino Uno), with arm-none-eabi-g++ (for Teensy), this problem does not occur.

1 Answers

After some searching around it turns out that C++ from C++14 on defines two additional delete operators:

void operator delete ( void* ptr, std::size_t sz ) noexcept; (5) (since C++14)
void operator delete[]( void* ptr, std::size_t sz ) noexcept; (6) (since C++14)

5-6) Called instead of (1-2) if a user-defined replacement is provided, except that it's unspecified whether (1-2) or (5-6) is called when deleting objects of incomplete type and arrays of non-class and trivially-destructible class types. A memory allocator can use the given size to be more efficient. The standard library implementations are identical to (1-2).

(from https://en.cppreference.com/w/cpp/memory/new/operator_delete)

Looking at ArduinoCore-avr's source, these are actually present, and defined as follows:

#if __cplusplus >= 201402L
void operator delete(void* ptr, std::size_t size) noexcept {
  operator delete(ptr);
}
void operator delete[](void * ptr, std::size_t size) noexcept {
  operator delete[](ptr);
}
#endif // __cplusplus >= 201402L

However, it seems like there hasn't been a new release of ArduinoCore-avr in a while, and the last release predates this (relatively recent) code.

After adding the above definition to my code myself, it compiles :)

Related