#define AU_FL_APP_ND 0x005BFFFF
#define AU_FL_DISK_ST 0x005C0000
#define AU_FL_DISK_ND 0x00FFFFFF
-#else /* 8 MB Flash, 16 MB RAM */
+#else /* 8 MB Flash, 32 MB RAM */
#define AU_FL_FIRMWARE_ST 0x00000000
-#define AU_FL_FIRMWARE_ND 0x0003FFFF
-#define AU_FL_KERNEL_ST 0x00040000
-#define AU_FL_KERNEL_ND 0x0011FFFF
-#define AU_FL_APP_ST 0x00120000
-#define AU_FL_APP_ND 0x003FFFFF
-#define AU_FL_DISK_ST 0x00400000
+#define AU_FL_FIRMWARE_ND 0x0005FFFF
+#define AU_FL_KERNEL_ST 0x00060000
+#define AU_FL_KERNEL_ND 0x0013FFFF
+#define AU_FL_APP_ST 0x00140000
+#define AU_FL_APP_ND 0x0067FFFF
+#define AU_FL_DISK_ST 0x00680000
#define AU_FL_DISK_ND 0x007DFFFF
#define AU_FL_VFD_ST 0x007E0000
#define AU_FL_VFD_ND 0x007FFFFF
#define LOAD_ADDR ((unsigned char *)0x0C100100)
/* where to build strings in memory - 256 bytes should be enough */
#define STRING_ADDR ((char *)0x0C100000)
-/* the disk is the largest image */
-#define MAX_LOADSZ ausize[IDX_DISK]
+/* the app is the largest image */
+#define MAX_LOADSZ ausize[IDX_APP]
/* externals */
extern int fat_register_device(block_dev_desc_t *, int);
#endif
if (ntohl(hdr->ih_magic) != IH_MAGIC ||
hdr->ih_arch != IH_CPU_ARM ||
- nbytes < ntohl(hdr->ih_size))
+ nbytes != (sizeof(*hdr) + ntohl(hdr->ih_size)))
{
printf ("Image %s bad MAGIC or ARCH or SIZE\n", aufile[idx]);
return -1;
*/
if (got_ctrlc == 0)
au_update_eeprom(i);
+ else
+ /* enable the power switch */
+ *CPLD_VFD_BK &= ~POWER_OFF;
}
usb_stop();
/* restore the old state */
#define OHCI_CONTROL_INIT \
(OHCI_CTRL_CBSR & 0x3) | OHCI_CTRL_IE | OHCI_CTRL_PLE
-#define OHCI_UNLINK_TIMEOUT (CFG_HZ / 10)
-
#define readl(a) (*((vu_long *)(a)))
#define writel(a, b) (*((vu_long *)(b)) = ((vu_long)a))
struct ohci_device ohci_dev;
/* urb_priv */
urb_priv_t urb_priv;
+/* RHSC flag */
+int got_rhsc;
+/* device which was disconnected */
+struct usb_device *devgone;
/*-------------------------------------------------------------------------*/
/* request to virtual root hub */
-static int ohci_submit_rh_msg(struct usb_device *dev, unsigned long pipe, void *buffer,
- int transfer_len, struct devrequest *cmd)
+int rh_check_port_status(ohci_t *controller)
+{
+ __u32 temp, ndp, i;
+ int res;
+
+ res = -1;
+ temp = roothub_a (controller);
+ ndp = (temp & RH_A_NDP);
+ for (i = 0; i < ndp; i++) {
+ temp = roothub_portstatus (controller, i);
+ /* check for a device disconnect */
+ if (((temp & (RH_PS_PESC | RH_PS_CSC)) ==
+ (RH_PS_PESC | RH_PS_CSC)) &&
+ ((temp & RH_PS_CCS) == 0)) {
+ res = i;
+ break;
+ }
+ }
+ return res;
+}
+
+static int ohci_submit_rh_msg(struct usb_device *dev, unsigned long pipe,
+ void *buffer, int transfer_len, struct devrequest *cmd)
{
void * data = buffer;
int leni = transfer_len;
int maxsize = usb_maxpacket(dev, pipe);
int timeout;
+ /* device pulled? Shortcut the action. */
+ if (devgone == dev) {
+ dev->status = USB_ST_CRC_ERR;
+ return 0;
+ }
+
#ifdef DEBUG
urb_priv.actual_length = 0;
pkt_print(dev, pipe, buffer, transfer_len, setup, "SUB", usb_pipein(pipe));
/* check whether the controller is done */
stat = hc_interrupt();
if (stat < 0) {
- stat = 1;
+ stat = USB_ST_CRC_ERR;
break;
}
if (stat >= 0 && stat != 0xff) {
if (--timeout) {
wait_ms(1);
} else {
- err("CTL:TIMEOUT");
- stat = 1;
+ err("CTL:TIMEOUT ");
+ stat = USB_ST_CRC_ERR;
break;
}
}
+ /* we got an Root Hub Status Change interrupt */
+ if (got_rhsc) {
+#ifdef DEBUG
+ ohci_dump_roothub (&gohci, 1);
+#endif
+ got_rhsc = 0;
+ /* abuse timeout */
+ timeout = rh_check_port_status(&gohci);
+ if (timeout >= 0) {
+#if 0 /* this does nothing useful, but leave it here in case that changes */
+ /* the called routine adds 1 to the passed value */
+ usb_hub_port_connect_change(gohci.rh.dev, timeout - 1);
+#endif
+ /*
+ * XXX
+ * This is potentially dangerous because it assumes
+ * that only one device is ever plugged in!
+ */
+ devgone = dev;
+ }
+ }
+
dev->status = stat;
dev->act_len = transfer_len;
pipe);
return -1;
}
- if (((pipe >> 8) & 0x7f) == gohci.rh.devnum)
+ if (((pipe >> 8) & 0x7f) == gohci.rh.devnum) {
+ gohci.rh.dev = dev;
/* root hub - redirect */
return ohci_submit_rh_msg(dev, pipe, buffer, transfer_len,
setup);
+ }
return submit_common_msg(dev, pipe, buffer, transfer_len, setup, 0);
}
ohci->disabled = 0;
writel (ohci->hc_control, &ohci->regs->control);
- /* Choose the interrupts we care about now, others later on demand */
- mask = OHCI_INTR_MIE | OHCI_INTR_UE | OHCI_INTR_WDH | OHCI_INTR_SO;
+ /* disable all interrupts */
+ mask = (OHCI_INTR_SO | OHCI_INTR_WDH | OHCI_INTR_SF | OHCI_INTR_RD |
+ OHCI_INTR_UE | OHCI_INTR_FNO | OHCI_INTR_RHSC |
+ OHCI_INTR_OC | OHCI_INTR_MIE);
+ writel (mask, &ohci->regs->intrdisable);
+ /* clear all interrupts */
+ mask &= ~OHCI_INTR_MIE;
writel (mask, &ohci->regs->intrstatus);
+ /* Choose the interrupts we care about now - but w/o MIE */
+ mask = OHCI_INTR_RHSC | OHCI_INTR_UE | OHCI_INTR_WDH | OHCI_INTR_SO;
+ writel (mask, &ohci->regs->intrenable);
#ifdef OHCI_USE_NPS
/* required for AMD-756 and some Mac platforms */
/* dbg("Interrupt: %x frame: %x", ints, le16_to_cpu (ohci->hcca->frame_no)); */
+ if (ints & OHCI_INTR_RHSC) {
+ got_rhsc = 1;
+ }
+
if (ints & OHCI_INTR_UE) {
ohci->disabled++;
err ("OHCI Unrecoverable Error, controller usb-%s disabled",