aos/usr/init/distops/invocations.h
Daniel Schwyn 6d444bf552 Main handout
Signed-off-by: Daniel Schwyn <daniel.schwyn@inf.ethz.ch>
2022-03-03 14:57:51 +01:00

321 lines
12 KiB
C

/**
* \file
* \brief Capability invocations specific to the distributed capability operations
* NOTE: copied from Barrelfish's montior code
* * usr/monitor/include/monitor_invocations.h
* * usr/monitor/include/arch/arm/monitor_invocations_arch.h
* * usr/monitor/include/dom_invocations.h
*/
/*
* Copyright (c) 2007, 2008, 2009, 2010, 2016, ETH Zurich.
* All rights reserved.
*
* This file is distributed under the terms in the attached LICENSE file.
* If you do not find this file, copies can be found by writing to:
* ETH Zurich D-INFK, Universitaetstr. 6, CH-8092 Zurich. Attn: Systems Group.
*/
#ifndef DISTOPS_INVOCATIONS_H
#define DISTOPS_INVOCATIONS_H
#include <aos/cap_predicates.h>
#include <aos/caddr.h>
#include <aos/invocations_arch.h>
#include <aos/invocations.h>
#include <aos/syscall_arch.h>
#include <aos/syscalls.h>
#include <aos/types.h>
#include <barrelfish_kpi/capabilities.h>
#include <barrelfish_kpi/distcaps.h>
#include <stdbool.h>
#include "domcap.h"
#define DEBUG_INVOCATION(x...)
static inline errval_t
invoke_monitor_create_cap(uint64_t *raw, capaddr_t caddr, int level, capaddr_t slot, coreid_t owner)
{
DEBUG_INVOCATION("%s: called from %p\n", __FUNCTION__, __builtin_return_address(0));
return cap_invoke6(cap_kernel, KernelCmd_Create_cap, caddr, level, slot,
owner, (uintptr_t)raw).error;
}
STATIC_ASSERT(ObjType_Num < 0xFFFF, "retype invocation argument packing does not truncate enum objtype");
static inline errval_t
invoke_monitor_remote_cap_retype(capaddr_t src_root, capaddr_t src, gensize_t offset,
enum objtype newtype, gensize_t objsize, size_t count,
capaddr_t to_cspace, capaddr_t to, capaddr_t slot,
int level)
{
DEBUG_INVOCATION("%s: called from %p\n", __FUNCTION__, __builtin_return_address(0));
assert(newtype < ObjType_Num);
assert(level <= 0xFF);
assert(slot <= 0xFFFF);
return cap_invoke10(cap_kernel, KernelCmd_Retype,
src_root, src, offset, ((uint32_t)level << 16) | newtype,
objsize, count, to_cspace, to, slot).error;
}
static inline errval_t
invoke_monitor_revoke_mark_relations(uint64_t *raw_base)
{
DEBUG_INVOCATION("%s: called from %p\n", __FUNCTION__, __builtin_return_address(0));
// XXX: this is assumed in client code of this function!
assert(sizeof(struct capability) / sizeof(uint64_t) <= 4);
return cap_invoke2(cap_kernel, KernelCmd_Revoke_mark_relations,
(uintptr_t)raw_base).error;
}
static inline errval_t
invoke_monitor_has_descendants(uint64_t *raw, bool *res)
{
DEBUG_INVOCATION("%s: called from %p\n", __FUNCTION__, __builtin_return_address(0));
// XXX: this is assumed in client code of this function!
assert(sizeof(struct capability) / sizeof(uint64_t) <= 4);
struct sysret sysret;
sysret = cap_invoke2(cap_kernel, KernelCmd_Has_descendants,
(uintptr_t)raw);
if (err_is_ok(sysret.error)) {
*res = sysret.value;
}
return sysret.error;
}
static inline errval_t
invoke_monitor_is_retypeable(uint64_t *raw, gensize_t offset,
gensize_t objsize, size_t count)
{
assert(sizeof(struct capability) <= 4*sizeof(uint64_t));
return cap_invoke5(cap_kernel, KernelCmd_Is_retypeable,
(uintptr_t)raw, offset, objsize, count).error;
}
static inline errval_t
invoke_monitor_copy_existing(uint64_t *raw, capaddr_t croot_addr, capaddr_t cn_addr,
int cn_level, cslot_t slot)
{
DEBUG_INVOCATION("%s: called from %p\n", __FUNCTION__, __builtin_return_address(0));
// XXX: this is assumed in client code of this function!
assert(sizeof(struct capability) <= 4*sizeof(uint64_t));
return cap_invoke6(cap_kernel, KernelCmd_Copy_existing,
croot_addr, cn_addr, cn_level, slot, (uintptr_t)raw).error;
}
//{{{1 Cap identification and relation checking
static inline errval_t
invoke_monitor_remote_relations(capaddr_t root_cap, int root_level,
capaddr_t cap, int level,
uint8_t relations, uint8_t mask,
uint8_t *ret_remote_relations)
{
struct sysret r = cap_invoke6(cap_kernel, KernelCmd_Remote_relations,
root_cap, root_level, cap, level,
((uint16_t)relations) | (((uint16_t)mask)<<8));
if (err_is_ok(r.error) && ret_remote_relations) {
*ret_remote_relations = r.value;
}
return r.error;
}
static inline errval_t
invoke_monitor_cap_has_relations(capaddr_t caddr, uint8_t level, uint8_t mask,
uint8_t *res)
{
assert(res);
struct sysret ret = cap_invoke4(cap_kernel, KernelCmd_Cap_has_relations,
caddr, level, mask);
if (err_is_ok(ret.error)) {
*res = ret.value;
}
return ret.error;
}
static inline errval_t
invoke_monitor_identify_cap(capaddr_t cap, int level, struct capability *out)
{
return cap_invoke4(cap_kernel, KernelCmd_Identify_cap, cap, level,
(uintptr_t)out).error;
}
static inline errval_t
invoke_monitor_identify_domains_cap(capaddr_t root_cap, int root_level,
capaddr_t cap, int level,
struct capability *out)
{
return cap_invoke6(cap_kernel, KernelCmd_Identify_domains_cap,
root_cap, root_level, cap, level, (uintptr_t)out).error;
}
//{{{1 Cap zeroing
static inline errval_t
invoke_monitor_nullify_cap(capaddr_t cap, int level)
{
return cap_invoke3(cap_kernel, KernelCmd_Nullify_cap, cap, level).error;
}
//{{{1 Cap ownership manipulation
static inline errval_t
invoke_monitor_get_cap_owner(capaddr_t root, int rlevel, capaddr_t cap, int clevel, coreid_t *ret_owner)
{
assert(ret_owner);
struct sysret sysret = cap_invoke5(cap_kernel, KernelCmd_Get_cap_owner, root, rlevel, cap, clevel);
if (err_is_ok(sysret.error)) {
*ret_owner = sysret.value;
}
return sysret.error;
}
static inline errval_t
invoke_monitor_set_cap_owner(capaddr_t root, int rlevel, capaddr_t cap, int clevel, coreid_t owner)
{
return cap_invoke6(cap_kernel, KernelCmd_Set_cap_owner, root, rlevel, cap, clevel, owner).error;
}
//{{{1 Cap locking
static inline errval_t
invoke_monitor_lock_cap(capaddr_t root, int rlevel, capaddr_t cap, int clevel)
{
return cap_invoke5(cap_kernel, KernelCmd_Lock_cap, root, rlevel, cap, clevel).error;
}
static inline errval_t
invoke_monitor_unlock_cap(capaddr_t root, int rlevel, capaddr_t cap, int clevel)
{
return cap_invoke5(cap_kernel, KernelCmd_Unlock_cap, root, rlevel, cap, clevel).error;
}
//{{{1 Delete and revoke state machine stepping
static inline errval_t
invoke_monitor_delete_last(capaddr_t root, int rlevel, capaddr_t cap, int clevel,
capaddr_t retcn, int retcnlevel, cslot_t retslot)
{
return cap_invoke8(cap_kernel, KernelCmd_Delete_last, root, rlevel, cap,
clevel, retcn, retcnlevel, retslot).error;
}
static inline errval_t
invoke_monitor_delete_foreigns(capaddr_t cap, int level)
{
return cap_invoke3(cap_kernel, KernelCmd_Delete_foreigns, cap, level).error;
}
static inline errval_t
invoke_monitor_revoke_mark_target(capaddr_t root, int rlevel,
capaddr_t cap, int clevel)
{
return cap_invoke5(cap_kernel, KernelCmd_Revoke_mark_target,
root, rlevel, cap, clevel).error;
}
static inline errval_t
invoke_monitor_delete_step(capaddr_t retcn, int retcnlevel, cslot_t retslot)
{
return cap_invoke4(cap_kernel, KernelCmd_Delete_step,
retcn, retcnlevel, retslot).error;
}
static inline errval_t
invoke_monitor_clear_step(capaddr_t retcn, int retcnlevel, cslot_t retslot)
{
return cap_invoke4(cap_kernel, KernelCmd_Clear_step,
retcn, retcnlevel, retslot).error;
}
struct capability;
bool monitor_can_send_cap(struct capability *cap);
errval_t monitor_cap_identify(struct capref cap, struct capability *out);
errval_t monitor_domains_cap_identify(struct capref croot, capaddr_t cap,
int vlevel, struct capability *out);
errval_t monitor_domcap_remote_relations(struct capref croot, capaddr_t cptr,
int level, uint8_t relations, uint8_t
mask, uint8_t *ret_relations);
errval_t monitor_remote_relations(struct capref cap, uint8_t relations, uint8_t
mask, uint8_t *ret_relations);
errval_t monitor_cap_has_relations(struct capref cap, uint8_t mask,
uint8_t *res);
errval_t monitor_cap_create(struct capref dest, struct capability *cap,
coreid_t owner);
errval_t monitor_identify_cnode_get_cap(struct capability *cnode_raw,
capaddr_t slot, struct capability *ret);
errval_t monitor_nullify_cap(struct capref cap);
errval_t monitor_retype_remote_cap(struct capref dest_start, struct capref src, gensize_t offset,
enum objtype newtype, gensize_t objsize,
gensize_t count);
errval_t monitor_domcap_retype_remote_cap(struct domcapref dest_start, struct domcapref src, gensize_t offset, enum objtype newtype, gensize_t objsize, gensize_t count, capaddr_t slot);
errval_t monitor_create_caps(struct capref src_root, struct capref dest_root,
enum objtype newtype, gensize_t objsize,
size_t count, capaddr_t src,
int src_level, size_t offset, capaddr_t dest_cn,
int dest_level, cslot_t dest_slot);
errval_t monitor_copy_if_exists(struct capability* cap, struct capref dest);
errval_t monitor_delete_remote_cap(struct capref croot, capaddr_t src, int level);
errval_t monitor_revoke_remote_cap(struct capref croot, capaddr_t src, int level);
errval_t monitor_get_cap_owner(struct capref croot, capaddr_t cptr, int level, coreid_t *ret_owner);
errval_t monitor_set_cap_owner(struct capref croot, capaddr_t cptr, int level, coreid_t owner);
errval_t monitor_lock_cap(struct capref croot, capaddr_t cptr, int level);
errval_t monitor_unlock_cap(struct capref croot, capaddr_t cptr, int level);
errval_t monitor_has_descendants(struct capability *cap, bool *res);
errval_t monitor_is_retypeable(struct capability *cap, gensize_t offset,
gensize_t objsize, size_t count);
static inline errval_t monitor_domcap_lock_cap(struct domcapref cap) {
return monitor_lock_cap(cap.croot, cap.cptr, cap.level);
}
static inline errval_t monitor_domcap_unlock_cap(struct domcapref cap) {
return monitor_unlock_cap(cap.croot, cap.cptr, cap.level);
}
static inline errval_t monitor_domcap_identify(struct domcapref cap, struct capability *out) {
return monitor_domains_cap_identify(cap.croot, cap.cptr, cap.level, out);
}
static inline errval_t
monitor_get_domcap_owner(struct domcapref cap, coreid_t *ret_owner)
{
return monitor_get_cap_owner(cap.croot, cap.cptr, cap.level, ret_owner);
}
static inline errval_t
monitor_set_domcap_owner(struct domcapref cap, coreid_t owner)
{
return monitor_set_cap_owner(cap.croot, cap.cptr, cap.level, owner);
}
/*
* Domain cnode invocations
*/
static inline errval_t dom_cnode_get_state(struct domcapref cap, distcap_state_t *ret)
{
return invoke_cnode_get_state(cap.croot, cap.cptr, cap.level, ret);
}
static inline errval_t dom_cnode_delete(struct domcapref cap)
{
return invoke_cnode_delete(cap.croot, cap.cptr, cap.level);
}
/*
* Delete- and revoke-related operations
*/
errval_t monitor_delete_last(struct capref croot, capaddr_t cptr, int level,
struct capref ret_cap);
errval_t monitor_delete_foreigns(struct capref cap);
errval_t monitor_revoke_mark_target(struct capref croot,
capaddr_t cptr,
int level);
errval_t monitor_revoke_mark_relations(struct capability *cap);
errval_t monitor_delete_step(struct capref ret_cap);
errval_t monitor_clear_step(struct capref ret_cap);
#endif