Rev 9024 | Rev 9064 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 9024 | Rev 9037 | ||
---|---|---|---|
Line 20... | Line 20... | ||
20 | 20 | ||
21 | bit_AHCI_HBA_GHC_AHCI_ENABLE = 31 ; Enable AHCI mode |
21 | bit_AHCI_HBA_GHC_AHCI_ENABLE = 31 ; Enable AHCI mode |
22 | bit_AHCI_HBA_GHC_RESET = 0 ; Reset HBA |
22 | bit_AHCI_HBA_GHC_RESET = 0 ; Reset HBA |
Line -... | Line 23... | ||
- | 23 | bit_AHCI_HBA_GHC_INTERRUPT_ENABLE = 1 ; Enable interrupts from the HBA |
|
- | 24 | ||
- | 25 | AHCI_HBA_PxSSTS_DET = 0xF |
|
- | 26 | AHCI_HBA_PORT_IPM_ACTIVE = 1 |
|
23 | bit_AHCI_HBA_GHC_INTERRUPT_ENABLE = 1 ; Enable interrupts from the HBA |
27 | AHCI_HBA_PxSSTS_DET_PRESENT = 3 |
24 | 28 | ||
Line 25... | Line 29... | ||
25 | AHCI_MAX_PORTS = 32 ; |
29 | AHCI_MAX_PORTS = 32 ; |
26 | HBA_MEMORY_SIZE = 0x1100 |
- | |
27 | 30 | HBA_MEMORY_SIZE = 0x1100 |
|
28 | struct AHCI_DATA |
31 | |
29 | ;; |
32 | struct AHCI_DATA |
Line 30... | Line 33... | ||
30 | abar dd ? ; pointer to HBA Memory (BAR5) mapped to virtual kernelspace memory |
33 | abar dd ? ; pointer to HBA Memory (BAR5) mapped to virtual kernelspace memory |
Line 108... | Line 111... | ||
108 | movzx edx, byte [esi+PCIDEV.devfn] |
111 | movzx edx, byte [esi+PCIDEV.devfn] |
109 | and edx, 00000111b ; get only 3 lowest bits (function code) |
112 | and edx, 00000111b ; get only 3 lowest bits (function code) |
110 | DEBUGF 1, "K: found AHCI controller, (class, subcl, progif) = %x, bus = %x, device = %x, function = %x\n", eax, ebx, ecx, edx |
113 | DEBUGF 1, "K: found AHCI controller, (class, subcl, progif) = %x, bus = %x, device = %x, function = %x\n", eax, ebx, ecx, edx |
Line 111... | Line 114... | ||
111 | 114 | ||
112 | ; get BAR5 value, it is physical address |
115 | ; get BAR5 value, it is physical address |
113 | movzx eax, [esi + PCIDEV.bus] |
116 | movzx ebx, [esi + PCIDEV.bus] |
114 | movzx ebx, [esi + PCIDEV.devfn] |
117 | movzx ebp, [esi + PCIDEV.devfn] |
115 | stdcall pci_read32, eax, ebx, PCI_REG_BAR5 |
118 | stdcall pci_read32, ebx, ebp, PCI_REG_BAR5 |
- | 119 | DEBUGF 1, "K: AHCI controller MMIO = %x\n", eax |
|
- | 120 | mov edi, eax |
|
- | 121 | ||
- | 122 | ; get the size of MMIO region |
|
- | 123 | stdcall pci_write32, ebx, ebp, PCI_REG_BAR5, 0xFFFFFFFF |
|
- | 124 | stdcall pci_read32, ebx, ebp, PCI_REG_BAR5 |
|
- | 125 | not eax |
|
- | 126 | inc eax |
|
Line 116... | Line 127... | ||
116 | DEBUGF 1, "K: AHCI controller BAR5 = %x\n", eax |
127 | DEBUGF 1, "K: AHCI: MMIO region size = 0x%x bytes\n", eax |
117 | 128 | ||
118 | ; Map BAR5 to virtual memory |
129 | ; Map MMIO region to virtual memory |
119 | stdcall map_io_mem, eax, HBA_MEMORY_SIZE, PG_SWR + PG_NOCACHE |
130 | stdcall map_io_mem, edi, eax, PG_SWR + PG_NOCACHE |
Line -... | Line 131... | ||
- | 131 | mov [ahci_controller + AHCI_DATA.abar], eax |
|
- | 132 | DEBUGF 1, "K: AHCI controller BAR5 mapped to virtual addr %x\n", eax |
|
- | 133 | ||
120 | mov [ahci_controller + AHCI_DATA.abar], eax |
134 | ; Restore the original BAR5 value |
121 | DEBUGF 1, "K: AHCI controller BAR5 mapped to virtual addr %x\n", eax |
135 | stdcall pci_write32, ebx, ebp, PCI_REG_BAR5, edi |
122 | 136 | ||
123 | ; Enable dma bus mastering, memory space access, clear the "disable interrupts" bit |
137 | ; Enable dma bus mastering, memory space access, clear the "disable interrupts" bit |
124 | ; Usually, it is already done before us |
138 | ; Usually, it is already done before us |
Line 177... | Line 191... | ||
177 | bts [esi + HBA_MEM.global_host_control], bit_AHCI_HBA_GHC_AHCI_ENABLE |
191 | bts [esi + HBA_MEM.global_host_control], bit_AHCI_HBA_GHC_AHCI_ENABLE |
178 | bts [esi + HBA_MEM.global_host_control], bit_AHCI_HBA_GHC_INTERRUPT_ENABLE |
192 | bts [esi + HBA_MEM.global_host_control], bit_AHCI_HBA_GHC_INTERRUPT_ENABLE |
179 | mov ebx, 2 |
193 | mov ebx, 2 |
180 | call delay_hs |
194 | call delay_hs |
Line 181... | Line 195... | ||
181 | 195 | ||
- | 196 | DEBUGF 1, "K: AHCI: caps: %x %x, ver: %x, ghc: %x, pi: %x\n", [esi + HBA_MEM.capability], [esi + HBA_MEM.capability2], [esi + HBA_MEM.version], [esi + HBA_MEM.global_host_control], [esi + HBA_MEM.port_implemented] |
|
- | 197 | ||
- | 198 | ; TODO: |
|
- | 199 | ; calculate irq line |
|
- | 200 | ; ahciHBA->ghc |= AHCI_GHC_IE; |
|
- | 201 | ; IDT::RegisterInterruptHandler(irq, InterruptHandler); |
|
- | 202 | ; ahciHBA->is = 0xffffffff; |
|
- | 203 | ||
- | 204 | xor ebx, ebx |
|
- | 205 | .detect_drives: |
|
- | 206 | cmp ebx, AHCI_MAX_PORTS |
|
- | 207 | jae .end_detect_drives |
|
- | 208 | ||
- | 209 | ; if port with index ebx is not implemented then go to next |
|
- | 210 | mov ecx, [esi + HBA_MEM.port_implemented] |
|
- | 211 | bt ecx, ebx |
|
- | 212 | jnc .continue_detect_drives |
|
- | 213 | ||
- | 214 | mov edi, ebx |
|
- | 215 | shl edi, BSF sizeof.HBA_PORT |
|
- | 216 | add edi, HBA_MEM.ports |
|
- | 217 | add edi, esi |
|
- | 218 | ; now edi - base of HBA_MEM.ports[ebx] |
|
- | 219 | ||
- | 220 | DEBUGF 1, "K: AHCI: port %d, ssts = %x\n", ebx, [edi + HBA_PORT.sata_status] |
|
- | 221 | ||
- | 222 | mov ecx, [edi + HBA_PORT.sata_status] |
|
- | 223 | shr ecx, 8 |
|
- | 224 | and ecx, 0x0F |
|
- | 225 | cmp ecx, AHCI_HBA_PORT_IPM_ACTIVE |
|
- | 226 | jne .continue_detect_drives |
|
- | 227 | ||
- | 228 | mov ecx, [edi + HBA_PORT.sata_status] |
|
- | 229 | and ecx, AHCI_HBA_PxSSTS_DET |
|
- | 230 | cmp ecx, AHCI_HBA_PxSSTS_DET_PRESENT |
|
- | 231 | jne .continue_detect_drives |
|
- | 232 | ||
- | 233 | DEBUGF 1, "K: AHCI: found drive at port %d, signature = %x\n", ebx, [edi + HBA_PORT.signature] |
|
- | 234 | ||
- | 235 | .continue_detect_drives: |
|
- | 236 | inc ebx |
|
- | 237 | jmp .detect_drives |
|
- | 238 | ||
- | 239 | ; TODO: why signatures of found disks are 0xFFFFFFFF ? |
|
- | 240 | ||
- | 241 | .end_detect_drives: |
|
Line 182... | Line 242... | ||
182 | DEBUGF 1, "K: AHCI: caps: %x %x, ver: %x, ghc: %x\n", [esi + HBA_MEM.capability], [esi + HBA_MEM.capability2], [esi + HBA_MEM.version], [esi + HBA_MEM.global_host_control] |
242 |