207 lines
5.9 KiB
C
207 lines
5.9 KiB
C
#pragma once
|
|
|
|
/**
|
|
* The lcrash system bus is a root device which manages all other associated devices, and handles bookkeeping for other subsystems (e.g. classifying devices)
|
|
* The system bus supports device names to aid debuggers, however these names are otherwise meaningless and pointers to structures should be used instead
|
|
*
|
|
* Example device tree:
|
|
* /SYSBUS
|
|
* /PCI
|
|
* /PCI0000:00:00.0
|
|
* $ETHERNET
|
|
* /PCI0000:00:00.1
|
|
* $FRAMEBUF
|
|
* $TEXTBUF
|
|
* /ACPI:0
|
|
* $BATTERY
|
|
* /ACPI:1
|
|
* $SERIAL
|
|
* /COM:0
|
|
* $SERIAL
|
|
* /COM:1
|
|
* $SERIAL
|
|
*
|
|
* Device capabilities provide a way for devices to expose functionality without writing device specific code, a capability is defined by the following structure
|
|
* struct SysbusDeviceCapability {
|
|
* // Name of the device capability
|
|
* const char* CapabilityName;
|
|
* };
|
|
*
|
|
* Devices types are defined by the following structure:
|
|
* struct SysbusDeviceDescription {
|
|
* // Name of the device type
|
|
* const char* DeviceName;
|
|
*
|
|
* // == Instance Management ==
|
|
* // List of device instances
|
|
* struct SysbusDevice** Instances;
|
|
*
|
|
* // Device initialization code, returns 0 if ok
|
|
* int (*CreateDevice)(struct SysbusDevice* Device, void* Data);
|
|
*
|
|
* // Cleanup code for before a device is deleted, returns 0 if ok
|
|
* int (*DeleteDevice)(struct SysbusDevice* Device);
|
|
*
|
|
* // == Capablities ==
|
|
* // Returns a capability specific structure if a capability is present, otherwise returns NULL
|
|
* void* (*GetCapability)(struct SysbusDevice* Device, struct SysbusDeviceCapability* Capability);
|
|
* };
|
|
*
|
|
* Devices are stored in the following structure:
|
|
* struct SysbusDevice {
|
|
* // Pointer to the device type structure
|
|
* const struct SysbusDeviceDescription* DeviceDescription;
|
|
*
|
|
* // Name of the device
|
|
* const char* DeviceName;
|
|
*
|
|
* // Device specific data
|
|
* void* DeviceData;
|
|
*
|
|
* // Child devices
|
|
* struct SysbusDevice** Children;
|
|
* };
|
|
*
|
|
* Drivers can define a new device type by calling `struct SysbusDeviceDescription* SysbusCreateDeviceDescription()` which
|
|
* Allocates and returns a device description structure
|
|
*
|
|
* Drivers must free device types with `void SysbusDeleteDeviceDescription(struct SysbusDeviceDescription* DESCRIPTION)` which
|
|
* Deletes a DESCRIPTION's instances
|
|
* Deallocates a device DESCRIPTION structure
|
|
*
|
|
* Drivers can create a new device by calling `struct SysbusDevice* SysbusCreateDevice(struct SysbusDeviceDescription* DESCRIPTION, void* DATA)` which
|
|
* DEVICE = Allocate a device structure
|
|
* Initializes it by calling DESCRIPTION::CreateDevice(DEVICE, DATA)
|
|
* if ok then
|
|
* Adds the DEVICE to the DESCRIPTION's instance list
|
|
* Returns the DEVICE
|
|
* otherwise returns NULL
|
|
*
|
|
* Drivers must free devices with `void SysbusDeleteDevice(struct SysbusDevice* DEVICE)` which
|
|
* Uninitializes the DEVICE by calling DEVICE::DeviceDescription::DeleteDevice(DEVICE)
|
|
* Removes the DEVICE from the DEVICE::DeviceDescription's instance list
|
|
* Deallocates the DEVICE
|
|
*/
|
|
|
|
#include <lcrash/types.h>
|
|
|
|
/**
|
|
* Structure that describes a specific device capablility
|
|
*/
|
|
struct SysbusDeviceCapability {
|
|
// Name of the device capability
|
|
const char* CapabilityName;
|
|
};
|
|
|
|
/**
|
|
* Structure that describes a device and allows them to hook the sysbus subsystem
|
|
*/
|
|
struct SysbusDeviceDescription {
|
|
/// Device name, this is only used for debugging
|
|
const c8* DeviceName;
|
|
|
|
/// List of device instances
|
|
/// Do not hold pointers to this list
|
|
/// Managed by the sysbus subsystem. DRIVERS, DO NOT MODIFY THIS LIST.
|
|
struct SysbusDevice** Instances;
|
|
|
|
/// Number of instances
|
|
/// Managed by the sysbus subsystem. DO NOT MODIFY THIS.
|
|
u32 InstanceCount;
|
|
|
|
/// Instance array length
|
|
/// Managed by the sysbus subsysyem. DO NOT MODIFY THIS.
|
|
/// \internal
|
|
u32 InstanceSlots;
|
|
|
|
/// Called by the sysbus subsystem when a device is created, use this to initialize a device
|
|
/// \returns 0 on success
|
|
s32 (*CreateDevice)(struct SysbusDevice*, void*);
|
|
|
|
/// Called by the sysbus subsystem when a device is deleted, use this to deinitialize a device
|
|
/// \returns 0 on success
|
|
s32 (*DeleteDevice)(struct SysbusDevice* Device);
|
|
|
|
/// Returns a capability specific structure if a capability is present, otherwise returns NULL
|
|
void* (*GetCapability)(struct SysbusDevice* Device, struct SysbusDeviceCapability* Capability);
|
|
};
|
|
|
|
/**
|
|
* Structure that describes an instace of a specific device
|
|
*/
|
|
struct SysbusDevice {
|
|
/// Pointer to the device type structure
|
|
const struct SysbusDeviceDescription* DeviceDescription;
|
|
|
|
/// Name of the device
|
|
const c8* DeviceName;
|
|
|
|
/// Device specific data
|
|
void* DeviceData;
|
|
|
|
/// Parent device
|
|
/// Managed by the sysbus subsystem. DO NOT MODIFY THIS.
|
|
struct SysbusDevice* Parent;
|
|
|
|
/// Child devices
|
|
/// Managed by the sysbus subsystem. DRIVERS, DO NOT MODIFY THIS LIST
|
|
/// Do not hold pointers to this list, it may be moved or resized as needed
|
|
struct SysbusDevice** Children;
|
|
|
|
/// Number of children
|
|
/// Managed by the sysbus subsystem. DO NOT MODIFY THIS.
|
|
u32 ChildCount;
|
|
|
|
/// Child array length
|
|
/// Managed by the sysbus subsysyem. DO NOT MODIFY THIS.
|
|
/// \internal
|
|
u32 ChildSlots;
|
|
};
|
|
|
|
/// Initialize the sysbus subsystem
|
|
void SysbusInitialize();
|
|
|
|
/**
|
|
* Create and return a sysbus device description
|
|
*/
|
|
struct SysbusDeviceDescription* SysbusCreateDeviceDescription();
|
|
|
|
/**
|
|
* Delete a sysbus device description
|
|
*/
|
|
void SysbusDeleteDeviceDescription(struct SysbusDeviceDescription* Description);
|
|
|
|
/**
|
|
* Create a new device
|
|
*/
|
|
struct SysbusDevice* SysbusCreateDevice(
|
|
struct SysbusDeviceDescription* Description,
|
|
struct SysbusDevice* Parent,
|
|
void* Data
|
|
);
|
|
|
|
/**
|
|
* Delete a device
|
|
*/
|
|
void SysbusDeleteDevice(struct SysbusDevice* Device);
|
|
|
|
/**
|
|
* Create a sysbus capability
|
|
*/
|
|
struct SysbusDeviceCapability* SysbusCreateCapability();
|
|
|
|
/**
|
|
* Delete a sysbus capability
|
|
*/
|
|
void SysbusDeleteCapability();
|
|
|
|
/**
|
|
* Get a sysbus capability
|
|
*/
|
|
void* SysbusGetCapability(struct SysbusDevice* Device, struct SysbusDeviceCapability* Capability);
|
|
|
|
/**
|
|
* Get the system bus device
|
|
*/
|
|
struct SysbusDevice* SysbusGetRootDevice();
|