In various archs, Processor memory address may not be same with Pci memory address. For usb host controller, we should use pci memory address to initialize framelist register and all address field in QH/TD.

git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@9259 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
eric_tian 2009-09-14 05:26:09 +00:00
parent ef12a160de
commit 3af875e220
7 changed files with 195 additions and 71 deletions

View File

@ -707,7 +707,9 @@ Uhci2ControlTransfer (
Uhc, Uhc,
DeviceAddress, DeviceAddress,
PktId, PktId,
(UINT8*)Request,
RequestPhy, RequestPhy,
(UINT8*)Data,
DataPhy, DataPhy,
TransferDataLength, TransferDataLength,
(UINT8) MaximumPacketLength, (UINT8) MaximumPacketLength,
@ -724,7 +726,7 @@ Uhci2ControlTransfer (
// the TD to corrosponding queue head, then check // the TD to corrosponding queue head, then check
// the execution result // the execution result
// //
UhciLinkTdToQh (Uhc->CtrlQh, TDs); UhciLinkTdToQh (Uhc, Uhc->CtrlQh, TDs);
Status = UhciExecuteTransfer (Uhc, Uhc->CtrlQh, TDs, TimeOut, IsSlowDevice, &QhResult); Status = UhciExecuteTransfer (Uhc, Uhc->CtrlQh, TDs, TimeOut, IsSlowDevice, &QhResult);
UhciUnlinkTdFromQh (Uhc->CtrlQh, TDs); UhciUnlinkTdFromQh (Uhc->CtrlQh, TDs);
@ -858,6 +860,7 @@ Uhci2BulkTransfer (
DeviceAddress, DeviceAddress,
EndPointAddress, EndPointAddress,
PktId, PktId,
(UINT8 *)*Data,
DataPhy, DataPhy,
*DataLength, *DataLength,
DataToggle, DataToggle,
@ -878,7 +881,7 @@ Uhci2BulkTransfer (
// //
BulkQh = Uhc->BulkQh; BulkQh = Uhc->BulkQh;
UhciLinkTdToQh (BulkQh, TDs); UhciLinkTdToQh (Uhc, BulkQh, TDs);
Status = UhciExecuteTransfer (Uhc, BulkQh, TDs, TimeOut, FALSE, &QhResult); Status = UhciExecuteTransfer (Uhc, BulkQh, TDs, TimeOut, FALSE, &QhResult);
UhciUnlinkTdFromQh (BulkQh, TDs); UhciUnlinkTdFromQh (BulkQh, TDs);
@ -1036,6 +1039,7 @@ Uhci2AsyncInterruptTransfer (
DeviceAddress, DeviceAddress,
EndPointAddress, EndPointAddress,
PktId, PktId,
DataPtr,
DataPhy, DataPhy,
DataLength, DataLength,
DataToggle, DataToggle,
@ -1048,7 +1052,7 @@ Uhci2AsyncInterruptTransfer (
goto DESTORY_QH; goto DESTORY_QH;
} }
UhciLinkTdToQh (Qh, IntTds); UhciLinkTdToQh (Uhc, Qh, IntTds);
// //
// Save QH-TD structures to async Interrupt transfer list, // Save QH-TD structures to async Interrupt transfer list,
@ -1073,7 +1077,7 @@ Uhci2AsyncInterruptTransfer (
goto DESTORY_QH; goto DESTORY_QH;
} }
UhciLinkQhToFrameList (Uhc->FrameBase, Qh); UhciLinkQhToFrameList (Uhc, Qh);
gBS->RestoreTPL (OldTpl); gBS->RestoreTPL (OldTpl);
return EFI_SUCCESS; return EFI_SUCCESS;
@ -1209,6 +1213,7 @@ Uhci2SyncInterruptTransfer (
DeviceAddress, DeviceAddress,
EndPointAddress, EndPointAddress,
PktId, PktId,
(UINT8 *)Data,
DataPhy, DataPhy,
*DataLength, *DataLength,
DataToggle, DataToggle,
@ -1224,7 +1229,7 @@ Uhci2SyncInterruptTransfer (
} }
UhciLinkTdToQh (Uhc->SyncIntQh, TDs); UhciLinkTdToQh (Uhc, Uhc->SyncIntQh, TDs);
Status = UhciExecuteTransfer (Uhc, Uhc->SyncIntQh, TDs, TimeOut, IsSlowDevice, &QhResult); Status = UhciExecuteTransfer (Uhc, Uhc->SyncIntQh, TDs, TimeOut, IsSlowDevice, &QhResult);

View File

@ -117,6 +117,7 @@ struct _USB_HC_DEV {
// Schedule data structures // Schedule data structures
// //
UINT32 *FrameBase; UINT32 *FrameBase;
UINT32 *FrameBasePciMemAddr;
UHCI_QH_SW *SyncIntQh; UHCI_QH_SW *SyncIntQh;
UHCI_QH_SW *CtrlQh; UHCI_QH_SW *CtrlQh;
UHCI_QH_SW *BulkQh; UHCI_QH_SW *BulkQh;

View File

@ -152,19 +152,36 @@ EXIT:
/** /**
Link the TD To QH. Link the TD To QH.
@param Uhc The UHCI device.
@param Qh The queue head for the TD to link to. @param Qh The queue head for the TD to link to.
@param Td The TD to link. @param Td The TD to link.
**/ **/
VOID VOID
UhciLinkTdToQh ( UhciLinkTdToQh (
IN USB_HC_DEV *Uhc,
IN UHCI_QH_SW *Qh, IN UHCI_QH_SW *Qh,
IN UHCI_TD_SW *Td IN UHCI_TD_SW *Td
) )
{ {
ASSERT ((Qh != NULL) && (Td != NULL)); EFI_STATUS Status;
UINTN Len;
EFI_PHYSICAL_ADDRESS PhyAddr;
VOID* Map;
Qh->QhHw.VerticalLink = QH_VLINK (Td, FALSE); Len = sizeof (UHCI_TD_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Td,
&Len,
&PhyAddr,
&Map
);
ASSERT (!EFI_ERROR (Status) && (Qh != NULL) && (Td != NULL));
Qh->QhHw.VerticalLink = QH_VLINK (PhyAddr, FALSE);
Qh->TDs = (VOID *) Td; Qh->TDs = (VOID *) Td;
} }
@ -192,19 +209,36 @@ UhciUnlinkTdFromQh (
/** /**
Append a new TD To the previous TD. Append a new TD To the previous TD.
@param Uhc The UHCI device.
@param PrevTd Previous UHCI_TD_SW to be linked to. @param PrevTd Previous UHCI_TD_SW to be linked to.
@param ThisTd TD to link. @param ThisTd TD to link.
**/ **/
VOID VOID
UhciAppendTd ( UhciAppendTd (
IN USB_HC_DEV *Uhc,
IN UHCI_TD_SW *PrevTd, IN UHCI_TD_SW *PrevTd,
IN UHCI_TD_SW *ThisTd IN UHCI_TD_SW *ThisTd
) )
{ {
ASSERT ((PrevTd != NULL) && (ThisTd != NULL)); EFI_STATUS Status;
UINTN Len;
EFI_PHYSICAL_ADDRESS PhyAddr;
VOID* Map;
PrevTd->TdHw.NextLink = TD_LINK (ThisTd, TRUE, FALSE); Len = sizeof (UHCI_TD_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
ThisTd,
&Len,
&PhyAddr,
&Map
);
ASSERT (!EFI_ERROR (Status) && (PrevTd != NULL) && (ThisTd != NULL));
PrevTd->TdHw.NextLink = TD_LINK (PhyAddr, TRUE, FALSE);
PrevTd->NextTd = (VOID *) ThisTd; PrevTd->NextTd = (VOID *) ThisTd;
} }
@ -290,7 +324,6 @@ UhciCreateTd (
return NULL; return NULL;
} }
Td->TdHw.NextLink = TD_LINK (NULL, FALSE, TRUE);
Td->NextTd = NULL; Td->NextTd = NULL;
Td->Data = NULL; Td->Data = NULL;
Td->DataLen = 0; Td->DataLen = 0;
@ -304,7 +337,8 @@ UhciCreateTd (
@param Uhc The UHCI device. @param Uhc The UHCI device.
@param DevAddr Device address. @param DevAddr Device address.
@param Request Device request. @param Request A pointer to cpu memory address of Device request.
@param RequestPhy A pointer to pci memory address of Device request.
@param IsLow Full speed or low speed. @param IsLow Full speed or low speed.
@return The created setup Td Pointer. @return The created setup Td Pointer.
@ -315,6 +349,7 @@ UhciCreateSetupTd (
IN USB_HC_DEV *Uhc, IN USB_HC_DEV *Uhc,
IN UINT8 DevAddr, IN UINT8 DevAddr,
IN UINT8 *Request, IN UINT8 *Request,
IN UINT8 *RequestPhy,
IN BOOLEAN IsLow IN BOOLEAN IsLow
) )
{ {
@ -338,7 +373,7 @@ UhciCreateSetupTd (
Td->TdHw.DeviceAddr = DevAddr & 0x7F; Td->TdHw.DeviceAddr = DevAddr & 0x7F;
Td->TdHw.MaxPacketLen = (UINT32) (sizeof (EFI_USB_DEVICE_REQUEST) - 1); Td->TdHw.MaxPacketLen = (UINT32) (sizeof (EFI_USB_DEVICE_REQUEST) - 1);
Td->TdHw.PidCode = SETUP_PACKET_ID; Td->TdHw.PidCode = SETUP_PACKET_ID;
Td->TdHw.DataBuffer = (UINT32) (UINTN) Request; Td->TdHw.DataBuffer = (UINT32) (UINTN) RequestPhy;
Td->Data = Request; Td->Data = Request;
Td->DataLen = sizeof (EFI_USB_DEVICE_REQUEST); Td->DataLen = sizeof (EFI_USB_DEVICE_REQUEST);
@ -353,7 +388,8 @@ UhciCreateSetupTd (
@param Uhc The UHCI device. @param Uhc The UHCI device.
@param DevAddr Device address. @param DevAddr Device address.
@param Endpoint Endpoint number. @param Endpoint Endpoint number.
@param DataPtr Data buffer. @param DataPtr A pointer to cpu memory address of Data buffer.
@param DataPhyPtr A pointer to pci memory address of Data buffer.
@param Len Data length. @param Len Data length.
@param PktId Packet ID. @param PktId Packet ID.
@param Toggle Data toggle value. @param Toggle Data toggle value.
@ -368,6 +404,7 @@ UhciCreateDataTd (
IN UINT8 DevAddr, IN UINT8 DevAddr,
IN UINT8 Endpoint, IN UINT8 Endpoint,
IN UINT8 *DataPtr, IN UINT8 *DataPtr,
IN UINT8 *DataPhyPtr,
IN UINTN Len, IN UINTN Len,
IN UINT8 PktId, IN UINT8 PktId,
IN UINT8 Toggle, IN UINT8 Toggle,
@ -399,7 +436,7 @@ UhciCreateDataTd (
Td->TdHw.DeviceAddr = DevAddr & 0x7F; Td->TdHw.DeviceAddr = DevAddr & 0x7F;
Td->TdHw.MaxPacketLen = (UINT32) (Len - 1); Td->TdHw.MaxPacketLen = (UINT32) (Len - 1);
Td->TdHw.PidCode = (UINT8) PktId; Td->TdHw.PidCode = (UINT8) PktId;
Td->TdHw.DataBuffer = (UINT32) (UINTN) DataPtr; Td->TdHw.DataBuffer = (UINT32) (UINTN) DataPhyPtr;
Td->Data = DataPtr; Td->Data = DataPtr;
Td->DataLen = (UINT16) Len; Td->DataLen = (UINT16) Len;
@ -462,8 +499,10 @@ UhciCreateStatusTd (
@param Uhc The UHCI device. @param Uhc The UHCI device.
@param DeviceAddr The device address. @param DeviceAddr The device address.
@param DataPktId Packet Identification of Data Tds. @param DataPktId Packet Identification of Data Tds.
@param Request A pointer to request structure buffer to transfer. @param Request A pointer to cpu memory address of request structure buffer to transfer.
@param Data A pointer to user data buffer to transfer. @param RequestPhy A pointer to pci memory address of request structure buffer to transfer.
@param Data A pointer to cpu memory address of user data buffer to transfer.
@param DataPhy A pointer to pci memory address of user data buffer to transfer.
@param DataLen Length of user data to transfer. @param DataLen Length of user data to transfer.
@param MaxPacket Maximum packet size for control transfer. @param MaxPacket Maximum packet size for control transfer.
@param IsLow Full speed or low speed. @param IsLow Full speed or low speed.
@ -477,7 +516,9 @@ UhciCreateCtrlTds (
IN UINT8 DeviceAddr, IN UINT8 DeviceAddr,
IN UINT8 DataPktId, IN UINT8 DataPktId,
IN UINT8 *Request, IN UINT8 *Request,
IN UINT8 *RequestPhy,
IN UINT8 *Data, IN UINT8 *Data,
IN UINT8 *DataPhy,
IN UINTN DataLen, IN UINTN DataLen,
IN UINT8 MaxPacket, IN UINT8 MaxPacket,
IN BOOLEAN IsLow IN BOOLEAN IsLow
@ -502,7 +543,7 @@ UhciCreateCtrlTds (
// //
// Create setup packets for the transfer // Create setup packets for the transfer
// //
SetupTd = UhciCreateSetupTd (Uhc, DeviceAddr, Request, IsLow); SetupTd = UhciCreateSetupTd (Uhc, DeviceAddr, Request, RequestPhy, IsLow);
if (SetupTd == NULL) { if (SetupTd == NULL) {
return NULL; return NULL;
@ -523,7 +564,8 @@ UhciCreateCtrlTds (
Uhc, Uhc,
DeviceAddr, DeviceAddr,
0, 0,
Data, Data, //cpu memory address
DataPhy, //Pci memory address
ThisTdLen, ThisTdLen,
DataPktId, DataPktId,
DataToggle, DataToggle,
@ -538,12 +580,13 @@ UhciCreateCtrlTds (
FirstDataTd = DataTd; FirstDataTd = DataTd;
FirstDataTd->NextTd = NULL; FirstDataTd->NextTd = NULL;
} else { } else {
UhciAppendTd (PrevDataTd, DataTd); UhciAppendTd (Uhc, PrevDataTd, DataTd);
} }
DataToggle ^= 1; DataToggle ^= 1;
PrevDataTd = DataTd; PrevDataTd = DataTd;
Data += ThisTdLen; Data += ThisTdLen;
DataPhy += ThisTdLen;
DataLen -= ThisTdLen; DataLen -= ThisTdLen;
} }
@ -566,10 +609,10 @@ UhciCreateCtrlTds (
// Link setup Td -> data Tds -> status Td together // Link setup Td -> data Tds -> status Td together
// //
if (FirstDataTd != NULL) { if (FirstDataTd != NULL) {
UhciAppendTd (SetupTd, FirstDataTd); UhciAppendTd (Uhc, SetupTd, FirstDataTd);
UhciAppendTd (PrevDataTd, StatusTd); UhciAppendTd (Uhc, PrevDataTd, StatusTd);
} else { } else {
UhciAppendTd (SetupTd, StatusTd); UhciAppendTd (Uhc, SetupTd, StatusTd);
} }
return SetupTd; return SetupTd;
@ -594,7 +637,8 @@ FREE_TD:
@param DevAddr Address of Device. @param DevAddr Address of Device.
@param EndPoint Endpoint Number. @param EndPoint Endpoint Number.
@param PktId Packet Identification of Data Tds. @param PktId Packet Identification of Data Tds.
@param Data A pointer to user data buffer to transfer. @param Data A pointer to cpu memory address of user data buffer to transfer.
@param DataPhy A pointer to pci memory address of user data buffer to transfer.
@param DataLen Length of user data to transfer. @param DataLen Length of user data to transfer.
@param DataToggle Data Toggle Pointer. @param DataToggle Data Toggle Pointer.
@param MaxPacket Maximum packet size for Bulk/Interrupt transfer. @param MaxPacket Maximum packet size for Bulk/Interrupt transfer.
@ -610,6 +654,7 @@ UhciCreateBulkOrIntTds (
IN UINT8 EndPoint, IN UINT8 EndPoint,
IN UINT8 PktId, IN UINT8 PktId,
IN UINT8 *Data, IN UINT8 *Data,
IN UINT8 *DataPhy,
IN UINTN DataLen, IN UINTN DataLen,
IN OUT UINT8 *DataToggle, IN OUT UINT8 *DataToggle,
IN UINT8 MaxPacket, IN UINT8 MaxPacket,
@ -643,6 +688,7 @@ UhciCreateBulkOrIntTds (
DevAddr, DevAddr,
EndPoint, EndPoint,
Data, Data,
DataPhy,
ThisTdLen, ThisTdLen,
PktId, PktId,
*DataToggle, *DataToggle,
@ -661,12 +707,13 @@ UhciCreateBulkOrIntTds (
FirstDataTd = DataTd; FirstDataTd = DataTd;
FirstDataTd->NextTd = NULL; FirstDataTd->NextTd = NULL;
} else { } else {
UhciAppendTd (PrevDataTd, DataTd); UhciAppendTd (Uhc, PrevDataTd, DataTd);
} }
*DataToggle ^= 1; *DataToggle ^= 1;
PrevDataTd = DataTd; PrevDataTd = DataTd;
Data += ThisTdLen; Data += ThisTdLen;
DataPhy += ThisTdLen;
DataLen -= ThisTdLen; DataLen -= ThisTdLen;
} }

View File

@ -97,14 +97,14 @@ struct _UHCI_TD_SW {
/** /**
Link the TD To QH. Link the TD To QH.
@param Uhc The UHCI device.
@param Qh The queue head for the TD to link to. @param Qh The queue head for the TD to link to.
@param Td The TD to link. @param Td The TD to link.
@return None.
**/ **/
VOID VOID
UhciLinkTdToQh ( UhciLinkTdToQh (
IN USB_HC_DEV *Uhc,
IN UHCI_QH_SW *Qh, IN UHCI_QH_SW *Qh,
IN UHCI_TD_SW *Td IN UHCI_TD_SW *Td
); );
@ -212,8 +212,10 @@ UhciCreateQh (
@param Uhc The UHCI device. @param Uhc The UHCI device.
@param DeviceAddr The device address. @param DeviceAddr The device address.
@param DataPktId Packet Identification of Data Tds. @param DataPktId Packet Identification of Data Tds.
@param Request A pointer to request structure buffer to transfer. @param Request A pointer to cpu memory address of request structure buffer to transfer.
@param Data A pointer to user data buffer to transfer. @param RequestPhy A pointer to pci memory address of request structure buffer to transfer.
@param Data A pointer to cpu memory address of user data buffer to transfer.
@param DataPhy A pointer to pci memory address of user data buffer to transfer.
@param DataLen Length of user data to transfer. @param DataLen Length of user data to transfer.
@param MaxPacket Maximum packet size for control transfer. @param MaxPacket Maximum packet size for control transfer.
@param IsLow Full speed or low speed. @param IsLow Full speed or low speed.
@ -227,7 +229,9 @@ UhciCreateCtrlTds (
IN UINT8 DeviceAddr, IN UINT8 DeviceAddr,
IN UINT8 DataPktId, IN UINT8 DataPktId,
IN UINT8 *Request, IN UINT8 *Request,
IN UINT8 *RequestPhy,
IN UINT8 *Data, IN UINT8 *Data,
IN UINT8 *DataPhy,
IN UINTN DataLen, IN UINTN DataLen,
IN UINT8 MaxPacket, IN UINT8 MaxPacket,
IN BOOLEAN IsLow IN BOOLEAN IsLow
@ -241,7 +245,8 @@ UhciCreateCtrlTds (
@param DevAddr Address of Device. @param DevAddr Address of Device.
@param EndPoint Endpoint Number. @param EndPoint Endpoint Number.
@param PktId Packet Identification of Data Tds. @param PktId Packet Identification of Data Tds.
@param Data A pointer to user data buffer to transfer. @param Data A pointer to cpu memory address of user data buffer to transfer.
@param DataPhy A pointer to pci memory address of user data buffer to transfer.
@param DataLen Length of user data to transfer. @param DataLen Length of user data to transfer.
@param DataToggle Data Toggle Pointer. @param DataToggle Data Toggle Pointer.
@param MaxPacket Maximum packet size for Bulk/Interrupt transfer. @param MaxPacket Maximum packet size for Bulk/Interrupt transfer.
@ -257,6 +262,7 @@ UhciCreateBulkOrIntTds (
IN UINT8 EndPoint, IN UINT8 EndPoint,
IN UINT8 PktId, IN UINT8 PktId,
IN UINT8 *Data, IN UINT8 *Data,
IN UINT8 *DataPhy,
IN UINTN DataLen, IN UINTN DataLen,
IN OUT UINT8 *DataToggle, IN OUT UINT8 *DataToggle,
IN UINT8 MaxPacket, IN UINT8 MaxPacket,

View File

@ -38,6 +38,8 @@ UhciInitFrameList (
UINTN Pages; UINTN Pages;
UINTN Bytes; UINTN Bytes;
UINTN Index; UINTN Index;
UINTN Len;
EFI_PHYSICAL_ADDRESS PhyAddr;
// //
// The Frame List is a common buffer that will be // The Frame List is a common buffer that will be
@ -75,7 +77,8 @@ UhciInitFrameList (
goto ON_ERROR; goto ON_ERROR;
} }
Uhc->FrameBase = (UINT32 *) (UINTN) MappedAddr; Uhc->FrameBase = (UINT32 *) (UINTN) Buffer; // Cpu memory address
Uhc->FrameBasePciMemAddr = (UINT32 *) (UINTN) MappedAddr; // Pci memory address
Uhc->FrameMapping = Mapping; Uhc->FrameMapping = Mapping;
// //
@ -101,10 +104,31 @@ UhciInitFrameList (
// Each frame entry is linked to this sequence of QH. These QH // Each frame entry is linked to this sequence of QH. These QH
// will remain on the schedul, never got removed // will remain on the schedul, never got removed
// //
Uhc->SyncIntQh->QhHw.HorizonLink = QH_HLINK (Uhc->CtrlQh, FALSE); Len = sizeof (UHCI_QH_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Uhc->CtrlQh,
&Len,
&PhyAddr,
&Mapping
);
ASSERT (!EFI_ERROR (Status));
Uhc->SyncIntQh->QhHw.HorizonLink = QH_HLINK (PhyAddr, FALSE);
Uhc->SyncIntQh->NextQh = Uhc->CtrlQh; Uhc->SyncIntQh->NextQh = Uhc->CtrlQh;
Uhc->CtrlQh->QhHw.HorizonLink = QH_HLINK (Uhc->BulkQh, FALSE); Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Uhc->BulkQh,
&Len,
&PhyAddr,
&Mapping
);
ASSERT (!EFI_ERROR (Status));
Uhc->CtrlQh->QhHw.HorizonLink = QH_HLINK (PhyAddr, FALSE);
Uhc->CtrlQh->NextQh = Uhc->BulkQh; Uhc->CtrlQh->NextQh = Uhc->BulkQh;
// //
@ -112,19 +136,31 @@ UhciInitFrameList (
// in supporting the full speed bandwidth reclamation in the previous // in supporting the full speed bandwidth reclamation in the previous
// mentioned form. Most new platforms don't suffer it. // mentioned form. Most new platforms don't suffer it.
// //
Uhc->BulkQh->QhHw.HorizonLink = QH_HLINK (Uhc->BulkQh, FALSE); Uhc->BulkQh->QhHw.HorizonLink = QH_HLINK (PhyAddr, FALSE);
Uhc->BulkQh->NextQh = NULL; Uhc->BulkQh->NextQh = NULL;
Len = sizeof (UHCI_QH_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Uhc->SyncIntQh,
&Len,
&PhyAddr,
&Mapping
);
ASSERT (!EFI_ERROR (Status));
for (Index = 0; Index < UHCI_FRAME_NUM; Index++) { for (Index = 0; Index < UHCI_FRAME_NUM; Index++) {
Uhc->FrameBase[Index] = QH_HLINK (Uhc->SyncIntQh, FALSE); Uhc->FrameBase[Index] = QH_HLINK (Uhc->SyncIntQh, FALSE);
Uhc->FrameBasePciMemAddr[Index] = QH_HLINK (PhyAddr, FALSE);
} }
// //
// Tell the Host Controller where the Frame List lies, // Tell the Host Controller where the Frame List lies,
// by set the Frame List Base Address Register. // by set the Frame List Base Address Register.
// //
UhciSetFrameListBaseAddr (Uhc->PciIo, (VOID *) (Uhc->FrameBase)); UhciSetFrameListBaseAddr (Uhc->PciIo, (VOID *) (Uhc->FrameBasePciMemAddr));
return EFI_SUCCESS; return EFI_SUCCESS;
ON_ERROR: ON_ERROR:
@ -182,6 +218,7 @@ UhciDestoryFrameList (
} }
Uhc->FrameBase = NULL; Uhc->FrameBase = NULL;
Uhc->FrameBasePciMemAddr = NULL;
Uhc->SyncIntQh = NULL; Uhc->SyncIntQh = NULL;
Uhc->CtrlQh = NULL; Uhc->CtrlQh = NULL;
Uhc->BulkQh = NULL; Uhc->BulkQh = NULL;
@ -224,29 +261,45 @@ UhciConvertPollRate (
Link a queue head (for asynchronous interrupt transfer) to Link a queue head (for asynchronous interrupt transfer) to
the frame list. the frame list.
@param FrameBase The base of the frame list. @param Uhc The UHCI device.
@param Qh The queue head to link into. @param Qh The queue head to link into.
**/ **/
VOID VOID
UhciLinkQhToFrameList ( UhciLinkQhToFrameList (
UINT32 *FrameBase, USB_HC_DEV *Uhc,
UHCI_QH_SW *Qh UHCI_QH_SW *Qh
) )
{ {
UINTN Index; UINTN Index;
UHCI_QH_SW *Prev; UHCI_QH_SW *Prev;
UHCI_QH_SW *Next; UHCI_QH_SW *Next;
UINTN Len;
EFI_PHYSICAL_ADDRESS PhyAddr;
EFI_PHYSICAL_ADDRESS QhPciAddr;
VOID* Map;
EFI_STATUS Status;
ASSERT ((FrameBase != NULL) && (Qh != NULL)); ASSERT ((Uhc->FrameBase != NULL) && (Qh != NULL));
Len = sizeof (UHCI_QH_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Qh,
&Len,
&QhPciAddr,
&Map
);
ASSERT (!EFI_ERROR (Status));
for (Index = 0; Index < UHCI_FRAME_NUM; Index += Qh->Interval) { for (Index = 0; Index < UHCI_FRAME_NUM; Index += Qh->Interval) {
// //
// First QH can't be NULL because we always keep static queue // First QH can't be NULL because we always keep static queue
// heads on the frame list // heads on the frame list
// //
ASSERT (!LINK_TERMINATED (FrameBase[Index])); ASSERT (!LINK_TERMINATED (Uhc->FrameBase[Index]));
Next = UHCI_ADDR (FrameBase[Index]); Next = UHCI_ADDR (Uhc->FrameBase[Index]);
Prev = NULL; Prev = NULL;
// //
@ -266,9 +319,8 @@ UhciLinkQhToFrameList (
while (Next->Interval > Qh->Interval) { while (Next->Interval > Qh->Interval) {
Prev = Next; Prev = Next;
Next = Next->NextQh; Next = Next->NextQh;
}
ASSERT (Next != NULL); ASSERT (Next != NULL);
}
// //
// The entry may have been linked into the frame by early insertation. // The entry may have been linked into the frame by early insertation.
@ -298,7 +350,8 @@ UhciLinkQhToFrameList (
Prev->NextQh = Qh; Prev->NextQh = Qh;
Qh->QhHw.HorizonLink = Prev->QhHw.HorizonLink; Qh->QhHw.HorizonLink = Prev->QhHw.HorizonLink;
Prev->QhHw.HorizonLink = QH_HLINK (Qh, FALSE);
Prev->QhHw.HorizonLink = QH_HLINK (QhPciAddr, FALSE);
break; break;
} }
@ -309,14 +362,27 @@ UhciLinkQhToFrameList (
// //
if (Qh->NextQh == NULL) { if (Qh->NextQh == NULL) {
Qh->NextQh = Next; Qh->NextQh = Next;
Qh->QhHw.HorizonLink = QH_HLINK (Next, FALSE);
Len = sizeof (UHCI_QH_HW);
Status = Uhc->PciIo->Map (
Uhc->PciIo,
EfiPciIoOperationBusMasterRead,
Next,
&Len,
&PhyAddr,
&Map
);
ASSERT (!EFI_ERROR (Status));
Qh->QhHw.HorizonLink = QH_HLINK (PhyAddr, FALSE);
} }
if (Prev == NULL) { if (Prev == NULL) {
FrameBase[Index] = QH_HLINK (Qh, FALSE); Uhc->FrameBase[Index] = QH_HLINK (Qh, FALSE);
Uhc->FrameBasePciMemAddr[Index] = QH_HLINK (QhPciAddr, FALSE);
} else { } else {
Prev->NextQh = Qh; Prev->NextQh = Qh;
Prev->QhHw.HorizonLink = QH_HLINK (Qh, FALSE); Prev->QhHw.HorizonLink = QH_HLINK (QhPciAddr, FALSE);
} }
} }
} }
@ -327,13 +393,13 @@ UhciLinkQhToFrameList (
the precedence node, and pointer there next to QhSw's the precedence node, and pointer there next to QhSw's
next. next.
@param FrameBase The base address of the frame list. @param Uhc The UHCI device.
@param Qh The queue head to unlink. @param Qh The queue head to unlink.
**/ **/
VOID VOID
UhciUnlinkQhFromFrameList ( UhciUnlinkQhFromFrameList (
UINT32 *FrameBase, USB_HC_DEV *Uhc,
UHCI_QH_SW *Qh UHCI_QH_SW *Qh
) )
{ {
@ -341,15 +407,15 @@ UhciUnlinkQhFromFrameList (
UHCI_QH_SW *Prev; UHCI_QH_SW *Prev;
UHCI_QH_SW *This; UHCI_QH_SW *This;
ASSERT ((FrameBase != NULL) && (Qh != NULL)); ASSERT ((Uhc->FrameBase != NULL) && (Qh != NULL));
for (Index = 0; Index < UHCI_FRAME_NUM; Index += Qh->Interval) { for (Index = 0; Index < UHCI_FRAME_NUM; Index += Qh->Interval) {
// //
// Frame link can't be NULL because we always keep static // Frame link can't be NULL because we always keep static
// queue heads on the frame list // queue heads on the frame list
// //
ASSERT (!LINK_TERMINATED (FrameBase[Index])); ASSERT (!LINK_TERMINATED (Uhc->FrameBase[Index]));
This = UHCI_ADDR (FrameBase[Index]); This = UHCI_ADDR (Uhc->FrameBase[Index]);
Prev = NULL; Prev = NULL;
// //
@ -373,7 +439,8 @@ UhciUnlinkQhFromFrameList (
// //
// Qh is the first entry in the frame // Qh is the first entry in the frame
// //
FrameBase[Index] = Qh->QhHw.HorizonLink; Uhc->FrameBase[Index] = (UINT32)(UINTN)Qh->NextQh;
Uhc->FrameBasePciMemAddr[Index] = Qh->QhHw.HorizonLink;
} else { } else {
Prev->NextQh = Qh->NextQh; Prev->NextQh = Qh->NextQh;
Prev->QhHw.HorizonLink = Qh->QhHw.HorizonLink; Prev->QhHw.HorizonLink = Qh->QhHw.HorizonLink;
@ -592,6 +659,7 @@ UhciExecuteTransfer (
/** /**
Update Async Request, QH and TDs. Update Async Request, QH and TDs.
@param Uhc The UHCI device.
@param AsyncReq The UHCI asynchronous transfer to update. @param AsyncReq The UHCI asynchronous transfer to update.
@param Result Transfer reslut. @param Result Transfer reslut.
@param NextToggle The toggle of next data. @param NextToggle The toggle of next data.
@ -599,6 +667,7 @@ UhciExecuteTransfer (
**/ **/
VOID VOID
UhciUpdateAsyncReq ( UhciUpdateAsyncReq (
IN USB_HC_DEV *Uhc,
IN UHCI_ASYNC_REQUEST *AsyncReq, IN UHCI_ASYNC_REQUEST *AsyncReq,
IN UINT32 Result, IN UINT32 Result,
IN UINT32 NextToggle IN UINT32 NextToggle
@ -627,7 +696,7 @@ UhciUpdateAsyncReq (
Td->TdHw.Status |= USBTD_ACTIVE; Td->TdHw.Status |= USBTD_ACTIVE;
} }
UhciLinkTdToQh (Qh, FirstTd); UhciLinkTdToQh (Uhc, Qh, FirstTd);
return ; return ;
} }
} }
@ -759,7 +828,7 @@ UhciUnlinkAsyncReq (
ASSERT ((Uhc != NULL) && (AsyncReq != NULL)); ASSERT ((Uhc != NULL) && (AsyncReq != NULL));
RemoveEntryList (&(AsyncReq->Link)); RemoveEntryList (&(AsyncReq->Link));
UhciUnlinkQhFromFrameList (Uhc->FrameBase, AsyncReq->QhSw); UhciUnlinkQhFromFrameList (Uhc, AsyncReq->QhSw);
if (FreeNow) { if (FreeNow) {
UhciFreeAsyncReq (Uhc, AsyncReq); UhciFreeAsyncReq (Uhc, AsyncReq);
@ -985,7 +1054,7 @@ UhciMonitorAsyncReqList (
CopyMem (Data, AsyncReq->FirstTd->Data, QhResult.Complete); CopyMem (Data, AsyncReq->FirstTd->Data, QhResult.Complete);
} }
UhciUpdateAsyncReq (AsyncReq, QhResult.Result, QhResult.NextToggle); UhciUpdateAsyncReq (Uhc, AsyncReq, QhResult.Result, QhResult.NextToggle);
// //
// Now, either transfer is SUCCESS or met errors since // Now, either transfer is SUCCESS or met errors since

View File

@ -131,15 +131,13 @@ UhciConvertPollRate (
Link a queue head (for asynchronous interrupt transfer) to Link a queue head (for asynchronous interrupt transfer) to
the frame list. the frame list.
@param FrameBase The base of the frame list. @param Uhc The UHCI device.
@param Qh The queue head to link into. @param Qh The queue head to link into.
@return None.
**/ **/
VOID VOID
UhciLinkQhToFrameList ( UhciLinkQhToFrameList (
UINT32 *FrameBase, USB_HC_DEV *Uhc,
UHCI_QH_SW *Qh UHCI_QH_SW *Qh
); );
@ -149,15 +147,13 @@ UhciLinkQhToFrameList (
the precedence node, and pointer there next to QhSw's the precedence node, and pointer there next to QhSw's
next. next.
@param FrameBase The base address of the frame list. @param Uhc The UHCI device.
@param Qh The queue head to unlink. @param Qh The queue head to unlink.
@return None.
**/ **/
VOID VOID
UhciUnlinkQhFromFrameList ( UhciUnlinkQhFromFrameList (
UINT32 *FrameBase, USB_HC_DEV *Uhc,
UHCI_QH_SW *Qh UHCI_QH_SW *Qh
); );

View File

@ -852,8 +852,8 @@ UsbEnumeratePort (
return EFI_SUCCESS; return EFI_SUCCESS;
} }
DEBUG (( EFI_D_INFO, "UsbEnumeratePort: port %d state - %x, change - %x\n", DEBUG (( EFI_D_INFO, "UsbEnumeratePort: port %d state - %x, change - %x on %p\n",
Port, PortState.PortStatus, PortState.PortChangeStatus)); Port, PortState.PortStatus, PortState.PortChangeStatus, HubIf));
// //
// This driver only process two kinds of events now: over current and // This driver only process two kinds of events now: over current and