diff options
Diffstat (limited to 'sys/arch')
-rw-r--r-- | sys/arch/armish/stand/boot/machdep.c | 52 | ||||
-rw-r--r-- | sys/arch/armish/stand/boot/pciide.c | 10 | ||||
-rw-r--r-- | sys/arch/armish/stand/boot/wd.c | 3 |
3 files changed, 59 insertions, 6 deletions
diff --git a/sys/arch/armish/stand/boot/machdep.c b/sys/arch/armish/stand/boot/machdep.c index dbd33e526ad..eca4ec3fea5 100644 --- a/sys/arch/armish/stand/boot/machdep.c +++ b/sys/arch/armish/stand/boot/machdep.c @@ -1,4 +1,4 @@ -/* $OpenBSD: machdep.c,v 1.2 2006/07/29 16:08:20 kettenis Exp $ */ +/* $OpenBSD: machdep.c,v 1.3 2006/07/30 20:46:30 drahn Exp $ */ /* * Copyright (c) 2006 Mark Kettenis @@ -18,6 +18,7 @@ #include <sys/types.h> #include <arm/pte.h> +#include <dev/pci/pcireg.h> #include "libsa.h" @@ -26,6 +27,8 @@ #define ATU_OIOWTVR 0xffffe15c #define ATU_ATUCR 0xffffe180 #define ATU_PCSR 0xffffe184 +#define ATU_OCCAR 0xffffe1a4 +#define ATU_OCCDR 0xffffe1ac #define ATUCR_OUT_EN (1U << 1) @@ -56,6 +59,53 @@ machdep(void) __asm volatile ("mcr p6, 0, %0, c1, c1, 0" :: "r" (0x00000032)); cninit(); + +{ + /* + * this code does a device probe on pci space, + * It looks for a wd compatible controller. + * however when it reads the device register, it does + * not check if a bus fault occurs on the access. + * Since the bootloader doesn't handle faults, this + * crashes the bootloader if it reads a non-existant + * device. + * The tag computation comes from arm/xscale/i80321_pci.c + * i80321_pci_conf_setup() + */ + int device, bar; + for (device = 1; device < 4; device++) { + u_int32_t tag, result, size; + volatile u_int32_t *occar = (u_int32_t *)ATU_OCCAR; + volatile u_int32_t *occdr = (u_int32_t *)ATU_OCCDR; + + tag = 1 << (device + 16) | (device << 11); + *occar = tag; + result = *occdr; + if (result == ~0) + continue; + *occar = tag | PCI_CLASS_REG; + result = *occdr; + + if (PCI_CLASS(result) != PCI_CLASS_MASS_STORAGE) + continue; + if (PCI_SUBCLASS(result) != PCI_SUBCLASS_MASS_STORAGE_ATA && + PCI_SUBCLASS(result) != PCI_SUBCLASS_MASS_STORAGE_SATA && + PCI_SUBCLASS(result) != PCI_SUBCLASS_MASS_STORAGE_MISC) + continue; + + *occar = tag | PCI_MAPREG_START; + result = *occdr; + + /* verify result is an IO BAR */ + if (PCI_MAPREG_TYPE(result) == PCI_MAPREG_TYPE_IO) { + extern u_int32_t wdc_base_addr; + wdc_base_addr = PCI_MAPREG_MEM_ADDR(result); + DPRINTF(("setting wdc_base addr to %x\n", + wdc_base_addr)); + } + } +} + } int diff --git a/sys/arch/armish/stand/boot/pciide.c b/sys/arch/armish/stand/boot/pciide.c index f27f173e982..e4cef71102a 100644 --- a/sys/arch/armish/stand/boot/pciide.c +++ b/sys/arch/armish/stand/boot/pciide.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pciide.c,v 1.2 2006/07/29 15:01:49 kettenis Exp $ */ +/* $OpenBSD: pciide.c,v 1.3 2006/07/30 20:46:30 drahn Exp $ */ /* $NetBSD: pciide.c,v 1.5 2005/12/11 12:17:06 christos Exp $ */ /*- @@ -39,6 +39,8 @@ #include "libsa.h" #include "wdvar.h" +u_int32_t wdc_base_addr = 0; + int pciide_init(struct wdc_channel *chp, u_int chan) { @@ -48,7 +50,7 @@ pciide_init(struct wdc_channel *chp, u_int chan) /* * two channels per chip, one drive per channel */ - if (chan >= PCIIDE_NUM_CHANNELS) + if (chan >= PCIIDE_NUM_CHANNELS || wdc_base_addr == 0) return (ENXIO); chp->ndrives = 1; @@ -57,8 +59,8 @@ pciide_init(struct wdc_channel *chp, u_int chan) /* * XXX map? */ - cmdreg = 0x90000200 + chan * 0x10; - ctlreg = 0x90000208 + chan * 0x10; + cmdreg = wdc_base_addr + chan * 0x10; + ctlreg = wdc_base_addr+0x8 + chan * 0x10; /* set up cmd regsiters */ chp->c_cmdbase = (u_int8_t *)cmdreg; diff --git a/sys/arch/armish/stand/boot/wd.c b/sys/arch/armish/stand/boot/wd.c index 7fc9fceac41..662a246edb8 100644 --- a/sys/arch/armish/stand/boot/wd.c +++ b/sys/arch/armish/stand/boot/wd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: wd.c,v 1.2 2006/07/29 15:01:49 kettenis Exp $ */ +/* $OpenBSD: wd.c,v 1.3 2006/07/30 20:46:30 drahn Exp $ */ /* $NetBSD: wd.c,v 1.5 2005/12/11 12:17:06 christos Exp $ */ /*- @@ -72,6 +72,7 @@ wdprobe(void) DPRINTF(("wd%d: channel %d drive %d\n", unit, chan, drive)); unit++; + wd++; } } |