summaryrefslogtreecommitdiff
path: root/Chipset/NB/NbPciCSP.c
diff options
context:
space:
mode:
Diffstat (limited to 'Chipset/NB/NbPciCSP.c')
-rw-r--r--Chipset/NB/NbPciCSP.c1165
1 files changed, 1165 insertions, 0 deletions
diff --git a/Chipset/NB/NbPciCSP.c b/Chipset/NB/NbPciCSP.c
new file mode 100644
index 0000000..396e0df
--- /dev/null
+++ b/Chipset/NB/NbPciCSP.c
@@ -0,0 +1,1165 @@
+//*************************************************************************
+//*************************************************************************
+//** **
+//** (C)Copyright 1985-2011, American Megatrends, Inc. **
+//** **
+//** All Rights Reserved. **
+//** **
+//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 **
+//** **
+//** Phone: (770)-246-8600 **
+//** **
+//*************************************************************************
+//*************************************************************************
+
+//*************************************************************************
+// $Header: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/NbPciCSP.c 2 5/13/14 10:41p Dennisliu $
+//
+// $Revision: 2 $
+//
+// $Date: 5/13/14 10:41p $
+//*************************************************************************
+// Revision History
+// ----------------
+// $Log: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/NbPciCSP.c $
+//
+// 2 5/13/14 10:41p Dennisliu
+// [TAG] EIP167027
+// [Category] Improvement
+// [Description] [SharkBay Aptio4]Variable's attribute needs to be
+// reviewed by SA component driver
+// [Files] NBDXEBoard.c; IntelSaGopSetup.c; IntelSaGopPolicy.c;
+// NBDxe.c; NbPciCSP.c; PciHostBridge.c;
+//
+// 1 2/08/12 4:34a Yurenlai
+// Intel Haswell/NB eChipset initially releases.
+//
+//*************************************************************************
+//<AMI_FHDR_START>
+//
+// Name: NbPciCSP.c
+//
+// Description: Chipset Porting Hooks for PCI Host Bridge Driver.
+//
+//<AMI_FHDR_END>
+//*************************************************************************
+
+#include <Token.h>
+#if AMI_ROOT_BRIDGE_SUPPORT == 1
+/****** DO NOT WRITE ABOVE THIS LINE *******/
+
+//----------------------------------------------------------------------------
+// Include(s)
+//----------------------------------------------------------------------------
+
+#include "PciHostBridge.h"
+#include <Acpi11.h>
+#include <Acpi20.h>
+#include <Protocol\AcpiTable.h>
+#include <AmiCspLib.h>
+
+//----------------------------------------------------------------------------
+// Constant, Macro and Type Definition(s)
+//----------------------------------------------------------------------------
+// Constant Definition(s)
+
+#if ACPI_SUPPORT
+ #if defined(PI_SPECIFICATION_VERSION) && (PI_SPECIFICATION_VERSION >= 0x00010014)
+ #include <Protocol\AcpiSystemDescriptionTable.h>
+ #else
+ #include <Protocol\AcpiSupport.h>
+ #endif
+#endif
+
+// Macro Definition(s)
+
+// Type Definition(s)
+
+// Function Prototype(s)
+
+//----------------------------------------------------------------------------
+// Variable and External Declaration(s)
+//----------------------------------------------------------------------------
+// GUID Definition(s)
+
+EFI_GUID gEfiGlobalVariableGuid = EFI_GLOBAL_VARIABLE;
+
+// Variable Declaration(s)
+
+EFI_EVENT mAcpiEvent;
+VOID *mAcpiReg;
+UINTN mMcfgTblHandle = 0;
+CHAR16 gMemoryCeilingVariable[] = L"MemCeil.";
+
+#if (CORE_VERSION <= 4635)
+//----------------------------------------------------------------------------
+// For HOST AND ROOT BRIDGE Architectural information
+// see chapter 12.1.1 PCI Root Bridge I/O Overview of EFI 1.1 spec
+//----------------------------------------------------------------------------
+//This table will provide information on how many Root Bridges
+//particular Host Bridge will produce.
+//The table has NB_NUMBER_OF_HOST_BRG entries.
+//(Token NB_NUMBER_OF_HOST_BRG is defined in NB.sdl)
+//
+//For desktop chipset it will be ONE ROOT UNDER ONE HOST.
+//
+//If system has more than ONE Host Add more Lines
+//-----------------------------------------------------------------------------------------------
+
+UINTN gRbCountTbl[NB_NUMBER_OF_HOST_BRG]={
+ 1, //Number of root bridges produced by Host #0
+ //Number of root bridges produced by Host #1
+ //Number of root bridges produced by Host #2
+ //Number of root bridges produced by Host #3
+};
+
+//-----------------------------------------------------------------------------------------------
+// This is the table to provide each host allocation attributes
+// The table has NB_NUMBER_OF_HOST_BRG entries.
+// (Token NB_NUMBER_OF_HOST_BRG is defined in NB.sdl)
+// Accepted values are:
+// EFI_PCI_HOST_BRIDGE_COMBINE_MEM_PMEM
+// EFI_PCI_HOST_BRIDGE_MEM64_DECODE
+// These values can be ORed.
+// The values are defined and explained in
+// PCI Host Bridge Resource Allocation Protocol Specification V 0.9
+//-----------------------------------------------------------------------------------------------
+
+UINT64 gHbAllocAttribTbl[NB_NUMBER_OF_HOST_BRG]={
+ 0, //Allocation Attributes of Host #0
+ //Allocation Attributes of Host #1
+ //Allocation Attributes of Host #2
+ //Allocation Attributes of Host #3
+ // And so on
+};
+
+//-----------------------------------------------------------------------------------------------
+// This table will provide PCI Buses Decoding Information
+// in form of ACPI QWORD resource descriptor.
+// The only valid fields are:
+// ResourceType, _MIN, _LEN.
+// Maximum Bus may be calculated as: _MAX=_MIN+_LEN -1
+//
+// If system has more then one root bridge, add more lines
+//
+// Desktop chipset is simple chipset with only one root bridge
+// which decodes all bus ranges from 0 to 0xFF
+//
+// See definition of QWORD ACPI Resource Descriptor in ACPI 2.0 Spec
+// and "Address Space Resource Descriptor Internal definitions" in AcpiRes.h
+// Number of table entries depends on values ported in gRbCountTbl
+//-----------------------------------------------------------------------------------------------
+
+// Name, Len, Resource Type, Flags ,_GRA, _MIN, _MAX, _TRA, _LEN
+ASLR_QWORD_ASD gRbBusesTbl[] = {
+// for Root 0 at Host 0
+ {0x8a, 0x2b,ASLRV_SPC_TYPE_BUS, 0, 0, 0x1, 0x00, 0xff, 0, 0x100}
+// for Root 1 at Host 0 if any
+
+// for Root 0 at Host 1 if any
+};
+
+//-----------------------------------------------------------------------------------------------
+// This is the table for the Capabilities Supported by ROOT BRIDGE
+// See EFI 1.1 spec for meaning of the Capabilities bits
+//
+// if system has more than one root bridge add more lines
+// Number of table entries depends on values ported in gRbCountTbl
+//-----------------------------------------------------------------------------------------------
+
+UINT64 gRbSupportsTbl[] = {
+//for Root 0 at Host 0
+ (EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO | EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO| \
+ EFI_PCI_ATTRIBUTE_ISA_IO | EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO | \
+ EFI_PCI_ATTRIBUTE_VGA_MEMORY | EFI_PCI_ATTRIBUTE_VGA_IO | \
+ EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO),
+//for Root 1 at Host 0 if any
+
+//for Root 0 at Host 1 if any
+
+// and so on...
+};
+#endif
+
+// Protocol Definition(s)
+
+// External Declaration(s)
+
+// Function Definition(s)
+
+//----------------------------------------------------------------------------
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspGetPciSegment
+//
+// Description: This procedure returns PCI segment number for chipsets which
+// capable of decoding multiple PCI segments.
+//
+// Input: HostBridgeNumber - Host Bridge Number (0 Based)
+// RootBridgeNumber - Root Bridge Number (0 Based)
+//
+// Output: UINTN - PCI Segment Number (0 Based)
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+UINTN HbCspGetPciSegment (
+ IN UINTN HostBridgeNumber,
+ IN UINTN RootBridgeNumber )
+{
+
+ // Usually even server chipsets decodes only one PCI segment
+ // but if chipsets has more than one SEGMENT we have to specify
+ // which HOST/ROOT(s) pare will have SEG=0; SEG=1 and so on...
+
+ return 0; // this is for Single Host chipset
+
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspBeforeEnumeration
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeBeginEnumeration.
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspBeforeEnumeration (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspBeginBusAllocation
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeBeginBusAllocation.
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspBeginBusAllocation (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspEndBusAllocation
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeEndBusAllocation
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspEndBusAllocation (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspBeginResourceAllocation
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeBeginResourceAllocation.
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspBeginResourceAllocation (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspAllocateResources
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeAllocateResources.
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspAllocateResources (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspSetResources
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeSetResources.
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspSetResources (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbNotifyCspEndResourceAllocation
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// when NotifyPhase function is called with phase
+// EfiPciHostBridgeEndResourceAllocation
+//
+// Input: ResAllocProtocol - Pointer to Host Bridge Resource
+// Allocation Protocol.
+// RbIoProtocolBuffer - Pointer to Root Bridge I/O Protocol.
+// RbCount - Root Bridge counter.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbNotifyCspEndResourceAllocation (
+ IN EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL *ResAllocProtocol,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL **RbIoProtocolBuffer,
+ IN UINTN RbCount )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspStartBusEnumeration
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// StartBusEnumeration function, it must prepare initial Bus
+// ACPI Resource
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgIndex - Root Bridge index (0 Based).
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspStartBusEnumeration (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgIndex )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+#if (CORE_COMBINED_VERSION <= 0x4027B) // 4.6.3.5
+
+ ASLR_QWORD_ASD *br; // Bus Resource Descriptor
+
+ br = Malloc(sizeof(ASLR_QWORD_ASD));
+ ASSERT(br);
+ if(!br) return EFI_OUT_OF_RESOURCES;
+
+ // Fill out Bus Resource Requirements
+ MemCpy(br, &gRbBusesTbl[RootBrgIndex], sizeof(ASLR_QWORD_ASD));
+ Status = AppendItemLst((T_ITEM_LIST*)&RootBrgData->ResInitCnt, br);
+ ASSERT_EFI_ERROR(Status);
+#endif
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspSetBusNnumbers
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// SubmitBusNumbers function.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgIndex - Root Bridge index (0 Based).
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspSetBusNnumbers (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgIndex )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspSubmitResources
+//
+// Description: This procedure will be invoked in PCI Host Bridge Protocol
+// SubmitResources function.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgIndex - Root Bridge index (0 Based).
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspSubmitResources (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgIndex )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspAdjustMemoryMmioOverlap
+//
+// Description: This procedure will be invoked during PCI bus enumeration,
+// it determines the PCI memory base address below 4GB whether
+// it is overlapping the main memory, if it is overlapped, then
+// updates MemoryCeiling variable and reboot.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgIndex - Root Bridge index (0 Based).
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspAdjustMemoryMmioOverlap (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgIndex )
+{
+ EFI_STATUS Status;
+
+ EFI_GCD_MEMORY_SPACE_DESCRIPTOR *MemorySpaceMap;
+ UINTN NumberOfDescriptors;
+ ASLR_QWORD_ASD *Res;
+ UINTN i;
+ EFI_PHYSICAL_ADDRESS Highest4GMem = 0;
+ EFI_PHYSICAL_ADDRESS LowestMMIO = 0xffffffff;
+ EFI_PHYSICAL_ADDRESS LowestAllocMMIO = 0xffffffff;
+ UINTN MemoryCeiling = 0; // Init to 0
+ UINTN NewMemoryCeiling = 0xffffffff;
+ UINTN DataSize = sizeof(UINT32);
+ UINT32 Attributes; // [ EIP167027 ]
+#if (CORE_VERSION >= 4600)
+ DXE_SERVICES *DxeSvc;
+
+//------------------------------------
+ Status = LibGetDxeSvcTbl( &DxeSvc );
+ ASSERT_EFI_ERROR(Status)
+ if(EFI_ERROR(Status)) return Status;
+#else
+ ASSERT(gDxeSvcTbl);
+#endif
+ return EFI_SUCCESS;
+ //pRS->GetVariable ( gMemoryCeilingVariable, \ // [ EIP167027 ]
+ // &gEfiGlobalVariableGuid, \
+ // NULL, \
+ // &DataSize, \
+ // &MemoryCeiling );
+ pRS->GetVariable ( gMemoryCeilingVariable, \
+ &gEfiGlobalVariableGuid, \
+ &Attributes, \
+ &DataSize, \
+ &MemoryCeiling );
+ if (EFI_ERROR(Status))
+ Attributes = EFI_VARIABLE_NON_VOLATILE + EFI_VARIABLE_BOOTSERVICE_ACCESS;
+
+ // Memory sizing uses memory ceiling to set top of memory.
+
+
+#if (CORE_VERSION >= 4600)
+ Status = DxeSvc->GetMemorySpaceMap( &NumberOfDescriptors, \
+ &MemorySpaceMap );
+#else
+ Status = gDxeSvcTbl->GetMemorySpaceMap( &NumberOfDescriptors, \
+ &MemorySpaceMap );
+#endif
+ ASSERT_EFI_ERROR(Status)
+
+ // Find the lowest MMIO and lowest allocated MMIO in GCD.
+ for (i = 0; i < NumberOfDescriptors; ++i) {
+ EFI_GCD_MEMORY_SPACE_DESCRIPTOR *Descr = &MemorySpaceMap[i];
+ EFI_PHYSICAL_ADDRESS Base = Descr->BaseAddress;
+
+ // Find highest system below 4GB memory.
+ // Treat any non MMIO as system memory. Not all system memory is
+ // reported as system memory, such as SMM.
+
+ if (Descr->GcdMemoryType != EfiGcdMemoryTypeMemoryMappedIo && \
+ Base < LowestMMIO) {
+ EFI_PHYSICAL_ADDRESS EndMem = Base + Descr->Length - 1;
+ if (EndMem > Highest4GMem && EndMem <= 0xffffffff)
+ Highest4GMem = EndMem;
+
+ // Find Lowest mmio above system memory.
+ } else if (Descr->GcdMemoryType == EfiGcdMemoryTypeMemoryMappedIo) {
+ if (Base >= 0x100000) {
+ if (Base < LowestMMIO) LowestMMIO = Base;
+
+ // If ImageHandle, then MMIO is allocated.
+ if ((Base < LowestAllocMMIO) && Descr->ImageHandle)
+ LowestAllocMMIO = Base;
+ }
+ }
+ }
+
+ pBS->FreePool(MemorySpaceMap);
+
+ if (Highest4GMem + 1 != LowestMMIO) {
+ TRACE( (-1, "PciHostCSHooks: ") );
+ TRACE( (-1, "System Memory and MMIO are not consequitive.\n") );
+ TRACE( (-1, "Top of Below 4G Memory: %lX", Highest4GMem) );
+ TRACE( (-1, "Bottom of MMIO: %X\n", LowestMMIO) );
+ }
+
+
+ // Find any MMIO that could not be allocated due to small of MMIO region.
+ for (i = 0; i < RootBrgData->ResCount; ++i) {
+ EFI_PHYSICAL_ADDRESS NeededBottomMmio;
+
+ Res = RootBrgData->RbRes[i];
+
+ // Any unallocated MMIO will have Res->_MIN set to zero for the MMIO
+ // type.
+ if (Res->Type != ASLRV_SPC_TYPE_MEM || Res->_GRA != 32 || Res->_MIN)
+ continue;
+
+ // Determine new memory ceiling variable needed to allocate this
+ // memory.
+ NeededBottomMmio = LowestAllocMMIO - Res->_LEN;
+
+ // Round down. If resource is not allocated, _MAX contains
+ // granularity.
+ NeededBottomMmio &= ~Res->_MAX;
+ if (NeededBottomMmio < NewMemoryCeiling)
+ NewMemoryCeiling = (UINTN) NeededBottomMmio;
+ }
+
+ // Check if a NewMemory Ceiling is needed.
+ if (NewMemoryCeiling < 0xffffffff) {
+ if (!MemoryCeiling || MemoryCeiling != NewMemoryCeiling ) {
+
+ // Set memory ceiling variable.
+ //pRS->SetVariable( gMemoryCeilingVariable, \ // [ EIP167027 ]
+ // &gEfiGlobalVariableGuid, \
+ // EFI_VARIABLE_NON_VOLATILE + \
+ // EFI_VARIABLE_BOOTSERVICE_ACCESS + \
+ // EFI_VARIABLE_RUNTIME_ACCESS,
+ // sizeof (UINT32), \
+ // &NewMemoryCeiling );
+ pRS->SetVariable( gMemoryCeilingVariable, \
+ &gEfiGlobalVariableGuid, \
+ Attributes,
+ sizeof (UINT32), \
+ &NewMemoryCeiling );
+
+ TRACE((-1, "Adjusting maximum top of RAM.\n Resetting System.\n"));
+
+ // Reset only needed of type of physical memory overlaps with MMIO.
+
+#if (NV_SIMULATION != 1)
+ // Don't reset system in case of NVRAM simulation
+ pRS->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);
+#endif
+ // Control should not come here if NV_SIMULATION = 0.
+ }
+ return EFI_SUCCESS;
+ }
+
+ // Check to see if Ceiling needs to be increased. If too low,
+ // then part of the memory be not be usuable.
+ if (MemoryCeiling != LowestAllocMMIO) {
+
+ // Set memory ceiling variable.
+ //pRS->SetVariable( gMemoryCeilingVariable, \ // [ EIP167027 ]
+ // &gEfiGlobalVariableGuid, \
+ // EFI_VARIABLE_NON_VOLATILE + \
+ // EFI_VARIABLE_BOOTSERVICE_ACCESS + \
+ // EFI_VARIABLE_RUNTIME_ACCESS,
+ // sizeof (UINT32), \
+ // &LowestAllocMMIO );
+ pRS->SetVariable( gMemoryCeilingVariable, \
+ &gEfiGlobalVariableGuid, \
+ Attributes,
+ sizeof (UINT32), \
+ &LowestAllocMMIO );
+
+ TRACE((-1, "Adjusting maximum top of RAM.\n Resetting System.\n"));
+
+#if (NV_SIMULATION != 1)
+ // Don't reset system in case of NVRAM simulation
+ pRS->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);
+#endif
+ // Control should not come here if NV_SIMULATION = 0.
+ }
+
+ return EFI_SUCCESS;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspPreprocessController
+//
+// Description: This function is called for all the PCI controllers that
+// the PCI bus driver finds.
+// It can be used to Preprogram the controller.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgNumber - Root Bridge number (0 Based).
+// PciAddress - Address of the controller on the PCI bus.
+// Phase - The phase during enumeration
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspPreprocessController (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgNumber,
+ IN EFI_PCI_CONFIGURATION_ADDRESS PciAddress,
+ IN EFI_PCI_CONTROLLER_RESOURCE_ALLOCATION_PHASE Phase )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspMapRootBrgToHost
+//
+// Description: Chipset specific function that returns Host Bridge Number for
+// the corresponded Root Bridge.
+//
+// Input: RootBrgXlatHdr - Pointer to Root Bridge XLAT table entry.
+// AllocationAttr - Pointer to allocation attribute.
+// RbSuportedAttr - Pointer to Root Bridge supported attribute.
+//
+// Output: UINTN - Number of the Host Bridge that root bridge
+// identified by RootBrgXlatHdr belongs to.
+//
+// Note: THIS FUNCTION MUST BE PORTED FOR MULTI-HOST SYSTEMS
+// HOST bridge handle supports:
+// - ResourceAllocation Protocol (REQUIRED);
+// - RootHotplugControllerInitialization
+// Protocol (OPTIONAL);
+// - PciPlatform Protocol (OPTIONAL).
+// ROOT bridge handle supports:
+// - PciRootBridgeIo Protocol (REQUIRED).
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+UINTN HbCspMapRootBrgToHost (
+#if (PCIBUS_VERSION > 020102)
+ IN PCI_BUS_XLAT_HDR *RootBrgXlatHdr,
+ IN UINT64 *AllocationAttr,
+ IN UINT64 *RbSuportedAttr )
+#else
+ IN PCI_BUS_XLAT_HDR *RootBrgXlatHdr )
+#endif
+{
+ // Usually even server chipsets use only one PCI HOST abstraction
+ // but if chipset has more than one HOST we have to specify
+ // which ROOT from PciBusXlat table belongs to which HOST.
+
+ // Check if we need to update/change Allocation Attributes Passed to
+ // this function.
+ // Here we have ability to override Automaticaly generated Attributes
+ // based on SDL tokens COMBINE_MEM_PMEM and ABOVE_4G_PCI_DECODE
+ // bits currently defined for Allocation Attributes is:
+ // EFI_PCI_HOST_BRIDGE_COMBINE_MEM_PMEM
+ // EFI_PCI_HOST_BRIDGE_MEM64_DECODE
+ // Usually nothing needs to be done sor SINGLE HOST-SINGLE-ROOT systems
+ // NOTE: this function could be called more than one time for each HOST
+ // if you updating AllocationAttr only last data will be valid.
+ // PCI HostBridge Driver sets DEFAULT allocation attributes.
+ // Add code only if you need to overwrite it.
+
+ // if i.e. second root does not support PF_MMIO
+ // if(RootBrgXlatHdr->BusBuild == 0x80 ) \
+ // *AllocationAttr &= ~(EFI_PCI_HOST_BRIDGE_COMBINE_MEM_PMEM);
+ // else *RbSuportedAttr = ....;
+
+ // Check that in VeB PCI Wizard this Root creates bus 0
+ // This is usualy a compatibility bus
+ // Set the Compatibility bus Attributes it must decode Legacy resources
+
+ // PCI HostBridge Driver sets DEFAULT Supported ROOT BRIDGE Attributes.
+ // Add code only if you need to overwrite it.
+
+ // if (RootBrgXlatHdr->BusBuild == 0) *RbSuportedAttr= \
+ // (EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO | \
+ // EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO | \
+ // EFI_PCI_ATTRIBUTE_ISA_IO | \
+ // EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO | \
+ // EFI_PCI_ATTRIBUTE_VGA_MEMORY | \
+ // EFI_PCI_ATTRIBUTE_VGA_IO | \
+ // EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO);
+ // else *RbSuportedAttr = 0;
+
+ // Returning Host Number for Root Bridge corresponded to the Root
+ // ported as RootBrgXlatHdr->BusBuild from BusXLat Table
+ // for single SINGLEHOST-SINGLE-ROOT system this value always 0
+
+ // If your system MULTY-HOST/MULTY-ROOTs system
+ // you need to add code here to correctly map each ROOT referenced in
+ // VeB wizard to it's corresponded host
+
+ return 0;
+}
+
+#if (PCIBUS_VERSION > 020102)
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspAllocateResources
+//
+// Description: This function is invoked in PCI Host Bridge Driver when time
+// to ask GCD for resources. You can overwrite a default
+// algorithm used to allocate resources for the Root Bridge.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+// RootBrgData - Pointer to Root Bridge private structure data.
+// RootBrgIndex - Root Bridge index (0 Based).
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspAllocateResources (
+ IN PCI_HOST_BRG_DATA *HostBrgData,
+ IN PCI_ROOT_BRG_DATA *RootBrgData,
+ IN UINTN RootBrgIndex )
+{
+ EFI_STATUS Status = EFI_UNSUPPORTED;
+
+ return Status;
+}
+#endif
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: HbCspBasicChipsetInit
+//
+// Description: This function will be invoked after Initialization of generic
+// part of the Host and Root Bridges.
+// All Handles for PCIHostBrg and PciRootBrg has been created
+// and Protocol Intergaces installed.
+//
+// Input: HostBrgData - Pointer to Host Bridge private structure data.
+//
+// Output: EFI_STATUS
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS HbCspBasicChipsetInit (
+ IN PCI_HOST_BRG_DATA *HostBrg0 )
+{
+
+ return EFI_SUCCESS;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: RbCspIoPciMap
+//
+// Description: Chipset Specific function to Map Internal Device address
+// residing ABOVE 4G to the BELOW 4G address space for DMA.
+// MUST BE IMPLEMENTED if CHIPSET supports address space
+// decoding ABOVE 4G.
+//
+// Input: *RbData - Root Bridge private structure data
+// Operation - Operation to provide Mapping for
+// HostAddress - HostAddress of the Device
+// *NumberOfBytes - Number of Byte in Mapped Buffer.
+// *DeviceAddress - Mapped Device Address.
+// **Mapping - Mapping Info Structure this function must
+// allocate and fill.
+//
+// Output: EFI_STATUS
+// EFI_SUCCESS - Successful.
+// EFI_UNSUPPORTED - The Map function is not supported.
+// EFI_INVALID_PARAMETER - One of the parameters has an
+// invalid value.
+//
+// Notes: Porting is required for chipsets that supports Decoding
+// of the PCI Address Space ABOVE 4G.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS RbCspIoPciMap (
+ IN PCI_ROOT_BRG_DATA *RbData,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL_OPERATION Operation,
+ IN EFI_PHYSICAL_ADDRESS HostAddress,
+ IN OUT UINTN *NumberOfBytes,
+ OUT EFI_PHYSICAL_ADDRESS *DeviceAddress,
+ OUT VOID **Mapping )
+{
+
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ *Mapping = NULL;
+ Status = EFI_UNSUPPORTED;
+
+ // For Chipsets which DOES support decoding of the PCI resources ABOVE 4G.
+ // here must be something like that.
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: RbCspIoPciUnmap
+//
+// Description: Chipset Specific function to Unmap previousely Mapped
+// buffer for DMA.
+// MUST BE IMPLEMENTED if CHIPSET supports address space
+// decoding ABOVE 4G.
+//
+// Input: *RbData - Root Bridge private structure data
+// *Mapping - Mapping Info Structure this function must free.
+//
+// Output: EFI_STATUS
+// EFI_SUCCESS - Successful.
+// EFI_UNSUPPORTED - The Unmap function is not supported.
+// EFI_INVALID_PARAMETER - One of the parameters has an
+// invalid value.
+//
+// Notes: Porting required if needed.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS RbCspIoPciUnmap (
+ IN PCI_ROOT_BRG_DATA *RbData,
+ OUT PCI_ROOT_BRIDGE_MAPPING *Mapping )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+
+ if (Mapping != NULL) return EFI_INVALID_PARAMETER;
+ // for all other conditions we would return EFI_UNSUPPORTED.
+ Status = EFI_UNSUPPORTED;
+
+ // for Chipsets which DOES support decoding of the PCI resources ABOVE 4G.
+ // And provides corresponded mapping for the host address
+ // here must be something like that.
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: RbCspIoPciAttributes
+//
+// Description: Chipset Specific function to do PCI RB Attributes releated
+// programming.
+//
+// Input: RbData - Pointer to Root Bridge private structure.
+// Attributes - The Root Bridge attributes to be programming.
+// ResourceBase - Pointer to the resource base. (OPTIONAL)
+// ResourceLength - Pointer to the resource Length. (OPTIONAL)
+//
+// Output: EFI_STATUS
+// EFI_SUCCESS - Successful.
+// EFI_INVALID_PARAMETER - One of the parameters has an
+// invalid value.
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+EFI_STATUS RbCspIoPciAttributes (
+ IN PCI_ROOT_BRG_DATA *RbData,
+ IN UINT64 Attributes,
+ IN OUT UINT64 *ResourceBase OPTIONAL,
+ IN OUT UINT64 *ResourceLength OPTIONAL )
+{
+
+
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ // Any Additional Variables goes here
+
+ return Status;
+}
+
+//<AMI_PHDR_START>
+//----------------------------------------------------------------------------
+//
+// Procedure: RootBridgeIoPciRW
+//
+// Description: Read Pci Registers into buffer.
+// Csp Function which actualy access PCI Config Space.
+// Chipsets that capable of having PCI EXPRESS Ext Cfg Space
+// transactions.
+// Must Implement this access routine here.
+//
+// Input: *RbData - Root Bridge private structure.
+// Width - PCI Width.
+// Address - PCI Address.
+// Count - Number of width reads/writes.
+// *Buffer - Buffer where read/written.
+// Write - Set if write.
+//
+// Output: EFI_STATUS
+// EFI_SUCCESS - Successful read.
+// EFI_INVALID_PARAMETER - One of the parameters has an
+//----------------------------------------------------------------------------
+//<AMI_PHDR_END>
+
+EFI_STATUS RootBridgeIoPciRW (
+ IN PCI_ROOT_BRG_DATA *RbData,
+ IN EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL_WIDTH Width,
+ IN UINT64 Address,
+ IN UINTN Count,
+ IN OUT VOID *Buffer,
+ IN BOOLEAN Write )
+{
+ BOOLEAN ValidCfg = TRUE;
+ UINT8 IncrementValue = 1 << (Width & 3); // 1st 2 bits currently define
+ // width.
+ // Other bits define type.
+
+ UINTN PciAddress = PCIEX_BASE_ADDRESS + \
+ (((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->Bus << 20 ) + \
+ (((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->Device << 15 ) + \
+ (((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->Function << 12 );
+
+ PciAddress += \
+ ((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->ExtendedRegister ? \
+ ((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->ExtendedRegister : \
+ ((EFI_PCI_CONFIGURATION_ADDRESS*) &Address)->Register;
+
+ // To read 64bit values, reduce Increment Value (by half) and
+ // double the count value (by twice)
+ if (IncrementValue > 4) {
+ IncrementValue >>= 1;
+ Count <<= 1;
+ }
+
+ if (Width >= EfiPciWidthMaximum || IncrementValue > 4)
+ return EFI_INVALID_PARAMETER;
+
+ while (Count--) {
+ if (PciAddress >= (PCIEX_BASE_ADDRESS + PCIEX_LENGTH)) \
+ ValidCfg = FALSE;
+ if (Write) {
+ switch(IncrementValue) {
+ case 1:
+ if (ValidCfg) *(UINT8*)PciAddress = *(UINT8*)Buffer;
+ break;
+ case 2:
+ if (ValidCfg) *(UINT16*)PciAddress = *(UINT16*)Buffer;
+ break;
+ default:
+ if (ValidCfg) *(UINT32*)PciAddress = *(UINT32*)Buffer;
+ break;
+ }
+ } else {
+ switch(IncrementValue) {
+ case 1:
+ *(UINT8*)Buffer = (ValidCfg) ? *(UINT8*)PciAddress : -1;
+ break;
+ case 2:
+ *(UINT16*)Buffer = (ValidCfg) ? *(UINT16*)PciAddress : -1;
+ break;
+ default:
+ *(UINT32*)Buffer = (ValidCfg) ? *(UINT32*)PciAddress : -1;
+ break;
+ }
+ }
+
+ if (Width <= EfiPciWidthFifoUint64) {
+ Buffer = ((UINT8 *)Buffer + IncrementValue);
+ // Buffer is increased for only EfiPciWidthUintxx and
+ // EfiPciWidthFifoUintxx
+ }
+
+ // Only increment the PCI address if Width is not a FIFO.
+ if ((Width & 4) == 0) {
+ PciAddress += IncrementValue;
+ }
+ }
+
+ return EFI_SUCCESS;
+}
+
+/****** DO NOT WRITE BELOW THIS LINE *******/
+#endif //#if AMI_ROOT_BRIDGE_SUPPORT == 1
+
+//*************************************************************************
+//*************************************************************************
+//** **
+//** (C)Copyright 1985-2011, American Megatrends, Inc. **
+//** **
+//** All Rights Reserved. **
+//** **
+//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 **
+//** **
+//** Phone: (770)-246-8600 **
+//** **
+//*************************************************************************
+//*************************************************************************