3 Copyright (c) 2006 - 2008, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 This file include all platform action which can be customized
23 #include "BdsPlatform.h"
25 #define IS_PCI_ISA_PDECODE(_p) IS_CLASS3 (_p, PCI_CLASS_BRIDGE, PCI_CLASS_BRIDGE_ISA_PDECODE, 0)
27 CHAR16 mFirmwareVendor
[] = L
"TianoCore.org";
28 extern BOOLEAN gConnectAllHappened
;
29 extern USB_CLASS_FORMAT_DEVICE_PATH gUsbClassKeyboardDevicePath
;
31 // BDS Platform Functions
35 GetSystemTablesFromHob (
41 Find GUID'ed HOBs that contain EFI_PHYSICAL_ADDRESS of ACPI, SMBIOS, MPs tables
51 EFI_PEI_HOB_POINTERS GuidHob
;
52 EFI_PEI_HOB_POINTERS HobStart
;
53 EFI_PHYSICAL_ADDRESS
*Table
;
55 EFI_GUID
*TableGuidArray
[] = {
56 &gEfiAcpi20TableGuid
, &gEfiAcpiTableGuid
, &gEfiSmbiosTableGuid
, &gEfiMpsTableGuid
62 HobStart
.Raw
= GetHobList ();
64 // Iteratively add ACPI Table, SMBIOS Table, MPS Table to EFI System Table
66 for (Index
= 0; Index
< sizeof (TableGuidArray
) / sizeof (*TableGuidArray
); ++Index
) {
67 GuidHob
.Raw
= GetNextGuidHob (TableGuidArray
[Index
], HobStart
.Raw
);
68 if (GuidHob
.Raw
!= NULL
) {
69 Table
= GET_GUID_HOB_DATA (GuidHob
.Guid
);
72 // Check if Mps Table/Smbios Table/Acpi Table exists in E/F seg,
73 // According to UEFI Spec, we should make sure Smbios table,
74 // ACPI table and Mps tables kept in memory of specified type
76 ConvertSystemTable(TableGuidArray
[Index
], (VOID
**)&Table
);
77 gBS
->InstallConfigurationTable (TableGuidArray
[Index
], (VOID
*)Table
);
85 #define EFI_LDR_MEMORY_DESCRIPTOR_GUID \
86 { 0x7701d7e5, 0x7d1d, 0x4432, {0xa4, 0x68, 0x67, 0x3d, 0xab, 0x8a, 0xde, 0x60 }}
88 EFI_GUID gEfiLdrMemoryDescriptorGuid
= EFI_LDR_MEMORY_DESCRIPTOR_GUID
;
93 EFI_HOB_GUID_TYPE Hob
;
95 EFI_MEMORY_DESCRIPTOR
*MemDesc
;
106 EFI_MEMORY_DESCRIPTOR
*MemMap
;
107 EFI_MEMORY_DESCRIPTOR
*MemMapPtr
;
109 UINTN MapKey
, DescriptorSize
;
111 UINT32 DescriptorVersion
;
117 Status
= gBS
->GetMemoryMap (&MemMapSize
, MemMap
, &MapKey
, &DescriptorSize
, &DescriptorVersion
);
118 ASSERT (Status
== EFI_BUFFER_TOO_SMALL
);
119 MemMapSize
+= EFI_PAGE_SIZE
;
120 Status
= gBS
->AllocatePool (EfiBootServicesData
, MemMapSize
, &MemMap
);
121 ASSERT (Status
== EFI_SUCCESS
);
122 Status
= gBS
->GetMemoryMap (&MemMapSize
, MemMap
, &MapKey
, &DescriptorSize
, &DescriptorVersion
);
123 ASSERT (Status
== EFI_SUCCESS
);
126 ASSERT (DescriptorVersion
== EFI_MEMORY_DESCRIPTOR_VERSION
);
128 for (Index
= 0; Index
< MemMapSize
/ DescriptorSize
; Index
++) {
129 Bytes
= LShiftU64 (MemMap
->NumberOfPages
, 12);
130 DEBUG ((EFI_D_ERROR
, "%lX-%lX %lX %lX %X\n",
131 MemMap
->PhysicalStart
,
132 MemMap
->PhysicalStart
+ Bytes
- 1,
133 MemMap
->NumberOfPages
,
135 (UINTN
)MemMap
->Type
));
136 MemMap
= (EFI_MEMORY_DESCRIPTOR
*)((UINTN
)MemMap
+ DescriptorSize
);
139 gBS
->FreePool (MemMapPtr
);
149 EFI_PEI_HOB_POINTERS GuidHob
;
151 MEMORY_DESC_HOB MemoryDescHob
;
153 EFI_PHYSICAL_ADDRESS Memory
;
158 GuidHob
.Raw
= GetHobList();
160 GuidHob
.Raw
= GetNextGuidHob (&gEfiLdrMemoryDescriptorGuid
, GuidHob
.Raw
);
161 if (GuidHob
.Raw
== NULL
) {
162 DEBUG ((EFI_D_ERROR
, "Fail to get gEfiLdrMemoryDescriptorGuid from GUID HOB LIST!\n"));
165 Table
= GET_GUID_HOB_DATA (GuidHob
.Guid
);
167 DEBUG ((EFI_D_ERROR
, "Fail to get gEfiLdrMemoryDescriptorGuid from GUID HOB LIST!\n"));
170 MemoryDescHob
.MemDescCount
= *(UINTN
*)Table
;
171 MemoryDescHob
.MemDesc
= *(EFI_MEMORY_DESCRIPTOR
**)((UINTN
)Table
+ sizeof(UINTN
));
174 // Add ACPINVS, ACPIReclaim, and Reserved memory to MemoryMap
176 for (Index
= 0; Index
< MemoryDescHob
.MemDescCount
; Index
++) {
177 if (MemoryDescHob
.MemDesc
[Index
].PhysicalStart
< 0x100000) {
180 if (MemoryDescHob
.MemDesc
[Index
].PhysicalStart
>= 0x100000000ULL
) {
183 if ((MemoryDescHob
.MemDesc
[Index
].Type
== EfiReservedMemoryType
) ||
184 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiRuntimeServicesData
) ||
185 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiRuntimeServicesCode
) ||
186 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiACPIReclaimMemory
) ||
187 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiACPIMemoryNVS
)) {
188 DEBUG ((EFI_D_ERROR
, "PhysicalStart - 0x%x, ", MemoryDescHob
.MemDesc
[Index
].PhysicalStart
));
189 DEBUG ((EFI_D_ERROR
, "PageNumber - 0x%x, ", MemoryDescHob
.MemDesc
[Index
].NumberOfPages
));
190 DEBUG ((EFI_D_ERROR
, "Type - 0x%x\n", MemoryDescHob
.MemDesc
[Index
].Type
));
191 if ((MemoryDescHob
.MemDesc
[Index
].Type
== EfiRuntimeServicesData
) ||
192 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiRuntimeServicesCode
)) {
194 // Skip RuntimeSevicesData and RuntimeServicesCode, they are BFV
198 Status
= gDS
->AddMemorySpace (
199 EfiGcdMemoryTypeSystemMemory
,
200 MemoryDescHob
.MemDesc
[Index
].PhysicalStart
,
201 LShiftU64 (MemoryDescHob
.MemDesc
[Index
].NumberOfPages
, EFI_PAGE_SHIFT
),
202 MemoryDescHob
.MemDesc
[Index
].Attribute
204 if (EFI_ERROR (Status
)) {
205 DEBUG ((EFI_D_ERROR
, "AddMemorySpace fail!\n"));
206 if ((MemoryDescHob
.MemDesc
[Index
].Type
== EfiACPIReclaimMemory
) ||
207 (MemoryDescHob
.MemDesc
[Index
].Type
== EfiACPIMemoryNVS
)) {
209 // For EfiACPIReclaimMemory and EfiACPIMemoryNVS, it must success.
210 // For EfiReservedMemoryType, there maybe overlap. So skip check here.
212 // ASSERT_EFI_ERROR (Status);
217 Memory
= MemoryDescHob
.MemDesc
[Index
].PhysicalStart
;
218 Status
= gBS
->AllocatePages (
220 MemoryDescHob
.MemDesc
[Index
].Type
,
221 (UINTN
)MemoryDescHob
.MemDesc
[Index
].NumberOfPages
,
224 if (EFI_ERROR (Status
)) {
225 DEBUG ((EFI_D_ERROR
, "AllocatePages fail!\n"));
227 // For the page added, it must be allocated.
229 // ASSERT_EFI_ERROR (Status);
238 DisableUsbLegacySupport(
244 Disabble the USB legacy Support in all Ehci and Uhci.
245 This function assume all PciIo handles have been created in system.
256 EFI_HANDLE
*HandleArray
;
257 UINTN HandleArrayCount
;
259 EFI_PCI_IO_PROTOCOL
*PciIo
;
268 // Find the usb host controller
270 Status
= gBS
->LocateHandleBuffer (
272 &gEfiPciIoProtocolGuid
,
277 if (!EFI_ERROR (Status
)) {
278 for (Index
= 0; Index
< HandleArrayCount
; Index
++) {
279 Status
= gBS
->HandleProtocol (
281 &gEfiPciIoProtocolGuid
,
284 if (!EFI_ERROR (Status
)) {
286 // Find the USB host controller controller
288 Status
= PciIo
->Pci
.Read (PciIo
, EfiPciIoWidthUint8
, 0x09, 3, &Class
);
289 if (!EFI_ERROR (Status
)) {
290 if ((PCI_CLASS_SERIAL
== Class
[2]) &&
291 (PCI_CLASS_SERIAL_USB
== Class
[1])) {
292 if (PCI_CLASSC_PI_UHCI
== Class
[0]) {
294 // Found the UHCI, then disable the legacy support
297 Status
= PciIo
->Pci
.Write (PciIo
, EfiPciIoWidthUint16
, 0xC0, 1, &Command
);
298 } else if (PCI_CLASSC_PI_EHCI
== Class
[0]) {
300 // Found the EHCI, then disable the legacy support
302 Status
= PciIo
->Mem
.Read (
306 (UINT64
) 0x08, //EHC_HCCPARAMS_OFFSET
311 ExtendCap
= (HcCapParams
>> 8) & 0xFF;
313 // Disable the SMI in USBLEGCTLSTS firstly
315 PciIo
->Pci
.Read (PciIo
, EfiPciIoWidthUint32
, ExtendCap
+ 0x4, 1, &Value
);
317 PciIo
->Pci
.Write (PciIo
, EfiPciIoWidthUint32
, ExtendCap
+ 0x4, 1, &Value
);
320 // Get EHCI Ownership from legacy bios
322 PciIo
->Pci
.Read (PciIo
, EfiPciIoWidthUint32
, ExtendCap
, 1, &Value
);
323 Value
|= (0x1 << 24);
324 PciIo
->Pci
.Write (PciIo
, EfiPciIoWidthUint32
, ExtendCap
, 1, &Value
);
330 PciIo
->Pci
.Read (PciIo
, EfiPciIoWidthUint32
, ExtendCap
, 1, &Value
);
332 if ((Value
& 0x01010000) == 0x01000000) {
344 gBS
->FreePool (HandleArray
);
351 IN EFI_BDS_ARCH_PROTOCOL_INSTANCE
*PrivateData
357 Platform Bds init. Incude the platform firmware vendor, revision
362 PrivateData - The EFI_BDS_ARCH_PROTOCOL_INSTANCE instance
371 // set firmwarevendor, here can be IBV/OEM customize
373 gST
->FirmwareVendor
= AllocateRuntimeCopyPool (
374 sizeof (mFirmwareVendor
),
377 ASSERT (gST
->FirmwareVendor
!= NULL
);
379 gST
->FirmwareRevision
= 0;
382 // Fixup Tasble CRC after we updated Firmware Vendor and Revision
384 gBS
->CalculateCrc32 ((VOID
*) gST
, sizeof (EFI_SYSTEM_TABLE
), &gST
->Hdr
.CRC32
);
386 GetSystemTablesFromHob ();
391 // Append Usb Keyboard short form DevicePath into "ConInDev"
393 BdsLibUpdateConsoleVariable (
395 (EFI_DEVICE_PATH_PROTOCOL
*) &gUsbClassKeyboardDevicePath
,
401 GetPciExpressBaseAddressForRootBridge (
402 IN UINTN HostBridgeNumber
,
403 IN UINTN RootBridgeNumber
408 This routine is to get PciExpress Base Address for this RootBridge
411 HostBridgeNumber - The number of HostBridge
412 RootBridgeNumber - The number of RootBridge
415 UINT64 - PciExpressBaseAddress for this HostBridge and RootBridge
419 EFI_PCI_EXPRESS_BASE_ADDRESS_INFORMATION
*PciExpressBaseAddressInfo
;
423 EFI_PEI_HOB_POINTERS GuidHob
;
427 // Get Hob List from configuration table
429 GuidHob
.Raw
= GetHobList ();
432 // Get PciExpressAddressInfo Hob
434 GuidHob
.Raw
= GetNextGuidHob (&gEfiPciExpressBaseAddressGuid
, GuidHob
.Raw
);
435 if (GuidHob
.Raw
== NULL
) {
436 DEBUG ((EFI_D_ERROR
, "Fail to get gEfiPciExpressBaseAddressGuid from GUID HOB\n"));
439 PciExpressBaseAddressInfo
= (EFI_PCI_EXPRESS_BASE_ADDRESS_INFORMATION
*) GET_GUID_HOB_DATA (GuidHob
.Guid
);
440 if (PciExpressBaseAddressInfo
== NULL
) {
441 DEBUG ((EFI_D_ERROR
, "Fail to get gEfiPciExpressBaseAddressGuid from GUID HOB\n"));
446 // Search the PciExpress Base Address in the Hob for current RootBridge
448 Number
= (UINT32
)(BufferSize
/ sizeof(EFI_PCI_EXPRESS_BASE_ADDRESS_INFORMATION
));
449 for (Index
= 0; Index
< Number
; Index
++) {
450 if ((PciExpressBaseAddressInfo
[Index
].HostBridgeNumber
== HostBridgeNumber
) &&
451 (PciExpressBaseAddressInfo
[Index
].RootBridgeNumber
== RootBridgeNumber
)) {
452 return PciExpressBaseAddressInfo
[Index
].PciExpressBaseAddress
;
457 // Do not find the PciExpress Base Address in the Hob
463 PatchPciRootBridgeDevicePath (
464 IN UINTN HostBridgeNumber
,
465 IN UINTN RootBridgeNumber
,
466 IN PLATFORM_ROOT_BRIDGE_DEVICE_PATH
*RootBridge
469 UINT64 PciExpressBase
;
471 PciExpressBase
= GetPciExpressBaseAddressForRootBridge (HostBridgeNumber
, RootBridgeNumber
);
473 if (PciExpressBase
!= 0) {
474 RootBridge
->PciRootBridge
.HID
= EISA_PNP_ID(0x0A08);
494 EFI_SUCCESS - Connect RootBridge successfully.
495 EFI_STATUS - Connect RootBridge fail.
500 EFI_HANDLE RootHandle
;
503 // Patch Pci Root Bridge Device Path
505 PatchPciRootBridgeDevicePath (0, 0, &gPlatformRootBridge0
);
508 // Make all the PCI_IO protocols on PCI Seg 0 show up
510 BdsLibConnectDevicePath (gPlatformRootBridges
[0]);
512 Status
= gBS
->LocateDevicePath (
513 &gEfiDevicePathProtocolGuid
,
514 &gPlatformRootBridges
[0],
517 if (EFI_ERROR (Status
)) {
521 Status
= gBS
->ConnectController (RootHandle
, NULL
, NULL
, FALSE
);
522 if (EFI_ERROR (Status
)) {
530 PrepareLpcBridgeDevicePath (
531 IN EFI_HANDLE DeviceHandle
537 Add IsaKeyboard to ConIn,
538 add IsaSerial to ConOut, ConIn, ErrOut.
543 DeviceHandle - Handle of PCIIO protocol.
547 EFI_SUCCESS - LPC bridge is added to ConOut, ConIn, and ErrOut.
548 EFI_STATUS - No LPC bridge is added.
553 EFI_DEVICE_PATH_PROTOCOL
*DevicePath
;
554 EFI_DEVICE_PATH_PROTOCOL
*TempDevicePath
;
557 Status
= gBS
->HandleProtocol (
559 &gEfiDevicePathProtocolGuid
,
562 if (EFI_ERROR (Status
)) {
565 TempDevicePath
= DevicePath
;
570 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gPnpPs2KeyboardDeviceNode
);
572 BdsLibUpdateConsoleVariable (VarConsoleInp
, DevicePath
, NULL
);
577 DevicePath
= TempDevicePath
;
578 gPnp16550ComPortDeviceNode
.UID
= 0;
580 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gPnp16550ComPortDeviceNode
);
581 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gUartDeviceNode
);
582 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gTerminalTypeDeviceNode
);
584 BdsLibUpdateConsoleVariable (VarConsoleOut
, DevicePath
, NULL
);
585 BdsLibUpdateConsoleVariable (VarConsoleInp
, DevicePath
, NULL
);
586 BdsLibUpdateConsoleVariable (VarErrorOut
, DevicePath
, NULL
);
591 DevicePath
= TempDevicePath
;
592 gPnp16550ComPortDeviceNode
.UID
= 1;
594 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gPnp16550ComPortDeviceNode
);
595 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gUartDeviceNode
);
596 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gTerminalTypeDeviceNode
);
598 BdsLibUpdateConsoleVariable (VarConsoleOut
, DevicePath
, NULL
);
599 BdsLibUpdateConsoleVariable (VarConsoleInp
, DevicePath
, NULL
);
600 BdsLibUpdateConsoleVariable (VarErrorOut
, DevicePath
, NULL
);
607 IN EFI_DEVICE_PATH_PROTOCOL
*PciDevicePath
,
608 OUT EFI_DEVICE_PATH_PROTOCOL
**GopDevicePath
613 EFI_HANDLE PciDeviceHandle
;
614 EFI_DEVICE_PATH_PROTOCOL
*TempDevicePath
;
615 EFI_DEVICE_PATH_PROTOCOL
*TempPciDevicePath
;
616 UINTN GopHandleCount
;
617 EFI_HANDLE
*GopHandleBuffer
;
619 if (PciDevicePath
== NULL
|| GopDevicePath
== NULL
) {
620 return EFI_INVALID_PARAMETER
;
624 // Initialize the GopDevicePath to be PciDevicePath
626 *GopDevicePath
= PciDevicePath
;
627 TempPciDevicePath
= PciDevicePath
;
629 Status
= gBS
->LocateDevicePath (
630 &gEfiDevicePathProtocolGuid
,
634 if (EFI_ERROR (Status
)) {
639 // Try to connect this handle, so that GOP dirver could start on this
640 // device and create child handles with GraphicsOutput Protocol installed
641 // on them, then we get device paths of these child handles and select
642 // them as possible console device.
644 gBS
->ConnectController (PciDeviceHandle
, NULL
, NULL
, FALSE
);
646 Status
= gBS
->LocateHandleBuffer (
648 &gEfiGraphicsOutputProtocolGuid
,
653 if (!EFI_ERROR (Status
)) {
655 // Add all the child handles as possible Console Device
657 for (Index
= 0; Index
< GopHandleCount
; Index
++) {
658 Status
= gBS
->HandleProtocol (GopHandleBuffer
[Index
], &gEfiDevicePathProtocolGuid
, (VOID
*)&TempDevicePath
);
659 if (EFI_ERROR (Status
)) {
665 GetDevicePathSize (PciDevicePath
) - END_DEVICE_PATH_LENGTH
668 // In current implementation, we only enable one of the child handles
669 // as console device, i.e. sotre one of the child handle's device
670 // path to variable "ConOut"
671 // In futhure, we could select all child handles to be console device
674 *GopDevicePath
= TempDevicePath
;
677 // Delete the PCI device's path that added by GetPlugInPciVgaDevicePath()
678 // Add the integrity GOP device path.
680 BdsLibUpdateConsoleVariable (VarConsoleOutDev
, NULL
, PciDevicePath
);
681 BdsLibUpdateConsoleVariable (VarConsoleOutDev
, TempDevicePath
, NULL
);
684 gBS
->FreePool (GopHandleBuffer
);
691 PreparePciVgaDevicePath (
692 IN EFI_HANDLE DeviceHandle
698 Add PCI VGA to ConOut.
703 DeviceHandle - Handle of PCIIO protocol.
707 EFI_SUCCESS - PCI VGA is added to ConOut.
708 EFI_STATUS - No PCI VGA device is added.
713 EFI_DEVICE_PATH_PROTOCOL
*DevicePath
;
714 EFI_DEVICE_PATH_PROTOCOL
*GopDevicePath
;
717 Status
= gBS
->HandleProtocol (
719 &gEfiDevicePathProtocolGuid
,
722 if (EFI_ERROR (Status
)) {
726 GetGopDevicePath (DevicePath
, &GopDevicePath
);
727 DevicePath
= GopDevicePath
;
729 BdsLibUpdateConsoleVariable (VarConsoleOut
, DevicePath
, NULL
);
735 PreparePciSerialDevicePath (
736 IN EFI_HANDLE DeviceHandle
742 Add PCI Serial to ConOut, ConIn, ErrOut.
747 DeviceHandle - Handle of PCIIO protocol.
751 EFI_SUCCESS - PCI Serial is added to ConOut, ConIn, and ErrOut.
752 EFI_STATUS - No PCI Serial device is added.
757 EFI_DEVICE_PATH_PROTOCOL
*DevicePath
;
760 Status
= gBS
->HandleProtocol (
762 &gEfiDevicePathProtocolGuid
,
765 if (EFI_ERROR (Status
)) {
769 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gUartDeviceNode
);
770 DevicePath
= AppendDevicePathNode (DevicePath
, (EFI_DEVICE_PATH_PROTOCOL
*)&gTerminalTypeDeviceNode
);
772 BdsLibUpdateConsoleVariable (VarConsoleOut
, DevicePath
, NULL
);
773 BdsLibUpdateConsoleVariable (VarConsoleInp
, DevicePath
, NULL
);
774 BdsLibUpdateConsoleVariable (VarErrorOut
, DevicePath
, NULL
);
780 DetectAndPreparePlatformPciDevicePath (
781 BOOLEAN DetectVgaOnly
787 Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
791 DetectVgaOnly - Only detect VGA device if it's TRUE.
795 EFI_SUCCESS - PCI Device check and Console variable update successfully.
796 EFI_STATUS - PCI Device check or Console variable update fail.
802 EFI_HANDLE
*HandleBuffer
;
804 EFI_PCI_IO_PROTOCOL
*PciIo
;
808 // Start to check all the PciIo to find all possible device
812 Status
= gBS
->LocateHandleBuffer (
814 &gEfiPciIoProtocolGuid
,
819 if (EFI_ERROR (Status
)) {
823 for (Index
= 0; Index
< HandleCount
; Index
++) {
824 Status
= gBS
->HandleProtocol (HandleBuffer
[Index
], &gEfiPciIoProtocolGuid
, (VOID
*)&PciIo
);
825 if (EFI_ERROR (Status
)) {
830 // Check for all PCI device
832 Status
= PciIo
->Pci
.Read (
836 sizeof (Pci
) / sizeof (UINT32
),
839 if (EFI_ERROR (Status
)) {
843 if (!DetectVgaOnly
) {
845 // Here we decide whether it is LPC Bridge
847 if ((IS_PCI_LPC (&Pci
)) ||
848 ((IS_PCI_ISA_PDECODE (&Pci
)) && (Pci
.Hdr
.VendorId
== 0x8086) && (Pci
.Hdr
.DeviceId
== 0x7110))) {
850 // Add IsaKeyboard to ConIn,
851 // add IsaSerial to ConOut, ConIn, ErrOut
853 DEBUG ((EFI_D_INFO
, "Find the LPC Bridge device\n"));
854 PrepareLpcBridgeDevicePath (HandleBuffer
[Index
]);
858 // Here we decide which Serial device to enable in PCI bus
860 if (IS_PCI_16550SERIAL (&Pci
)) {
862 // Add them to ConOut, ConIn, ErrOut.
864 DEBUG ((EFI_D_INFO
, "Find the 16550 SERIAL device\n"));
865 PreparePciSerialDevicePath (HandleBuffer
[Index
]);
871 // Here we decide which VGA device to enable in PCI bus
873 if (IS_PCI_VGA (&Pci
)) {
875 // Add them to ConOut.
877 DEBUG ((EFI_D_INFO
, "Find the VGA device\n"));
878 PreparePciVgaDevicePath (HandleBuffer
[Index
]);
883 gBS
->FreePool (HandleBuffer
);
889 PlatformBdsConnectConsole (
890 IN BDS_CONSOLE_CONNECT_ENTRY
*PlatformConsole
896 Connect the predefined platform default console device. Always try to find
897 and enable the vga device if have.
901 PlatformConsole - Predfined platform default console device array.
905 EFI_SUCCESS - Success connect at least one ConIn and ConOut
906 device, there must have one ConOut device is
909 EFI_STATUS - Return the status of
910 BdsLibConnectAllDefaultConsoles ()
916 EFI_DEVICE_PATH_PROTOCOL
*VarConout
;
917 EFI_DEVICE_PATH_PROTOCOL
*VarConin
;
918 UINTN DevicePathSize
;
921 // Connect RootBridge
923 ConnectRootBridge ();
925 VarConout
= BdsLibGetVariableAndSize (
927 &gEfiGlobalVariableGuid
,
930 VarConin
= BdsLibGetVariableAndSize (
932 &gEfiGlobalVariableGuid
,
936 if (VarConout
== NULL
|| VarConin
== NULL
) {
938 // Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
940 DetectAndPreparePlatformPciDevicePath (FALSE
);
943 // Have chance to connect the platform default console,
944 // the platform default console is the minimue device group
945 // the platform should support
947 for (Index
= 0; PlatformConsole
[Index
].DevicePath
!= NULL
; ++Index
) {
949 // Update the console variable with the connect type
951 if ((PlatformConsole
[Index
].ConnectType
& CONSOLE_IN
) == CONSOLE_IN
) {
952 BdsLibUpdateConsoleVariable (VarConsoleInp
, PlatformConsole
[Index
].DevicePath
, NULL
);
954 if ((PlatformConsole
[Index
].ConnectType
& CONSOLE_OUT
) == CONSOLE_OUT
) {
955 BdsLibUpdateConsoleVariable (VarConsoleOut
, PlatformConsole
[Index
].DevicePath
, NULL
);
957 if ((PlatformConsole
[Index
].ConnectType
& STD_ERROR
) == STD_ERROR
) {
958 BdsLibUpdateConsoleVariable (VarErrorOut
, PlatformConsole
[Index
].DevicePath
, NULL
);
963 // Only detect VGA device and add them to ConOut
965 DetectAndPreparePlatformPciDevicePath (TRUE
);
969 // The ConIn devices connection will start the USB bus, should disable all
970 // Usb legacy support firstly.
971 // Caution: Must ensure the PCI bus driver has been started. Since the
972 // ConnectRootBridge() will create all the PciIo protocol, it's safe here now
974 Status
= DisableUsbLegacySupport();
977 // Connect the all the default console with current cosole variable
979 Status
= BdsLibConnectAllDefaultConsoles ();
980 if (EFI_ERROR (Status
)) {
988 PlatformBdsConnectSequence (
995 Connect with predeined platform connect sequence,
996 the OEM/IBV can customize with their own connect sequence.
1013 // Here we can get the customized platform connect sequence
1014 // Notes: we can connect with new variable which record the
1015 // last time boots connect device path sequence
1017 while (gPlatformConnectSequence
[Index
] != NULL
) {
1019 // Build the platform boot option
1021 BdsLibConnectDevicePath (gPlatformConnectSequence
[Index
]);
1028 PlatformBdsGetDriverOption (
1029 IN OUT LIST_ENTRY
*BdsDriverLists
1033 Routine Description:
1035 Load the predefined driver option, OEM/IBV can customize this
1036 to load their own drivers
1040 BdsDriverLists - The header of the driver option link list.
1053 // Here we can get the customized platform driver option
1055 while (gPlatformDriverOption
[Index
] != NULL
) {
1057 // Build the platform boot option
1059 BdsLibRegisterNewOption (BdsDriverLists
, gPlatformDriverOption
[Index
], NULL
, L
"DriverOrder");
1066 PlatformBdsDiagnostics (
1067 IN EXTENDMEM_COVERAGE_LEVEL MemoryTestLevel
,
1068 IN BOOLEAN QuietBoot
1072 Routine Description:
1074 Perform the platform diagnostic, such like test memory. OEM/IBV also
1075 can customize this fuction to support specific platform diagnostic.
1079 MemoryTestLevel - The memory test intensive level
1081 QuietBoot - Indicate if need to enable the quiet boot
1092 // Here we can decide if we need to show
1093 // the diagnostics screen
1094 // Notes: this quiet boot code should be remove
1095 // from the graphic lib
1098 Status
= EnableQuietBoot (&gEfiDefaultBmpLogoGuid
);
1099 if (EFI_ERROR (Status
)) {
1100 DisableQuietBoot ();
1105 // Perform system diagnostic
1107 Status
= BdsMemoryTest (MemoryTestLevel
);
1108 if (EFI_ERROR (Status
)) {
1109 DisableQuietBoot ();
1115 // Perform system diagnostic
1117 Status
= BdsMemoryTest (MemoryTestLevel
);
1121 PlatformBdsPolicyBehavior (
1122 IN EFI_BDS_ARCH_PROTOCOL_INSTANCE
*PrivateData
,
1123 IN OUT LIST_ENTRY
*DriverOptionList
,
1124 IN OUT LIST_ENTRY
*BootOptionList
1128 Routine Description:
1130 The function will excute with as the platform policy, current policy
1131 is driven by boot mode. IBV/OEM can customize this code for their specific
1136 PrivateData - The EFI_BDS_ARCH_PROTOCOL_INSTANCE instance
1138 DriverOptionList - The header of the driver option link list
1140 BootOptionList - The header of the boot option link list
1150 EFI_EVENT UserInputDurationTime
;
1152 BDS_COMMON_OPTION
*BootOption
;
1158 // Init the time out value
1160 Timeout
= BdsLibGetTimeout ();
1163 // Load the driver option as the driver option list
1165 PlatformBdsGetDriverOption (DriverOptionList
);
1168 // Get current Boot Mode
1170 Status
= BdsLibGetBootMode (&PrivateData
->BootMode
);
1171 DEBUG ((EFI_D_ERROR
, "Boot Mode:%x\n", PrivateData
->BootMode
));
1174 // Go the different platform policy with different boot mode
1175 // Notes: this part code can be change with the table policy
1177 ASSERT (PrivateData
->BootMode
== BOOT_WITH_FULL_CONFIGURATION
);
1179 // Connect platform console
1181 Status
= PlatformBdsConnectConsole (gPlatformConsole
);
1182 if (EFI_ERROR (Status
)) {
1184 // Here OEM/IBV can customize with defined action
1186 PlatformBdsNoConsoleAction ();
1189 // Create a 300ms duration event to ensure user has enough input time to enter Setup
1191 Status
= gBS
->CreateEvent (
1196 &UserInputDurationTime
1198 ASSERT (Status
== EFI_SUCCESS
);
1199 Status
= gBS
->SetTimer (UserInputDurationTime
, TimerRelative
, 3000000);
1200 ASSERT (Status
== EFI_SUCCESS
);
1202 // Memory test and Logo show
1204 PlatformBdsDiagnostics (IGNORE
, TRUE
);
1207 // Perform some platform specific connect sequence
1209 PlatformBdsConnectSequence ();
1212 // Give one chance to enter the setup if we
1213 // have the time out
1216 PlatformBdsEnterFrontPage (Timeout
, FALSE
);
1220 //BdsLibConnectAll ();
1221 //BdsLibEnumerateAllBootOption (BootOptionList);
1224 // Please uncomment above ConnectAll and EnumerateAll code and remove following first boot
1225 // checking code in real production tip.
1227 // In BOOT_WITH_FULL_CONFIGURATION boot mode, should always connect every device
1228 // and do enumerate all the default boot options. But in development system board, the boot mode
1229 // cannot be BOOT_ASSUMING_NO_CONFIGURATION_CHANGES because the machine box
1230 // is always open. So the following code only do the ConnectAll and EnumerateAll at first boot.
1232 Status
= BdsLibBuildOptionFromVar (BootOptionList
, L
"BootOrder");
1233 if (EFI_ERROR(Status
)) {
1235 // If cannot find "BootOrder" variable, it may be first boot.
1236 // Try to connect all devices and enumerate all boot options here.
1238 BdsLibConnectAll ();
1239 BdsLibEnumerateAllBootOption (BootOptionList
);
1243 // To give the User a chance to enter Setup here, if user set TimeOut is 0.
1244 // BDS should still give user a chance to enter Setup
1246 // Connect first boot option, and then check user input before exit
1248 for (Link
= BootOptionList
->ForwardLink
; Link
!= BootOptionList
;Link
= Link
->ForwardLink
) {
1249 BootOption
= CR (Link
, BDS_COMMON_OPTION
, Link
, BDS_LOAD_OPTION_SIGNATURE
);
1250 if (!IS_LOAD_OPTION_TYPE (BootOption
->Attribute
, LOAD_OPTION_ACTIVE
)) {
1252 // skip the header of the link list, becuase it has no boot option
1257 // Make sure the boot option device path connected, but ignore the BBS device path
1259 if (DevicePathType (BootOption
->DevicePath
) != BBS_DEVICE_PATH
) {
1260 BdsLibConnectDevicePath (BootOption
->DevicePath
);
1267 // Check whether the user input after the duration time has expired
1269 OldTpl
= EfiGetCurrentTpl();
1270 gBS
->RestoreTPL (TPL_APPLICATION
);
1271 gBS
->WaitForEvent (1, &UserInputDurationTime
, &Index
);
1272 gBS
->CloseEvent (UserInputDurationTime
);
1273 Status
= gST
->ConIn
->ReadKeyStroke (gST
->ConIn
, &Key
);
1274 gBS
->RaiseTPL (OldTpl
);
1276 if (!EFI_ERROR (Status
)) {
1278 // Enter Setup if user input
1281 PlatformBdsEnterFrontPage (Timeout
, FALSE
);
1289 PlatformBdsBootSuccess (
1290 IN BDS_COMMON_OPTION
*Option
1294 Routine Description:
1296 Hook point after a boot attempt succeeds. We don't expect a boot option to
1297 return, so the EFI 1.0 specification defines that you will default to an
1298 interactive mode and stop processing the BootOrder list in this case. This
1299 is alos a platform implementation and can be customized by IBV/OEM.
1303 Option - Pointer to Boot Option that succeeded to boot.
1314 // If Boot returned with EFI_SUCCESS and there is not in the boot device
1315 // select loop then we need to pop up a UI and wait for user input.
1317 TmpStr
= Option
->StatusString
;
1318 if (TmpStr
!= NULL
) {
1319 BdsLibOutputStrings (gST
->ConOut
, TmpStr
, Option
->Description
, L
"\n\r", NULL
);
1320 gBS
->FreePool (TmpStr
);
1325 PlatformBdsBootFail (
1326 IN BDS_COMMON_OPTION
*Option
,
1327 IN EFI_STATUS Status
,
1328 IN CHAR16
*ExitData
,
1329 IN UINTN ExitDataSize
1333 Routine Description:
1335 Hook point after a boot attempt fails.
1339 Option - Pointer to Boot Option that failed to boot.
1341 Status - Status returned from failed boot.
1343 ExitData - Exit data returned from failed boot.
1345 ExitDataSize - Exit data size returned from failed boot.
1356 // If Boot returned with failed status then we need to pop up a UI and wait
1359 TmpStr
= Option
->StatusString
;
1360 if (TmpStr
!= NULL
) {
1361 BdsLibOutputStrings (gST
->ConOut
, TmpStr
, Option
->Description
, L
"\n\r", NULL
);
1362 gBS
->FreePool (TmpStr
);
1368 PlatformBdsNoConsoleAction (
1373 Routine Description:
1375 This function is remained for IBV/OEM to do some platform action,
1376 if there no console device can be connected.
1384 EFI_SUCCESS - Direct return success now.
1392 ConvertSystemTable (
1393 IN EFI_GUID
*TableGuid
,
1398 Routine Description:
1399 Convert ACPI Table /Smbios Table /MP Table if its location is lower than Address:0x100000
1401 As in legacy Bios, ACPI/Smbios/MP table is required to place in E/F Seg,
1402 So here we just check if the range is E/F seg,
1403 and if Not, assume the Memory type is EfiACPIReclaimMemory/EfiACPIMemoryNVS
1406 TableGuid - Guid of the table
1407 Table - pointer to the table
1410 EFI_SUCEESS - Convert Table successfully
1420 // If match acpi guid (1.0, 2.0, or later), Convert ACPI table according to version.
1422 AcpiHeader
= (VOID
*)(UINTN
)(*(UINT64
*)(*Table
));
1424 if (CompareGuid(TableGuid
, &gEfiAcpiTableGuid
) || CompareGuid(TableGuid
, &gEfiAcpi20TableGuid
)){
1425 if (((EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER
*)AcpiHeader
)->Reserved
== 0x00){
1427 // If Acpi 1.0 Table, then RSDP structure doesn't contain Length field, use structure size
1429 AcpiTableLen
= sizeof (EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER
);
1430 } else if (((EFI_ACPI_1_0_ROOT_SYSTEM_DESCRIPTION_POINTER
*)AcpiHeader
)->Reserved
>= 0x02){
1432 // If Acpi 2.0 or later, use RSDP Length fied.
1434 AcpiTableLen
= ((EFI_ACPI_2_0_ROOT_SYSTEM_DESCRIPTION_POINTER
*)AcpiHeader
)->Length
;
1437 // Invalid Acpi Version, return
1439 return EFI_UNSUPPORTED
;
1441 Status
= ConvertAcpiTable (AcpiTableLen
, Table
);
1446 // If matches smbios guid, convert Smbios table.
1448 if (CompareGuid(TableGuid
, &gEfiSmbiosTableGuid
)){
1449 Status
= ConvertSmbiosTable (Table
);
1454 // If the table is MP table?
1456 if (CompareGuid(TableGuid
, &gEfiMpsTableGuid
)){
1457 Status
= ConvertMpsTable (Table
);
1461 return EFI_UNSUPPORTED
;
1471 Routine Description:
1472 Caculate buffer checksum (8-bit)
1475 Buffer - Pointer to Buffer that to be caculated
1476 Length - How many bytes are to be caculated
1479 Checksum of the buffer
1487 Ptr8
= (UINT8
*) Buffer
;
1489 while (Length
> 0) {
1490 CheckSum
= (UINT8
) (CheckSum
+ *Ptr8
++);
1494 return ((0xFF - CheckSum
) + 1);
1504 Routine Description:
1505 Convert RSDP of ACPI Table if its location is lower than Address:0x100000
1507 As in legacy Bios, ACPI table is required to place in E/F Seg,
1508 So here we just check if the range is E/F seg,
1509 and if Not, assume the Memory type is EfiACPIReclaimMemory/EfiACPIMemoryNVS
1512 TableLen - Acpi RSDP length
1513 Table - pointer to the table
1516 EFI_SUCEESS - Convert Table successfully
1524 EFI_PHYSICAL_ADDRESS BufferPtr
;
1527 AcpiTableOri
= (VOID
*)(UINTN
)(*(UINT64
*)(*Table
));
1528 if (((UINTN
)AcpiTableOri
< 0x100000) && ((UINTN
)AcpiTableOri
> 0xE0000)) {
1529 BufferPtr
= EFI_SYSTEM_TABLE_MAX_ADDRESS
;
1530 Status
= gBS
->AllocatePages (
1533 EFI_SIZE_TO_PAGES(TableLen
),
1536 ASSERT_EFI_ERROR (Status
);
1537 AcpiTableNew
= (VOID
*)(UINTN
)BufferPtr
;
1538 CopyMem (AcpiTableNew
, AcpiTableOri
, TableLen
);
1540 AcpiTableNew
= AcpiTableOri
;
1543 // Change configuration table Pointer
1545 *Table
= AcpiTableNew
;
1551 ConvertSmbiosTable (
1556 Routine Description:
1558 Convert Smbios Table if the Location of the SMBios Table is lower than Addres 0x100000
1560 As in legacy Bios, Smbios table is required to place in E/F Seg,
1561 So here we just check if the range is F seg,
1562 and if Not, assume the Memory type is EfiACPIMemoryNVS/EfiRuntimeServicesData
1564 Table - pointer to the table
1567 EFI_SUCEESS - Convert Table successfully
1572 SMBIOS_TABLE_ENTRY_POINT
*SmbiosTableNew
;
1573 SMBIOS_TABLE_ENTRY_POINT
*SmbiosTableOri
;
1575 UINT32 SmbiosEntryLen
;
1577 EFI_PHYSICAL_ADDRESS BufferPtr
;
1579 SmbiosTableNew
= NULL
;
1580 SmbiosTableOri
= NULL
;
1583 // Get Smibos configuration Table
1585 SmbiosTableOri
= (SMBIOS_TABLE_ENTRY_POINT
*)(UINTN
)(*(UINT64
*)(*Table
));
1587 if ((SmbiosTableOri
== NULL
) ||
1588 ((UINTN
)SmbiosTableOri
> 0x100000) ||
1589 ((UINTN
)SmbiosTableOri
< 0xF0000)){
1593 // Relocate the Smibos memory
1595 BufferPtr
= EFI_SYSTEM_TABLE_MAX_ADDRESS
;
1596 if (SmbiosTableOri
->SmbiosBcdRevision
!= 0x21) {
1597 SmbiosEntryLen
= SmbiosTableOri
->EntryPointLength
;
1600 // According to Smbios Spec 2.4, we should set entry point length as 0x1F if version is 2.1
1602 SmbiosEntryLen
= 0x1F;
1604 BufferLen
= SmbiosEntryLen
+ SYS_TABLE_PAD(SmbiosEntryLen
) + SmbiosTableOri
->TableLength
;
1605 Status
= gBS
->AllocatePages (
1608 EFI_SIZE_TO_PAGES(BufferLen
),
1611 ASSERT_EFI_ERROR (Status
);
1612 SmbiosTableNew
= (SMBIOS_TABLE_ENTRY_POINT
*)(UINTN
)BufferPtr
;
1619 // Get Smbios Structure table address, and make sure the start address is 32-bit align
1621 BufferPtr
+= SmbiosEntryLen
+ SYS_TABLE_PAD(SmbiosEntryLen
);
1623 (VOID
*)(UINTN
)BufferPtr
,
1624 (VOID
*)(UINTN
)(SmbiosTableOri
->TableAddress
),
1625 SmbiosTableOri
->TableLength
1627 SmbiosTableNew
->TableAddress
= (UINT32
)BufferPtr
;
1628 SmbiosTableNew
->IntermediateChecksum
= 0;
1629 SmbiosTableNew
->IntermediateChecksum
=
1630 GetBufferCheckSum ((UINT8
*)SmbiosTableNew
+ 0x10, SmbiosEntryLen
-0x10);
1632 // Change the SMBIOS pointer
1634 *Table
= SmbiosTableNew
;
1645 Routine Description:
1647 Convert MP Table if the Location of the SMBios Table is lower than Addres 0x100000
1649 As in legacy Bios, MP table is required to place in E/F Seg,
1650 So here we just check if the range is E/F seg,
1651 and if Not, assume the Memory type is EfiACPIMemoryNVS/EfiRuntimeServicesData
1653 Table - pointer to the table
1656 EFI_SUCEESS - Convert Table successfully
1663 EFI_LEGACY_MP_TABLE_FLOATING_POINTER
*MpsFloatingPointerOri
;
1664 EFI_LEGACY_MP_TABLE_FLOATING_POINTER
*MpsFloatingPointerNew
;
1665 EFI_LEGACY_MP_TABLE_HEADER
*MpsTableOri
;
1666 EFI_LEGACY_MP_TABLE_HEADER
*MpsTableNew
;
1670 EFI_PHYSICAL_ADDRESS BufferPtr
;
1673 // Get MP configuration Table
1675 MpsFloatingPointerOri
= (EFI_LEGACY_MP_TABLE_FLOATING_POINTER
*)(UINTN
)(*(UINT64
*)(*Table
));
1676 if (!(((UINTN
)MpsFloatingPointerOri
<= 0x100000) &&
1677 ((UINTN
)MpsFloatingPointerOri
>= 0xF0000))){
1681 // Get Floating pointer structure length
1683 FPLength
= MpsFloatingPointerOri
->Length
* 16;
1684 Data32
= FPLength
+ SYS_TABLE_PAD (FPLength
);
1685 MpsTableOri
= (EFI_LEGACY_MP_TABLE_HEADER
*)(UINTN
)(MpsFloatingPointerOri
->PhysicalAddress
);
1686 if (MpsTableOri
!= NULL
) {
1687 Data32
+= MpsTableOri
->BaseTableLength
;
1688 Data32
+= MpsTableOri
->ExtendedTableLength
;
1689 if (MpsTableOri
->OemTablePointer
!= 0x00) {
1690 Data32
+= SYS_TABLE_PAD (Data32
);
1691 Data32
+= MpsTableOri
->OemTableSize
;
1699 BufferPtr
= EFI_SYSTEM_TABLE_MAX_ADDRESS
;
1700 Status
= gBS
->AllocatePages (
1703 EFI_SIZE_TO_PAGES(Data32
),
1706 ASSERT_EFI_ERROR (Status
);
1707 MpsFloatingPointerNew
= (EFI_LEGACY_MP_TABLE_FLOATING_POINTER
*)(UINTN
)BufferPtr
;
1708 CopyMem (MpsFloatingPointerNew
, MpsFloatingPointerOri
, FPLength
);
1710 // If Mp Table exists
1712 if (MpsTableOri
!= NULL
) {
1714 // Get Mps table length, including Ext table
1716 BufferPtr
= BufferPtr
+ FPLength
+ SYS_TABLE_PAD (FPLength
);
1717 MpsTableNew
= (EFI_LEGACY_MP_TABLE_HEADER
*)(UINTN
)BufferPtr
;
1718 CopyMem (MpsTableNew
, MpsTableOri
, MpsTableOri
->BaseTableLength
+ MpsTableOri
->ExtendedTableLength
);
1720 if ((MpsTableOri
->OemTableSize
!= 0x0000) && (MpsTableOri
->OemTablePointer
!= 0x0000)){
1721 BufferPtr
+= MpsTableOri
->BaseTableLength
+ MpsTableOri
->ExtendedTableLength
;
1722 BufferPtr
+= SYS_TABLE_PAD (BufferPtr
);
1723 OemTableNew
= (VOID
*)(UINTN
)BufferPtr
;
1724 OemTableOri
= (VOID
*)(UINTN
)MpsTableOri
->OemTablePointer
;
1725 CopyMem (OemTableNew
, OemTableOri
, MpsTableOri
->OemTableSize
);
1726 MpsTableNew
->OemTablePointer
= (UINT32
)(UINTN
)OemTableNew
;
1728 MpsTableNew
->Checksum
= 0;
1729 MpsTableNew
->Checksum
= GetBufferCheckSum (MpsTableNew
, MpsTableOri
->BaseTableLength
);
1730 MpsFloatingPointerNew
->PhysicalAddress
= (UINT32
)(UINTN
)MpsTableNew
;
1731 MpsFloatingPointerNew
->Checksum
= 0;
1732 MpsFloatingPointerNew
->Checksum
= GetBufferCheckSum (MpsFloatingPointerNew
, FPLength
);
1735 // Change the pointer
1737 *Table
= MpsFloatingPointerNew
;