Search code examples
c++

does span<T> have a stable layout?


you can mark an exported C++ function with extern "C" so it can be called by another compiler, however you usually cannot pass std types because their layout depends on the compiler, another method is virtual functions whose ABI is stable and don't need to be marked extern "C"

Is it safe to pass or return std::span<T> across compiler boundaries ? the cppref page says

A typical implementation holds a pointer to T, if the extent is dynamic, the implementation also holds a size.

  1. is there any guarantee that its layout will be stable between different compilers ?
  2. is its layout at least practically safe to be used between the commonly available implementations (MSVC, libstdc++, libc++, ?????) ?

or should i just create a dummy non-templated struct that holds T* and size_t to be able to pass or return it safely from extern "C" functions.


Solution

  • is there any guarantee that its layout will be stable between different compilers ?

    No. There is no such guarantee between anything at all whatsoever in C++.

    (The Common C++ ABI makes a few guarantees, but not for the layout of any particular std types.)

    is its layout at least practically safe to be used between the commonly available implementations

    No. There is nothing that is safe to be used between MSVC and anything else in general, and basically nothing between libc++ and libstdc++. The only thing that is somewhat safe is to use libstdc++ and mix Clang- and GCC-compiled object files. But I would avoid even this.