Browse Source

`StaticVector`: Replace `std::aligned_storage_t`

`std::aligned_*` are deprecated in C++23 per
https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2021/p1413r3.pdf
pull/5703/merge
Gleb Mazovetskiy 3 years ago
parent
commit
0fb9599e66
  1. 51
      Source/utils/static_vector.hpp

51
Source/utils/static_vector.hpp

@ -1,12 +1,11 @@
#pragma once #pragma once
#include <cstddef>
#include <initializer_list> #include <initializer_list>
#include <memory> #include <memory>
#include <type_traits>
#include <utility> #include <utility>
#include "appfat.h" #include "appfat.h"
#include "utils/stdcompat/cstddef.hpp"
namespace devilution { namespace devilution {
@ -58,47 +57,53 @@ public:
T &emplace_back(Args &&...args) // NOLINT(readability-identifier-naming) T &emplace_back(Args &&...args) // NOLINT(readability-identifier-naming)
{ {
assert(size_ < N); assert(size_ < N);
::new (&data_[size_]) T(std::forward<Args>(args)...); return *::new (&data_[size_++]) T(std::forward<Args>(args)...);
#if __cplusplus >= 201703L
T &result = *std::launder(reinterpret_cast<T *>(&data_[size_]));
#else
T &result = *reinterpret_cast<T *>(&data_[size_]);
#endif
++size_;
return result;
} }
T &operator[](std::size_t pos) T &operator[](std::size_t pos)
{ {
#if __cplusplus >= 201703L return *data_[pos].ptr();
return *std::launder(reinterpret_cast<T *>(&data_[pos]));
#else
return *reinterpret_cast<T *>(&data_[pos]);
#endif
} }
const T &operator[](std::size_t pos) const const T &operator[](std::size_t pos) const
{ {
#if __cplusplus >= 201703L return *data_[pos].ptr();
return *std::launder(reinterpret_cast<const T *>(&data_[pos]));
#else
return *reinterpret_cast<const T *>(&data_[pos]);
#endif
} }
~StaticVector() ~StaticVector()
{ {
for (std::size_t pos = 0; pos < size_; ++pos) { for (std::size_t pos = 0; pos < size_; ++pos) {
#if __cplusplus >= 201703L #if __cplusplus >= 201703L
std::destroy_at(std::launder(reinterpret_cast<T *>(&data_[pos]))); std::destroy_at(data_[pos].ptr());
#else #else
reinterpret_cast<T *>(&data_[pos])->~T(); data_[pos].ptr()->~T();
#endif #endif
} }
} }
private: private:
std::aligned_storage_t<sizeof(T), alignof(T)> data_[N]; struct AlignedStorage {
alignas(alignof(T)) byte data[sizeof(T)];
const T *ptr() const
{
#if __cplusplus >= 201703L
return std::launder(reinterpret_cast<const T *>(data));
#else
return reinterpret_cast<const T *>(data);
#endif
}
T *ptr()
{
#if __cplusplus >= 201703L
return std::launder(reinterpret_cast<T *>(data));
#else
return reinterpret_cast<T *>(data);
#endif
}
};
AlignedStorage data_[N];
std::size_t size_ = 0; std::size_t size_ = 0;
}; };

Loading…
Cancel
Save