diff --git a/zion/capability/capability_table.cpp b/zion/capability/capability_table.cpp index 4725389..1036679 100644 --- a/zion/capability/capability_table.cpp +++ b/zion/capability/capability_table.cpp @@ -17,7 +17,8 @@ uint64_t CapabilityTable::AddExistingCapability( glcr::RefPtr CapabilityTable::GetCapability(uint64_t id) { MutexHolder h(lock_); if (!capabilities_.Contains(id)) { - panic("Bad cap access {}", id); + dbgln("Bad cap access {}", id); + return {}; } return capabilities_.at(id); } @@ -25,7 +26,8 @@ glcr::RefPtr CapabilityTable::GetCapability(uint64_t id) { glcr::RefPtr CapabilityTable::ReleaseCapability(uint64_t id) { MutexHolder h(lock_); if (!capabilities_.Contains(id)) { - panic("Bad cap release {}", id); + dbgln("Bad cap release {}", id); + return {}; } auto cap = capabilities_.at(id); (void)capabilities_.Delete(id); diff --git a/zion/include/zcall.h b/zion/include/zcall.h index 643a2e3..011ee04 100644 --- a/zion/include/zcall.h +++ b/zion/include/zcall.h @@ -56,6 +56,7 @@ SYS5(ReplyPortRecv, z_cap_t, reply_port_cap, uint64_t*, num_bytes, void*, data, uint64_t*, num_caps, z_cap_t*, caps); SYS3(CapDuplicate, z_cap_t, cap_in, z_perm_t, perm_mask, z_cap_t*, cap_out); +SYS1(CapRelease, z_cap_t, cap); SYS1(MutexCreate, z_cap_t*, mutex_cap); SYS1(MutexLock, z_cap_t, mutex_cap); diff --git a/zion/include/ztypes.h b/zion/include/ztypes.h index c5970b5..0bf4695 100644 --- a/zion/include/ztypes.h +++ b/zion/include/ztypes.h @@ -53,6 +53,7 @@ const uint64_t kZionEndpointCall = 0x65; // Capability Calls const uint64_t kZionCapDuplicate = 0x70; +const uint64_t kZionCapRelease = 0x71; // Syncronization Calls const uint64_t kZionMutexCreate = 0x80; diff --git a/zion/syscall/capability.cpp b/zion/syscall/capability.cpp index c30f6a9..a51919d 100644 --- a/zion/syscall/capability.cpp +++ b/zion/syscall/capability.cpp @@ -18,3 +18,11 @@ z_err_t CapDuplicate(ZCapDuplicateReq* req) { cap->permissions() & req->perm_mask); return glcr::OK; } + +z_err_t CapRelease(ZCapReleaseReq* req) { + auto& proc = gScheduler->CurrentProcess(); + if (proc.ReleaseCapability(req->cap).empty()) { + return glcr::CAP_NOT_FOUND; + } + return glcr::OK; +} diff --git a/zion/syscall/capability.h b/zion/syscall/capability.h index 07ee631..f473db4 100644 --- a/zion/syscall/capability.h +++ b/zion/syscall/capability.h @@ -3,3 +3,4 @@ #include "include/zcall.h" z_err_t CapDuplicate(ZCapDuplicateReq* req); +z_err_t CapRelease(ZCapReleaseReq* req); diff --git a/zion/syscall/syscall.cpp b/zion/syscall/syscall.cpp index ca5623f..abaf609 100644 --- a/zion/syscall/syscall.cpp +++ b/zion/syscall/syscall.cpp @@ -81,6 +81,7 @@ extern "C" z_err_t SyscallHandler(uint64_t call_id, void* req) { CASE(ReplyPortRecv); // syscall/capability.h CASE(CapDuplicate); + CASE(CapRelease); // syscall/syncronization.h CASE(MutexCreate); CASE(MutexLock);