DocsCapabilities

Kore ABI

Capabilities

The stamped capability record in a task's arena: identity, kinds, rights, and what userland can and cannot do with a stamp.

Source: cap.rs

Identity

A capability's identity is a Cid: a 64-bit value with the resource's catalog id in the high 32 bits and a tag in the low 32. Tags are revocation identities, unique per epoch; retiring a tag revokes that capability and, by closure, every descendant that carries it. Tag 0 is reserved, so Cid::NULL (zero, meaning "no parent" or "no holder") can never be minted.

A capability can be derived at most MAX_DEPTH = 16 levels below its root. A capability at that depth can't derive further.

The record

Each capability lives in its holder's arena as a 128-byte CapRecord, #[repr(C)], linked identically by the kernel and by userland:

OffsetFieldTypeMeaning
0cidCidThis capability's identity
8parentCidThe parent, or NULL for a primordial root
16holderCidThe address-space root allowed to use it
24scope_ridu64The resource it authorizes
32rightsRightsGranted authority bits
34kindu16The resource kind
36epochu32The epoch the stamp was sealed under
40chain_lenu8Ancestor-chain length, at most 16
44chain[u32; 16]Ancestor tags, oldest first
108mac[u8; 16]The kernel's 128-bit AES-CMAC stamp

The record's size is pinned by assertion; the offsets are its repr(C) layout.

The stamp

mac is an AES-CMAC over every field above it, in declaration order, under a key only the kernel holds. Because the ancestor chain is inside the stamped message, a record can't be edited to dodge an ancestor's revocation.

What a program can do with a record: read its fields with pure readers, pass slot indices, and decode the bind-inert reports the kernel returns. What it can't: mint, verify or forge one. A record presented by a task other than its holder fails the kernel's bind gate, so a leaked capability is inert. Holding the bytes is not holding the authority.

Rights

BitRightMeaning
1 << 0ACCESSThe read projection
1 << 1MODIFYThe write projection
1 << 2DERIVECreate attenuated children; also required to send a capability
1 << 3REVOKERetire the capability and its subtree

The other four bits are reserved, and the kernel refuses any request that sets one. A derive can request only a subset of its parent's rights.

Resource kinds

ResourceKind is a u16, append-only. There are 44 kinds in this export. Kinds 0–7 are platform resources the kernel discovers at boot; the rest exist only by derivation.

KindsCovers
LogicalCpu, CpuShare, CpuReserve, FpuProcessors and run authority
PhysRegion, PhysExtent, Region, Subpool, Heap, MemLease, LeasedRegion, VirtMemory, AddrSpaceMemory and address spaces
PciDevice, PlatformDevice, RootComplex, PlatformBus, MmioRegion, IoPortGrantDevices and their registers
Iommu, IovaRegion, DeviceMmuDMA translation
IrqController, IrqRoute, Timer, SerialInterrupts, timers and the console
ChannelSpace, Channel, ChanSend, ChanRecvRendezvous channels
Task, ExecMint, ExecAuthority, InvocationWitnessTasks and executable memory
Display, SystemPower, SystemObserveDisplay, power and observation
DomainRegistration, MemoryFabricRoute, FabricRegistrar, MemoryControllerMemory domains and routes
Hypervisor, GuestSpace, GuestRegionVirtual machines

The arena

Each task owns an arena of 128-byte record slots. Descriptors name capabilities by slot index, never by Cid, so a name means nothing outside the arena that owns it. SlotRef is opaque; the only ways to make one are SlotRef::from_wire, the audit point for numbers that came from a peer, and the runtime's slot allocator.

The arena is mapped read-only into the task, followed by a one-page read-only execution-advice page. A task writes to its slots only by committing sessions, and the kernel re-verifies a record's stamp each time a session binds it, so a corrupted slot fails instead of granting anything. DERIVE_KIND_ARENA_EXTEND grows the arena by one chunk of slots, mapped read-only beside the first.

Bind-inert reports

The kernel returns data in result slots without minting authority. A report is a record with a NULL cid and a report kind in the 0xFF02 band, with a magic value in parent. It can be read but can never bind as a capability. There are 20 report kinds, distinct by assertion: device records, geometry reports, exit reports, quiesce reports and others. CapRecord::vacant(), the all-zero record, is their base.