libcheri_enter_init()
initializes the landing-pad environment for system-object invocation.
It implements a stack landing pad for system classes provided by libcheri. The single stack is statically allocated – meaning no concurrent invocation from sandboxes in multiple threads (or reentrantly). Currently, that is ensured by virtue of applications not themselves invoking sandboxes concurrently.
// file:
// lib/libcheri/libcheri_enter.c
void
libcheri_enter_init(void)
{
/* XXX: Should be MAP_STACK, but that is broken. */
__libcheri_enter_stack = mmap(NULL, LIBCHERI_ENTER_STACK_SIZE,
PROT_READ | PROT_WRITE, MAP_ANON, -1, 0);
assert(__libcheri_enter_stack != MAP_FAILED);
/*
* In CheriABI, we use the capability returned by mmap(2), which $sp
* will be relative to, and implement solely $csp. Otherwise, assume
* a global $sp and use $c0.
*/
#ifdef __CHERI_PURE_CAPABILITY__
__libcheri_enter_stack_csp = (caddr_t)__libcheri_enter_stack +
LIBCHERI_ENTER_STACK_SIZE;
#else
__libcheri_enter_stack_cap = cheri_getdefault();
__libcheri_enter_stack_sp =
(register_t)((char *)__libcheri_enter_stack +
LIBCHERI_ENTER_STACK_SIZE);
#endif
__libcheri_object_creturn = libcheri_make_sealed_return_object();
}
For a sandbox to call system class services, the Cheri System class CCall landing pad code is designed for a user sandbox to trigger the CCall.
CHERI system class CCall landing pad code: catches CCalls inbound from sandboxes seeking system services, and bootstraps C code. A number of differences from sandboxed code, including how $c0 is handled, and not setting up the C heap.
Macro LIBCHERI_CLASS_ASM(class)
is defined in lib/libcheri/mips/libcheri_system_md.h
, which includes the definition of global entry point for all sandboxes: __libcheri_## class ## _entry
.
General what it do includes:
DDC
via IDC
. Then__libcheri_enter_stack_***
;_gp
;try to get method vtable and call methods;
cjalr
into the proper methods;define return code:
__libcheri_object_creturn
capability;__libcheri_object_creturn
into c1, c2
;CCALL($c1, $c2)
; //??? why this is a ccall not jalr? Differences between CCALL
and cjalr
are ??For pure capability with captable:
__libcheri_enter_stack_csp
, which is derived from pcc
, captab_rel
, and __libcheri_enter_stack_csp
;__libcheri_object_creturn
, is derived from pcc
and captab_rel
;For pure capability without captable:
__libcheri_enter_stack_csp
;__libcheri_object_creturn
is derived directly;For hybrid mode:
__libcheri_enter_stack_cap
, and __libcheri_enter_stack_sp
;_gp
;return capability __libcheri_object_creturn
is derived directly;
// file:
// lib/libcheri/mips/libcheri_system_md.h
#define LIBCHERI_CLASS_ASM(class)
Callers:
Both are defined in [lib/libcheri/mips/libcheri_classes_cabi.S]() for CheriABI and [lib/libcheri/mips/libcheri_classes_hybrid.S]() for hybrid ABI;
Method numbers:
// file:
//
/*
* Method numbers used by the sandbox runtime itself.
*
* WARNING: These values must match those currently hard coded in the sandbox
* C runtime (lib/csu/libcheri/crt_invoke.S and crt_rtld.S).
*
* NB: In the future, these should be via a reserved entry point rather than
* the primary object-capability 'invoke' entry point, so that they can be
* called only by the runtime.
*/
#define SANDBOX_RUNTIME_CONSTRUCTORS (-1)
#define SANDBOX_RUNTIME_DESTROCTORS (-2)
#define CHERI_SYSTEM_USER_BASE 1000
#define CHERI_SYSTEM_USER_CEILING 2000
If you could revise
the fundmental principles of
computer system design
to improve security...
... what would you change?