Skip to content

Host API Documentation

thom_tl edited this page Apr 30, 2022 · 9 revisions

Host API Documentation

The following page describes what functions the host OS must implement in order to use LAI.

laihost functions

These are functions that need to be implemented by the host OS, however all these functions are made weak so if they are not implemented and needed lai will gracefully call laihost_panic()

These functions are in <lai/host.h>

Logging

/* Logs a message. level can either be LAI_DEBUG_LOG for debugging info,
   or LAI_WARN_LOG for warnings */
void laihost_log(int level, const char *msg);

/* Reports a fatal error, and halts. */
__attribute__((noreturn)) void laihost_panic(const char *msg);

Memory management

/* Self-explanatory */
void *laihost_malloc(size_t size);
void *laihost_realloc(void *oldptr, size_t newsize, size_t oldsize);
void laihost_free(void *ptr, size_t size);

/* Maps count bytes from the given physical address and returns
   a virtual address that can be used to access the memory. */
void *laihost_map(size_t address, size_t count);

/* Unmaps count bytes from the given virtual address.
   LAI only calls this on memory that was previously mapped by laihost_map(). */
void laihost_unmap(void *pointer, size_t count);

Table access

/* Returns the (virtual) address of the n-th table that has the given signature,
   or NULL when no such table was found. */
void *laihost_scan(char *sig, size_t index);

Port access

/* Write a byte/word/dword to the given I/O port. */
void laihost_outb(uint16_t port, uint8_t val);
void laihost_outw(uint16_t port, uint16_t val);
void laihost_outd(uint16_t port, uint32_t val);

/* Read a byte/word/dword from the given I/O port. */
uint8_t laihost_inb(uint16_t port);
uint16_t laihost_inw(uint16_t port);
uint32_t laihost_ind(uint16_t port);

PCI configuration space access

/* Write a byte/word/dword to the given device's PCI configuration space
   at the given offset. */
void laihost_pci_writeb(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset, uint8_t val);
void laihost_pci_writew(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset, uint16_t val);
void laihost_pci_writed(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset, uint32_t val);

/* Read a byte/word/dword from the given device's PCI configuration space
   at the given offset. */
uint8_t laihost_pci_readb(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset);
uint16_t laihost_pci_readw(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset);
uint32_t laihost_pci_readd(uint16_t seg, uint8_t bus, uint8_t slot, uint8_t fun, uint16_t offset);

Timing

/* Sleeps for the given amount of milliseconds. */
void laihost_sleep(uint64_t ms);

/* Returns a monotonic count in 100ns increments */
uint64_t laihost_timer(void);

Other

/* Reports information about a variable.
   This function does not need to be implemented. */
void laihost_handle_amldebug(lai_variable_t *var);

// Global handler for Notify, this function does not need to be implemented
void laihost_handle_global_notify(lai_nsnode_t *node, int code);

Synchronization

Synchronization functions are only needed if LAI is invoked from multiple threads. LAI's synchronization primitives resemble futexes.

/* Blocks the current thread.
   The host ensures that calls to laihost_sync_wait() and laihost_sync_wake()
   on the same lai_sync_state are totally ordered.
   Before blocking, sync->val is compared against val. If these two values are non-equal, the function returns immediately.
   Returns a non-zero value if the timeout was exhausted and zero otherwise. */
int laihost_sync_wait(struct lai_sync_state *sync, unsigned int val, int64_t timeout);

/* Unblocks a blocked thread.
   The host ensures that calls to laihost_sync_wait() and laihost_sync_wake()
   on the same lai_sync_state are totally ordered. */
void laihost_sync_wake(struct lai_sync_state *sync);

LAI makes two variables - namely sync->s and sync->p - freely available to the host implementation. As an implementation strategy, hosts can use sync->s to implement a (spin)lock and sync->p to point to a data structure that manages waiting threads.

Configuration functions

Lai also has a few functions that need to be called by the host OS in order to give information about the system, these functions are in <lai/core.h>

/* This function sets the ACPI revision of the system since this is not clear to lai since it does not have access to the RSDP */
void lai_set_acpi_revision(int revision);