diff --git a/kernel/Makefile b/kernel/Makefile index b218f7b6..9d11f6b2 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -63,8 +63,6 @@ kernel: head.o main.o $(OBJ_LIST) cd ..;\ done - - clean: rm -rf $(GARBAGE) diff --git a/kernel/driver/pci/msi.c b/kernel/driver/pci/msi.c index aba4bde3..d85a8b51 100644 --- a/kernel/driver/pci/msi.c +++ b/kernel/driver/pci/msi.c @@ -13,7 +13,6 @@ */ #define pci_get_arch_msi_message_data(vector, processor, edge_trigger, assert) ((uint32_t)((vector & 0xff) | (edge_trigger == 1 ? 0 : (1 << 15)) | ((assert == 0) ? 0 : (1 << 14)))) - /** * @brief 启用 Message Signaled Interrupts * @@ -25,9 +24,10 @@ * * @return 返回码 */ -int pci_enable_msi(void *header, uint8_t vector, uint32_t processor, uint8_t edge_trigger, uint8_t assert) +// int pci_enable_msi(void *header, uint8_t vector, uint32_t processor, uint8_t edge_trigger, uint8_t assert) +int pci_enable_msi(struct msi_desc_t *msi_desc) { - struct pci_device_structure_header_t *ptr = (struct pci_device_structure_header_t *)header; + struct pci_device_structure_header_t *ptr = msi_desc->pci_dev; uint32_t cap_ptr; uint32_t tmp; uint16_t message_control; @@ -36,8 +36,8 @@ int pci_enable_msi(void *header, uint8_t vector, uint32_t processor, uint8_t edg { case 0x00: // general device if (!(ptr->Status & 0x10)) - return E_NOT_SUPPORT_MSI; - + return E_NOT_SUPPORT_MSI; + cap_ptr = ((struct pci_device_structure_general_device_t *)ptr)->Capabilities_Pointer; tmp = pci_read_config(ptr->bus, ptr->device, ptr->func, cap_ptr); // 读取cap+0x0处的值 @@ -47,14 +47,15 @@ int pci_enable_msi(void *header, uint8_t vector, uint32_t processor, uint8_t edg return E_NOT_SUPPORT_MSI; // 写入message address - message_addr = pci_get_arch_msi_message_address(processor); // 获取message address + message_addr = pci_get_arch_msi_message_address(msi_desc->processor); // 获取message address pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0x4, (uint32_t)(message_addr & 0xffffffff)); if (message_control & (1 << 7)) // 64位 pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0x8, (uint32_t)((message_addr >> 32) & 0xffffffff)); // 写入message data - tmp = pci_get_arch_msi_message_data(vector, processor, edge_trigger, assert); + + tmp = pci_get_arch_msi_message_data(msi_desc->irq_num, msi_desc->processor, msi_desc->edge_trigger, msi_desc->assert); if (message_control & (1 << 7)) // 64位 pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0xc, tmp); else @@ -80,14 +81,14 @@ int pci_enable_msi(void *header, uint8_t vector, uint32_t processor, uint8_t edg return E_NOT_SUPPORT_MSI; // 写入message address - message_addr = pci_get_arch_msi_message_address(processor); // 获取message address + message_addr = pci_get_arch_msi_message_address(msi_desc->processor); // 获取message address pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0x4, (uint32_t)(message_addr & 0xffffffff)); if (message_control & (1 << 7)) // 64位 pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0x8, (uint32_t)((message_addr >> 32) & 0xffffffff)); // 写入message data - tmp = pci_get_arch_msi_message_data(vector, processor, edge_trigger, assert); + tmp = pci_get_arch_msi_message_data(msi_desc->irq_num, msi_desc->processor, msi_desc->edge_trigger, msi_desc->assert); if (message_control & (1 << 7)) // 64位 pci_write_config(ptr->bus, ptr->device, ptr->func, cap_ptr + 0xc, tmp); else diff --git a/kernel/driver/pci/msi.h b/kernel/driver/pci/msi.h index 4bef35e5..9e5291e1 100644 --- a/kernel/driver/pci/msi.h +++ b/kernel/driver/pci/msi.h @@ -1,19 +1,60 @@ #pragma once #include +/** + * @brief msi消息内容结构体 + * + */ +struct msi_msg_t +{ + uint32_t address_lo; + uint32_t address_hi; + uint32_t data; +}; +struct pci_msi_desc_t +{ + union + { + uint32_t msi_mask; // [PCI MSI] MSI cached mask bits + uint32_t msix_ctrl; // [PCI MSI-X] MSI-X cached per vector control bits + }; + + struct + { + uint8_t is_msix : 1; // [PCI MSI/X] True if MSI-X + uint8_t can_mask : 1; // [PCI MSI/X] Masking supported? + uint8_t is_64 : 1; // [PCI MSI/X] Address size: 0=32bit 1=64bit + } msi_attribute; +}; + +/** + * @brief msi描述符 + * + */ +struct msi_desc_t +{ + uint16_t irq_num; // 中断向量号 + uint16_t processor; // 定向投递的处理器 + uint16_t edge_trigger; // 是否边缘触发 + uint16_t assert; // 是否高电平触发 + struct pci_device_structure_header_t *pci_dev; // 对应的pci设备的结构体 + struct msi_msg_t msg; // msi消息 + uint16_t msi_index; // msi描述符的index + struct pci_msi_desc_t pci; // 与pci相关的msi描述符数据 +}; /** * @brief 启用 Message Signaled Interrupts - * + * * @param header 设备header * @param vector 中断向量号 * @param processor 要投递到的处理器 * @param edge_trigger 是否边缘触发 * @param assert 是否高电平触发 - * + * * @return 返回码 */ -int pci_enable_msi(void * header, uint8_t vector, uint32_t processor, uint8_t edge_trigger, uint8_t assert); +int pci_enable_msi(struct msi_desc_t * msi_desc); /** * @brief 禁用指定设备的msi diff --git a/kernel/driver/usb/xhci/xhci.c b/kernel/driver/usb/xhci/xhci.c index cfdc2948..5b465a16 100644 --- a/kernel/driver/usb/xhci/xhci.c +++ b/kernel/driver/usb/xhci/xhci.c @@ -557,8 +557,16 @@ uint64_t xhci_hc_irq_install(uint64_t irq_num, void *arg) return -EINVAL; struct xhci_hc_irq_install_info_t *info = (struct xhci_hc_irq_install_info_t *)arg; + struct msi_desc_t msi_desc; + memset(&msi_desc, 0, sizeof(struct msi_desc_t)); + + msi_desc.pci_dev = (struct pci_device_structure_header_t*)xhci_hc[cid].pci_dev_hdr; + msi_desc.assert = info->assert; + msi_desc.edge_trigger = info->edge_trigger; + msi_desc.processor = info->processor; + msi_desc.pci.msi_attribute.is_64 = 1; // todo: QEMU是使用msix的,因此要先在pci中实现msix - int retval = pci_enable_msi(xhci_hc[cid].pci_dev_hdr, irq_num, info->processor, info->edge_trigger, info->assert); + int retval = pci_enable_msi(&msi_desc); kdebug("pci retval = %d", retval); kdebug("xhci irq %d installed.", irq_num); return 0;