From ca5ccaa86b5a3d1ea16c0677641534f4e1020634 Mon Sep 17 00:00:00 2001 From: Abdur-Rahman Mansoor Date: Thu, 20 Jun 2024 18:14:28 -0400 Subject: [PATCH] refactor(nvme_init): use separately allocated queue pointers instead of using `dptr` --- drivers/nvme/nvme.asm | 42 +++++++++++++++++++++++++----------------- 1 file changed, 25 insertions(+), 17 deletions(-) diff --git a/drivers/nvme/nvme.asm b/drivers/nvme/nvme.asm index 2aea64d..1c331b2 100644 --- a/drivers/nvme/nvme.asm +++ b/drivers/nvme/nvme.asm @@ -511,7 +511,7 @@ proc nvme_init stdcall, pci:dword ; we want to disable all interrupts for now, since the controller randomly ; generates interrupts while starting up - mov dword [edi + NVME_MMIO.INTMS], 0xffffffff + ;mov dword [edi + NVME_MMIO.INTMS], 0xffffffff ; Attach interrupt handler movzx eax, byte [esi + pcidev.iline] @@ -523,45 +523,45 @@ proc nvme_init stdcall, pci:dword ; Restart the controller stdcall nvme_controller_start, edi - mov dword [edi + NVME_MMIO.INTMC], 0xffffffff ; re-enable interrupts + ;mov dword [edi + NVME_MMIO.INTMC], 0xffffffff ; re-enable interrupts invoke KernelAlloc, 0x1000 test eax, eax jz .exit_fail - mov dword [dptr], eax + mov ebx, eax invoke GetPhysAddr ; pci:dword, nsid:dword, dptr:dword, cns:byte stdcall nvme_identify, [pci], 0, eax, CNS_IDCS stdcall nvme_cmd_wait, [pci], 0, 0 - mov edx, dword [dptr] - lea edx, byte [edx + IDENTC.sn] + mov edi, ebx + lea ebx, byte [edi + IDENTC.sn] lea eax, byte [esi + pcidev.serial] - stdcall memcpy, eax, edx, 20 + stdcall memcpy, eax, ebx, 20 DEBUGF DBG_INFO, "(NVMe) Serial Number: %s\n", eax - add edx, 20 + add ebx, 20 lea eax, byte [esi + pcidev.model] - stdcall memcpy, eax, edx, 40 + stdcall memcpy, eax, ebx, 40 DEBUGF DBG_INFO, "(NVMe) Model: %s\n", eax - mov ebx, dword [esi + pcidev.version] - mov esi, dword [dptr] + mov edx, dword [esi + pcidev.version] - cmp ebx, VS140 + cmp edx, VS140 jl @f ; This is a reserved field in pre-1.4 controllers - mov al, byte [esi + IDENTC.cntrltype] + mov al, byte [edi + IDENTC.cntrltype] cmp al, CNTRLTYPE_IO_CONTROLLER jne .exit_fail DEBUGF DBG_INFO, "(NVMe) I/O controller detected...\n" @@: - mov al, byte [esi + IDENTC.sqes] + mov al, byte [edi + IDENTC.sqes] and al, 11110000b cmp al, 0x60 ; maximum submission queue size should at least be 64 bytes jl .exit_fail - mov al, byte [esi + IDENTC.cqes] + mov al, byte [edi + IDENTC.cqes] and al, 11110000b and al, 0x40 ; maximum completion queue entry size should at least be 16 bytes jl .exit_fail + invoke KernelFree, edi mov eax, (NVM_ASQS - 1) or ((NVM_ACQS - 1) shl 16) ; CDW11 (set the number of queues we want) stdcall set_features, [pci], NULLPTR, FID_NUMBER_OF_QUEUES, eax @@ -578,10 +578,19 @@ proc nvme_init stdcall, pci:dword jnz .exit_fail ; Create I/O Queues - mov eax, dword [dptr] + mov esi, [pci] + mov esi, dword [esi + pcidev.queue_entries] + lea esi, [esi + sizeof.NVM_QUEUE_ENTRY] + invoke KernelAlloc, 0x1000 + test eax, eax + jz .exit_fail + mov dword [esi + NVM_QUEUE_ENTRY.cq_ptr], eax invoke GetPhysAddr stdcall create_io_completion_queue, [pci], eax, 1, IEN_ON - mov eax, dword [dptr] + invoke KernelAlloc, 0x1000 + test eax, eax + jz .exit_fail + mov dword [esi + NVM_QUEUE_ENTRY.sq_ptr], eax invoke GetPhysAddr stdcall create_io_submission_queue, [pci], eax, 1, 1 @@ -880,7 +889,6 @@ endp align 4 p_nvme_devices dd 0 pcidevs_len dd 0 - dptr dd ? my_service db "NVMe",0 ;max 16 chars include zero if __DEBUG__ include_debug_strings