#pragma once #include #include #include "capability/capability.h" #include "lib/mutex.h" class CapabilityTable { public: CapabilityTable(); CapabilityTable(CapabilityTable&) = delete; CapabilityTable& operator=(CapabilityTable&) = delete; template z_cap_t AddNewCapability(const glcr::RefPtr& object, uint64_t permissions); template z_cap_t AddNewCapability(const glcr::RefPtr& object) { return AddNewCapability(object, T::DefaultPermissions()); } z_cap_t AddExistingCapability(const glcr::RefPtr& cap); glcr::RefPtr GetCapability(uint64_t id); glcr::RefPtr ReleaseCapability(uint64_t id); private: Mutex lock_{"cap table"}; // TODO: Do some randomization. uint64_t next_cap_id_ = 0x100; // FIXME: use a map data structure. struct CapEntry { uint64_t id; glcr::RefPtr cap; }; glcr::LinkedList capabilities_; }; template uint64_t CapabilityTable::AddNewCapability(const glcr::RefPtr& object, uint64_t permissions) { MutexHolder h(lock_); uint64_t id = next_cap_id_++; capabilities_.PushBack( {.id = id, .cap = MakeRefCounted(object, permissions)}); return id; }