55 lines
1.7 KiB
C
55 lines
1.7 KiB
C
#include <stdint.h>
|
|
#include <stddef.h>
|
|
#include "pci/pci.h"
|
|
#include "storedev/storedev.h"
|
|
#include "storedev/atasd.h"
|
|
#include "kprintf.h"
|
|
|
|
#define ATA_PROBE(STRING, IOBASE, CTRLBASE, S_OR_M) \
|
|
ps = ata_probesize_bytes((IOBASE), (CTRLBASE), (S_OR_M)); \
|
|
if (ps > 0) { \
|
|
AtaSdInitExtra extra = { \
|
|
.devno = (S_OR_M), \
|
|
.capacity = ps, \
|
|
.iobase = (IOBASE), \
|
|
.ctrlbase = (CTRLBASE), \
|
|
}; \
|
|
storedev_create(STOREDEV_ATASD, (STRING), (void *)&extra); \
|
|
}
|
|
|
|
#define ATA_MASTER 0x00
|
|
#define ATA_SLAVE 0x01
|
|
|
|
#define ATA_PRIM_IO 0x1F0
|
|
#define ATA_PRIM_CTRL 0x3F6
|
|
#define ATA_SCND_IO 0x170
|
|
#define ATA_SCND_CTRL 0x376
|
|
|
|
void pci_ata_init(void) {
|
|
PciDev dev = pci_getdev(0x8086, 0x7010, -1);
|
|
|
|
uint16_t iobase, ctrlbase;
|
|
uint64_t ps;
|
|
|
|
uint32_t bar0 = pci_read(dev, PCI_BAR0);
|
|
uint32_t bar1 = pci_read(dev, PCI_BAR1);
|
|
uint32_t bar2 = pci_read(dev, PCI_BAR2);
|
|
uint32_t bar3 = pci_read(dev, PCI_BAR3);
|
|
|
|
LOG("pci", "ATA bar0=0x%x, bar1=0x%x, bar2=0x%x, bar3=0x%x\n", bar0, bar1, bar2, bar3);
|
|
|
|
iobase = (bar0 & 0xFFFFFFFC) + ATA_PRIM_IO * (!bar0);
|
|
ctrlbase = (bar1 & 0xFFFFFFFC) + ATA_PRIM_CTRL * (!bar1);
|
|
LOG("pci", "ATA CHANNEL PRIM: iobase=0x%x, ctrlbase=0x%x\n", iobase, ctrlbase);
|
|
if (!bar0 || !bar1) LOG("pci", "falling back to ISA\n");
|
|
ATA_PROBE("atasd0m", iobase, ctrlbase, ATA_MASTER);
|
|
ATA_PROBE("atasd0s", iobase, ctrlbase, ATA_SLAVE);
|
|
|
|
iobase = (bar2 & 0xFFFFFFFC) + ATA_SCND_IO * (!bar2);
|
|
ctrlbase = (bar3 & 0xFFFFFFFC) + ATA_SCND_CTRL * (!bar3);
|
|
LOG("pci", "ATA CHANNEL SCND: iobase=0x%x, ctrlbase=0x%x\n", iobase, ctrlbase);
|
|
if (!bar2 || !bar3) LOG("pci", "falling back to ISA\n");
|
|
ATA_PROBE("atasd1m", iobase, ctrlbase, ATA_MASTER);
|
|
ATA_PROBE("atasd2s", iobase, ctrlbase, ATA_SLAVE);
|
|
}
|