PERFORCE change 180435 for review
Volodymyr Serbinenko
phcoder at FreeBSD.org
Sat Jul 3 14:38:36 UTC 2010
http://p4web.freebsd.org/@@180435?ac=10
Change 180435 by phcoder at phcoder_ on 2010/07/03 14:38:03
Fix several bonito bugs. Now OHCI seems to work correctly.
Affected files ...
.. //depot/projects/soc2010/phcoder_yeeloong/src/sys/cam/cam_xpt.c#3 edit
.. //depot/projects/soc2010/phcoder_yeeloong/src/sys/mips/yeeloong/bonito_pci.c#2 edit
Differences ...
==== //depot/projects/soc2010/phcoder_yeeloong/src/sys/cam/cam_xpt.c#3 (text+ko) ====
@@ -806,6 +806,9 @@
return 0;
}
+static struct root_hold_token *xpt_rool_hold = NULL;
+static int rescan_counter = 0;
+
static void
xpt_rescan_done(struct cam_periph *periph, union ccb *done_ccb)
{
@@ -818,6 +821,11 @@
(*done_ccb->ccb_h.cbfcnp)(periph, done_ccb);
}
xpt_release_boot();
+ if (atomic_fetchadd_int (&rescan_counter, -1) == 1)
+ {
+ root_mount_rel (xpt_rool_hold);
+ xpt_rool_hold = NULL;
+ }
}
/* thread to handle bus rescans */
@@ -851,6 +859,11 @@
{
struct ccb_hdr *hdr;
+ if (atomic_fetchadd_int (&rescan_counter, 1) == 0)
+ {
+ xpt_rool_hold = root_mount_hold("XPT bus rescan");
+ }
+
/* Prepare request */
if (ccb->ccb_h.path->target->target_id == CAM_TARGET_WILDCARD &&
ccb->ccb_h.path->device->lun_id == CAM_LUN_WILDCARD)
==== //depot/projects/soc2010/phcoder_yeeloong/src/sys/mips/yeeloong/bonito_pci.c#2 (text+ko) ====
@@ -42,6 +42,8 @@
#include <sys/kernel.h>
#include <sys/module.h>
#include <sys/rman.h>
+#include <sys/lock.h>
+#include <sys/mutex.h>
#include <vm/vm.h>
#include <vm/pmap.h>
@@ -69,6 +71,7 @@
struct rman sc_mem;
struct intr_event *intr_events[BONITO_NUM_INTS];
void *intr_cookie;
+ struct mtx config_mtx;
};
#define PCI_CONF_CTRL_REG (*(volatile uint32_t *)(intptr_t)(int32_t)0xbfe00118)
@@ -79,7 +82,12 @@
#define PCI_INTEN_REG (*(volatile uint32_t *)(intptr_t)(int32_t)0xbfe00138)
#define PCI_INTISR_REG (*(volatile uint32_t *)(intptr_t)(int32_t)0xbfe0013c)
#define PCI_CONFSPACE 0xbfe80000
-#define PCI_INT0 4
+#define PCI_INTA 4
+#define PCI_INTB 5
+#define PCI_INTC 6
+#define PCI_INTD 7
+#define HANDLED_INTERRUPTS 0xf0
+
#define BONITO_IRQ 4
static void
@@ -101,27 +109,16 @@
bonito_intr(void *sc_in)
{
struct intr_event *event;
- int i, intr;
+ int i;
struct bonito_softc *sc = sc_in;
- printf ("pre: intisr=%x inten=%x\n", PCI_INTISR_REG, PCI_INTEN_REG);
-
- /*
- * Do not handle masked interrupts. They were masked by
- * pre_ithread function (mips_mask_XXX_intr) and will be
- * unmasked once ithread is through with handler
- */
- intr = PCI_INTISR_REG & PCI_INTEN_REG;
- while ((i = fls(intr)) != 0) {
+ while ((i = fls(PCI_INTISR_REG & PCI_INTEN_REG & HANDLED_INTERRUPTS))
+ != 0) {
i--; /* Get a 0-offset interrupt. */
- intr &= ~(1 << i);
PCI_INTENCLR_REG = (1 << i);
PCI_INTENSET_REG = (1 << i);
event = sc->intr_events[i];
- printf ("Handling Bonito int %d isr=%x en=%x\n", i, PCI_INTISR_REG,
- PCI_INTEN_REG);
-
if (!event || TAILQ_EMPTY(&event->ie_handlers)) {
printf("stray bonito interrupt %d\n", i);
continue;
@@ -131,10 +128,6 @@
printf("stray bonito interrupt %d\n", i);
}
}
-
- printf ("intisr=%x inten=%x\n", PCI_INTISR_REG, PCI_INTEN_REG);
-
- KASSERT(i == 0, ("all interrupts handled"));
}
static int
@@ -145,6 +138,9 @@
sc = device_get_softc(dev);
+ mtx_init(&sc->config_mtx, "bonito_cfg",
+ "Bonito configuration space mutex", MTX_SPIN | MTX_QUIET);
+
sc->sc_irq.rm_type = RMAN_ARRAY;
sc->sc_irq.rm_descr = "Bonito PCI IRQs";
error = rman_init(&sc->sc_irq);
@@ -214,21 +210,32 @@
int bytes)
{
intptr_t addr;
+ uint32_t ret;
+ struct bonito_softc *sc;
- PCI_CONF_CTRL_REG = (1 << slot);
+ sc = device_get_softc(dev);
addr = (int32_t) (PCI_CONFSPACE | (func << 8) | (reg & ~(bytes - 1)));
+ mtx_lock_spin(&sc->config_mtx);
+ PCI_CONF_CTRL_REG = (1 << slot);
+
switch (bytes) {
case 4:
- return *((volatile uint32_t *) addr);
+ ret = *((volatile uint32_t *) addr);
+ break;
case 2:
- return *((volatile uint16_t *) addr);
+ ret = *((volatile uint16_t *) addr);
+ break;
case 1:
- return *((volatile uint8_t *) addr);
+ ret = *((volatile uint8_t *) addr);
+ break;
default:
- return ((uint32_t)-1);
+ ret = ((uint32_t)-1);
+ break;
}
+ mtx_unlock_spin(&sc->config_mtx);
+ return ret;
}
static void
@@ -236,24 +243,30 @@
u_int reg, uint32_t data, int bytes)
{
intptr_t addr;
+ struct bonito_softc *sc;
- PCI_CONF_CTRL_REG = (1 << slot);
+ sc = device_get_softc(dev);
addr = (int32_t) (PCI_CONFSPACE | (func << 8) | (reg & ~(bytes - 1)));
+ mtx_lock_spin(&sc->config_mtx);
+
+ PCI_CONF_CTRL_REG = (1 << slot);
+
switch (bytes) {
case 4:
*((volatile uint32_t *) addr) = data;
- return;
+ break;
case 2:
*((volatile uint16_t *) addr) = data;
- return;
+ break;
case 1:
*((volatile uint8_t *) addr) = data;
- return;
+ break;
default:
- return;
+ break;
}
+ mtx_unlock_spin(&sc->config_mtx);
}
static struct resource *
@@ -352,9 +365,7 @@
{
uintptr_t irq = (uintptr_t)source;
- printf ("Previous inten is %x\n", PCI_INTEN_REG);
PCI_INTENSET_REG = (1 << irq);
- printf ("Current inten is %x\n", PCI_INTEN_REG);
}
static int
@@ -376,7 +387,6 @@
if (irq < 0 || irq >= BONITO_NUM_INTS)
return ENXIO;
-// irq += PCI_INT0;
event = sc->intr_events[irq];
if (event == NULL) {
error = intr_event_create(&event, (void *)(uintptr_t) irq, 0,
@@ -410,7 +420,6 @@
if (irq < 0 || irq >= BONITO_NUM_INTS)
return (ENXIO);
- //irq += PCI_INT0;
event = sc->intr_events[irq];
intr_event_remove_handler(cookie);
@@ -423,7 +432,14 @@
static int
bonito_route_interrupt(device_t bus, device_t child, int pin)
{
- return pin + PCI_INT0 - 1;
+ /* Some strange Yeeloong routing? */
+ switch (pci_get_slot (child))
+ {
+ case 4:
+ return PCI_INTD;
+ default:
+ return pin + PCI_INTA - 1;
+ }
}
More information about the p4-projects
mailing list