On Sat, Aug 11, 2007 at 09:42:55PM -0700, Don Lewis wrote: > On 11 Aug, Don Lewis wrote: > > On 11 Aug, To: bruce_at_cran.org.uk wrote: > >> On 12 Aug, bruce_at_cran.org.uk wrote: > > > >> Something that you might want to also print is the value of > >> EOREAD4(sc, EHCI_USBSTS) > >> immediately before the > >> EOWRITE4(sc, EHCI_USBCMD, EHCI_CMD_HCRESET); > >> call in ehci_hcreset(). Bit 12 of this register (EHCI_STS_HCH) should > >> be a zero before the write to do the reset is performed. > > > > Correction, this bit should be a one before doing the reset. > > > >> Maybe > >> ehci_hcreset() needs to wait for that to happen (as is done in > >> ehci_init()), rather than just waiting a fixed amount of time. > > > > I misread the code in ehci_init(), which is waiting for a transition in > > the opposite direction. I don't know why, because the EHCI spec says > > that the 1->0 transition is immediate. > > A revised version of the patch is below. The only change is the > addition of a second wait loop in ehci_hcreset(), which would be > necessary according the the EHCI spec if the controller could ever > require more than 1ms to stop. > > This patch might fix the problem on your machine if you are observing a > zero for bit 12 (EHCI_STS_HCH) of the EHCI_USBSTS register in > ehci_hcreset(). > > Index: sys/dev/usb/ehci.c > > > If this doesn't help, you could test the SMI hypothesis by disabling the > SMI on OS Ownership Enable bit before clearing the EHCI_LEGSUP_OSOWNED > bit. Something like the following should disable the SMI enable bit, > but I don't know what side effects it might have. It could even melt > your computer ;-) In any case, it's not a proper fix. > > static void > ehci_pci_givecontroller(device_t self) > { > ehci_softc_t *sc = device_get_softc(self); > u_int32_t cparams, eec, legsup; > int eecp; > > cparams = EREAD4(sc, EHCI_HCCPARAMS); > for (eecp = EHCI_HCC_EECP(cparams); eecp != 0; > eecp = EHCI_EECP_NEXT(eec)) { > eec = pci_read_config(self, eecp, 4); > if (EHCI_EECP_ID(eec) != EHCI_EC_LEGSUP) > continue; > /* NEW */ legsup = pci_read_config(self,eecp+EHCI_LEGSUP_USBLEGCTLSTS,4); > /* NEW */ legsup = legsup & ~0x200; > /* NEW */ pci_write_config(self, eecp+EHCI_LEGSUP_USBLEGCTLSTS, legsup,4); > legsup = eec; > pci_write_config(self, eecp, legsup & ~EHCI_LEGSUP_OSOWNED, 4); > } > } > > Thanks for your help. The revised patch doesn't change the behaviour; in ehci_pci_givecontroller, eec has the value 0x1000001 and the pci_read_config returns 0xC0002000. Disabling the SMI bit doesn't help either, but something I have noticed it that (both with and without the SMI disabling code) I get an 'f' printed on the console occasionally, which is probably from the printf I put in, "finished in ehci_pci_givecontroller": // code to disable SMI bit... DPRINTF(("pci_write_config in ehci_pci_givecontroller\n")); pci_write_config(...) // end for loop DPRINT(("finished in ehci_pci_givecontroller\n")); // end of ehci_pci_givecontroller function which suggests that something is causing the system to hang after the pci_write_config has finished. -- Bruce CranReceived on Sun Aug 12 2007 - 10:52:36 UTC
This archive was generated by hypermail 2.4.0 : Wed May 19 2021 - 11:39:16 UTC