diff --git a/sys/voyageurs/xhci/control_command.h b/sys/voyageurs/xhci/control_command.h index d615e42..9cc05cd 100644 --- a/sys/voyageurs/xhci/control_command.h +++ b/sys/voyageurs/xhci/control_command.h @@ -21,7 +21,7 @@ class ReadControlCommand { uint64_t value = RequestConstants::Value() << 16; // TODO: May need to be non-0 for string descriptors. uint64_t index = (uint64_t)0 << 32; - uint64_t length = sizeof(Output) << 48; + uint64_t length = (uint64_t)0x1000 << 48; return { .parameter = request_type | request | value | index | length, .status = 8, @@ -34,7 +34,7 @@ class ReadControlCommand { XhciTrb DataTrb() { return { .parameter = output_phys_, - .status = sizeof(Output), + .status = 0x1000, .type_and_cycle = 1 | (1 << 5) | (3 << 10), .control = 1, }; diff --git a/sys/voyageurs/xhci/descriptors.h b/sys/voyageurs/xhci/descriptors.h index f54eb7e..8aec53b 100644 --- a/sys/voyageurs/xhci/descriptors.h +++ b/sys/voyageurs/xhci/descriptors.h @@ -34,3 +34,44 @@ class RequestConstants { static uint8_t Request() { return 0x6; }; static uint16_t Value() { return 0x100; }; }; + +struct ConfigurationDescriptor { + uint8_t length; + uint8_t type; + uint16_t total_length; + uint8_t num_interfaces; + uint8_t configuration_value; + uint8_t configuration_string_index; + uint8_t attributes; + uint8_t max_power; +} __attribute__((packed)); + +template <> +class RequestConstants { + public: + static uint8_t RequestType() { return 0x80; } + static uint8_t Request() { return 0x6; } + // TODO: Consider getting other description indexes. + static uint16_t Value() { return 0x200; } +}; + +struct InterfaceDescriptor { + uint8_t length; + uint8_t type; + uint8_t interface_number; + uint8_t alternate_setting; + uint8_t num_endpoints; + uint8_t interface_class; + uint8_t interface_subclass; + uint8_t interface_protocol; + uint8_t interfact_string_index; +} __attribute__((packed)); + +struct EndpointDescriptor { + uint8_t length; + uint8_t type; + uint8_t endpoint_address; + uint8_t attributes; + uint16_t max_packet_size; + uint8_t interval; +} __attribute__((packed)); diff --git a/sys/voyageurs/xhci/xhci_driver.cpp b/sys/voyageurs/xhci/xhci_driver.cpp index 8f21eaf..ba7bafa 100644 --- a/sys/voyageurs/xhci/xhci_driver.cpp +++ b/sys/voyageurs/xhci/xhci_driver.cpp @@ -31,6 +31,45 @@ void configure_device(void* void_device_slot) { dbgln("Descriptor Type {x}, ({x})", descriptor->type, descriptor->usb_spec); dbgln("Device Class/Sub/Protocol: {x}/{x}/{x}", descriptor->device_class, descriptor->device_subclass, descriptor->device_protocol); + dbgln("Num Configurations: {}", descriptor->num_configurations); + + ReadControlCommand config_command; + + device_slot->ExecuteReadControlCommand(config_command); + + ConfigurationDescriptor* config_descriptor = config_command.AwaitResult(); + + dbgln("Configuration Value: {x}", config_descriptor->configuration_value); + dbgln("Num Interfaces: {x}", config_descriptor->num_interfaces); + dbgln("Size: {x}, Total Length: {x}", config_descriptor->length, + config_descriptor->total_length); + + uint64_t next_vaddr = + reinterpret_cast(config_descriptor) + config_descriptor->length; + for (auto i = config_descriptor->num_interfaces; i > 0; i--) { + InterfaceDescriptor* interface = + reinterpret_cast(next_vaddr); + dbgln("Interface: {x}", interface->interface_number); + dbgln("Interface Class/Sub/Protocol: {x}/{x}/{x}", + interface->interface_class, interface->interface_subclass, + interface->interface_protocol); + dbgln("Num Endpoints: {x}", interface->num_endpoints); + + next_vaddr += interface->length; + for (auto j = interface->num_endpoints; j > 0; j--) { + EndpointDescriptor* endpoint = + reinterpret_cast(next_vaddr); + if (endpoint->type != 5) { + dbgln("Descriptor type {x}, skipping", endpoint->type); + j++; + next_vaddr += endpoint->length; + continue; + } + dbgln("Endpoint Addr: {x}", endpoint->endpoint_address); + dbgln("Endpoint Attr: {x}", endpoint->attributes); + next_vaddr += endpoint->length; + } + } } glcr::ErrorOr> XhciDriver::InitiateDriver( @@ -300,6 +339,11 @@ void XhciDriver::HandleCommandCompletion( } void XhciDriver::HandleTransferCompletion(const XhciTrb& transfer_event_trb) { + uint8_t status = transfer_event_trb.status >> 24; + if (status != 1 && status != 0xD) { + dbgln("Unexpected Status {x}", status); + return; + } uint8_t slot_id = transfer_event_trb.control >> 8; uint8_t endpoint_id = transfer_event_trb.control & 0x1F; uint64_t trb_phys = transfer_event_trb.parameter;