Files
Ashin Walpola d107534eb2 Keep vanetza-idf in obu-firmware, so a plain clone builds the firmware
obu-firmware builds against the vanetza-idf C-ITS library, which until now
came from the colleague's microbu-esp32c5 tree beside the repository and was
not tracked here, so a clone of this repository could not build the firmware
it ships. The library alone is now part of obu-firmware, as
obu-firmware/external/vanetza-idf: their external/vanetza-idf at commit
cf4b99f, unchanged (9775 files; see its PROVENANCE.md). CMake takes it from
there by default; -DVANETZA_IDF_DIR still points the build elsewhere.

The rest of the colleague's tree (their own VAM firmware, PKI tooling,
station-link Python tools, the V2X2MAP bridge) stays out of this repository
and gitignored; nothing is pushed to their repository. NOTES.md, docs/06,
TODO.md and the pcap verifier's usage line point at the new location.
2026-09-24 10:56:05 +02:00

112 lines
2.7 KiB
C++

#ifndef OBJECT_CONTAINER_HPP_25SOHVUH
#define OBJECT_CONTAINER_HPP_25SOHVUH
#include <functional>
#include <map>
#include <memory>
#include <typeindex>
#include <type_traits>
namespace vanetza
{
class ObjectContainer
{
private:
struct object_handle
{
template<typename T>
object_handle(std::unique_ptr<T> obj) :
object(obj.release()),
deleter([](void* ptr) { std::default_delete<T>()(static_cast<T*>(ptr)); })
{
}
~object_handle() {
deleter(object);
object = nullptr;
}
void* object;
std::function<void(void*)> deleter;
};
using container_type = std::map<std::type_index, object_handle>;
public:
ObjectContainer() = default;
// no copy
ObjectContainer(const ObjectContainer&) = delete;
ObjectContainer& operator=(const ObjectContainer&) = delete;
// allow move
ObjectContainer(ObjectContainer&&) = default;
ObjectContainer& operator=(ObjectContainer&&) = default;
bool empty() const { return m_container.empty(); }
std::size_t size() const { return m_container.size(); }
void clear() { m_container.clear(); }
template<typename T>
void erase()
{
m_container.erase(std::type_index(typeid(T)));
}
template<typename T>
T* find()
{
T* result = nullptr;
auto found = m_container.find(std::type_index(typeid(T)));
if (found != m_container.end()) {
result = static_cast<T*>(found->second.object);
}
return result;
}
template<typename T>
const T* find() const
{
const T* result = nullptr;
auto found = m_container.find(std::type_index(typeid(T)));
if (found != m_container.end()) {
result = static_cast<const T*>(found->second.object);
}
return result;
}
template<typename T>
bool insert(std::unique_ptr<T> obj)
{
static_assert(std::is_object<T>() && !std::is_const<T>(),
"Only non-const objects are supported by ObjectContainer");
return m_container.emplace(std::type_index(typeid(T)), std::move(obj)).second;
}
template<typename T>
T& get()
{
static_assert(std::is_default_constructible<T>(),
"Only default constructible types are accessible through ObjectContainer::get");
T* result = find<T>();
if (!result) {
std::unique_ptr<T> obj { new T() };
result = obj.get();
if (!insert(std::move(obj)))
result = nullptr;
}
assert(result);
return *result;
}
private:
container_type m_container;
};
} // namespace vanetza
#endif /* OBJECT_CONTAINER_HPP_25SOHVUH */