Reboot on "shutdown -r" hangs after final "uptime ..."
string
bruce at cran.org.uk
bruce at cran.org.uk
Sun Aug 12 05:52:36 PDT 2007
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 Cran
More information about the freebsd-current
mailing list