123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537 |
- /** @file
- Implementation for iSCSI Boot Firmware Table publication.
- Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR>
- SPDX-License-Identifier: BSD-2-Clause-Patent
- **/
- #include "IScsiImpl.h"
- BOOLEAN mIbftInstalled = FALSE;
- UINTN mTableKey;
- /**
- Initialize the header of the iSCSI Boot Firmware Table.
- @param[out] Header The header of the iSCSI Boot Firmware Table.
- @param[in] OemId The OEM ID.
- @param[in] OemTableId The OEM table ID for the iBFT.
- **/
- VOID
- IScsiInitIbfTableHeader (
- OUT EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_HEADER *Header,
- IN UINT8 *OemId,
- IN UINT64 *OemTableId
- )
- {
- Header->Signature = EFI_ACPI_3_0_ISCSI_BOOT_FIRMWARE_TABLE_SIGNATURE;
- Header->Length = IBFT_HEAP_OFFSET;
- Header->Revision = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_REVISION;
- Header->Checksum = 0;
- CopyMem (Header->OemId, OemId, sizeof (Header->OemId));
- CopyMem (&Header->OemTableId, OemTableId, sizeof (UINT64));
- }
- /**
- Initialize the control section of the iSCSI Boot Firmware Table.
- @param[in] Table The ACPI table.
- **/
- VOID
- IScsiInitControlSection (
- IN EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_HEADER *Table
- )
- {
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *Control;
- UINTN NumOffset;
- Control = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *)(Table + 1);
- Control->Header.StructureId = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE_ID;
- Control->Header.Version = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE_VERSION;
- Control->Header.Length = (UINT16)sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE);
- //
- // If in multipathing mode, enable the Boot Failover Flag.
- // If in single path mode, disable it. Mix-model is not allowed.
- //
- // BUGBUG: if Boot Failover Flag is set to 1, the OS installer cannot
- // find the iSCSI mapped disk. So still keep not set for single path mode.
- //
- if (mPrivate->EnableMpio) {
- Control->Header.Flags = 0;
- NumOffset = 2 * (mPrivate->MpioCount - mPrivate->Krb5MpioCount);
- } else {
- NumOffset = 2 * mPrivate->ValidSinglePathCount;
- }
- //
- // Each attempt occupies two offsets: one for the NIC section;
- // the other for the Target section.
- //
- if (NumOffset > 4) {
- //
- // Need expand the control section if more than 2 NIC/Target attempts
- // exist.
- //
- Control->Header.Length = (UINT16)(Control->Header.Length + (NumOffset - 4) * sizeof (UINT16));
- }
- }
- /**
- Add one item into the heap.
- @param[in, out] Heap On input, the current address of the heap. On output, the address of
- the heap after the item is added.
- @param[in] Data The data to add into the heap.
- @param[in] Len Length of the Data in byte.
- **/
- VOID
- IScsiAddHeapItem (
- IN OUT UINT8 **Heap,
- IN VOID *Data,
- IN UINTN Len
- )
- {
- //
- // Add one byte for the NULL delimiter.
- //
- *Heap -= Len + 1;
- CopyMem (*Heap, Data, Len);
- *(*Heap + Len) = 0;
- }
- /**
- Fill the Initiator section of the iSCSI Boot Firmware Table.
- @param[in] Table The ACPI table.
- @param[in, out] Heap The heap.
- **/
- VOID
- IScsiFillInitiatorSection (
- IN EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_HEADER *Table,
- IN OUT UINT8 **Heap
- )
- {
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *Control;
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE *Initiator;
- Control = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *)(Table + 1);
- //
- // Initiator section immediately follows the control section.
- //
- Initiator = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE *)
- ((UINT8 *)Control + IBFT_ROUNDUP (Control->Header.Length));
- Control->InitiatorOffset = (UINT16)((UINTN)Initiator - (UINTN)Table);
- Initiator->Header.StructureId = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE_ID;
- Initiator->Header.Version = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE_VERSION;
- Initiator->Header.Length = (UINT16)sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE);
- Initiator->Header.Flags = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE_FLAG_BLOCK_VALID |
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE_FLAG_BOOT_SELECTED;
- //
- // Fill the iSCSI Initiator Name into the heap.
- //
- IScsiAddHeapItem (Heap, mPrivate->InitiatorName, mPrivate->InitiatorNameLength - 1);
- Initiator->IScsiNameLength = (UINT16)(mPrivate->InitiatorNameLength - 1);
- Initiator->IScsiNameOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- }
- /**
- Map the v4 IP address into v6 IP address.
- @param[in] V4 The v4 IP address.
- @param[out] V6 The v6 IP address.
- **/
- VOID
- IScsiMapV4ToV6Addr (
- IN EFI_IPv4_ADDRESS *V4,
- OUT EFI_IPv6_ADDRESS *V6
- )
- {
- UINTN Index;
- ZeroMem (V6, sizeof (EFI_IPv6_ADDRESS));
- V6->Addr[10] = 0xff;
- V6->Addr[11] = 0xff;
- for (Index = 0; Index < 4; Index++) {
- V6->Addr[12 + Index] = V4->Addr[Index];
- }
- }
- /**
- Fill the NIC and target sections in iSCSI Boot Firmware Table.
- @param[in] Table The buffer of the ACPI table.
- @param[in, out] Heap The heap buffer used to store the variable length
- parameters such as iSCSI name.
- **/
- VOID
- IScsiFillNICAndTargetSections (
- IN EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_HEADER *Table,
- IN OUT UINT8 **Heap
- )
- {
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *Control;
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE *Nic;
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE *Target;
- ISCSI_SESSION_CONFIG_NVDATA *NvData;
- ISCSI_CHAP_AUTH_CONFIG_NVDATA *AuthConfig;
- UINT16 *SectionOffset;
- UINTN Index;
- UINT16 Length;
- LIST_ENTRY *Entry;
- ISCSI_ATTEMPT_CONFIG_NVDATA *Attempt;
- ISCSI_NIC_INFO *NicInfo;
- BOOLEAN Flag;
- //
- // Get the offset of the first Nic and Target section.
- //
- Control = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_CONTROL_STRUCTURE *)(Table + 1);
- Nic = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE *)((UINTN)Table +
- Control->InitiatorOffset + IBFT_ROUNDUP (sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_INITIATOR_STRUCTURE)));
- Target = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE *)((UINTN)Nic +
- IBFT_ROUNDUP (sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE)));
- SectionOffset = &Control->NIC0Offset;
- Index = 0;
- Flag = TRUE;
- NET_LIST_FOR_EACH (Entry, &mPrivate->AttemptConfigs) {
- if (Index == 0) {
- //
- // First entry should be boot selected entry.
- //
- Attempt = IScsiConfigGetAttemptByConfigIndex (mPrivate->BootSelectedIndex);
- if (Attempt == NULL) {
- //
- // First boot selected entry can not be found.
- //
- break;
- }
- ASSERT (Attempt->SessionConfigData.Enabled != ISCSI_DISABLED);
- } else {
- if ((Index == 1) && Flag) {
- Entry = mPrivate->AttemptConfigs.ForwardLink;
- Flag = FALSE;
- }
- Attempt = NET_LIST_USER_STRUCT (Entry, ISCSI_ATTEMPT_CONFIG_NVDATA, Link);
- if (Attempt->AttemptConfigIndex == mPrivate->BootSelectedIndex) {
- continue;
- }
- }
- if (Attempt->SessionConfigData.Enabled == ISCSI_DISABLED) {
- continue;
- }
- //
- // Krb5 attempt will not be recorded in iBFT.
- //
- if (Attempt->AuthenticationType == ISCSI_AUTH_TYPE_KRB) {
- continue;
- }
- //
- // If multipath mode is enabled, only the attempts in MPIO will be recorded in iBFT.
- //
- if (mPrivate->EnableMpio && (Attempt->SessionConfigData.Enabled != ISCSI_ENABLED_FOR_MPIO)) {
- continue;
- }
- //
- // Only the valid attempts will be recorded.
- //
- if (!Attempt->ValidiBFTPath) {
- continue;
- }
- NvData = &Attempt->SessionConfigData;
- AuthConfig = &Attempt->AuthConfigData.CHAP;
- //
- // Fill the Nic section.
- //
- Nic->Header.StructureId = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE_ID;
- Nic->Header.Version = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE_VERSION;
- Nic->Header.Length = (UINT16)sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE);
- Nic->Header.Index = (UINT8)Index;
- Nic->Header.Flags = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE_FLAG_BLOCK_VALID |
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE_FLAG_GLOBAL;
- if (Index == 0) {
- Nic->Header.Flags |= EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE_FLAG_BOOT_SELECTED;
- }
- if (NvData->InitiatorInfoFromDhcp) {
- Nic->Origin = IpPrefixOriginDhcp;
- } else {
- Nic->Origin = IpPrefixOriginManual;
- }
- if ((NvData->IpMode == IP_MODE_IP4) || (NvData->IpMode == IP_MODE_AUTOCONFIG)) {
- //
- // Get the subnet mask prefix length.
- //
- Nic->SubnetMaskPrefixLength = IScsiGetSubnetMaskPrefixLength (&NvData->SubnetMask);
- //
- // Map the various v4 addresses into v6 addresses.
- //
- IScsiMapV4ToV6Addr (&NvData->LocalIp.v4, &Nic->Ip);
- IScsiMapV4ToV6Addr (&NvData->Gateway.v4, &Nic->Gateway);
- IScsiMapV4ToV6Addr (&Attempt->PrimaryDns.v4, &Nic->PrimaryDns);
- IScsiMapV4ToV6Addr (&Attempt->SecondaryDns.v4, &Nic->SecondaryDns);
- IScsiMapV4ToV6Addr (&Attempt->DhcpServer.v4, &Nic->DhcpServer);
- } else if ((NvData->IpMode == IP_MODE_IP6) || (NvData->IpMode == IP_MODE_AUTOCONFIG)) {
- Nic->SubnetMaskPrefixLength = NvData->PrefixLength;
- CopyMem (&Nic->Ip, &NvData->LocalIp, sizeof (EFI_IPv6_ADDRESS));
- CopyMem (&Nic->Gateway, &NvData->Gateway, sizeof (EFI_IPv6_ADDRESS));
- CopyMem (&Nic->PrimaryDns, &Attempt->PrimaryDns, sizeof (EFI_IPv6_ADDRESS));
- CopyMem (&Nic->SecondaryDns, &Attempt->SecondaryDns, sizeof (EFI_IPv6_ADDRESS));
- CopyMem (&Nic->DhcpServer, &Attempt->DhcpServer, sizeof (EFI_IPv6_ADDRESS));
- } else {
- ASSERT (FALSE);
- }
- //
- // Get Nic Info: VLAN tag, Mac address, PCI location.
- //
- NicInfo = IScsiGetNicInfoByIndex (Attempt->NicIndex);
- ASSERT (NicInfo != NULL);
- Nic->VLanTag = NicInfo->VlanId;
- CopyMem (Nic->Mac, &NicInfo->PermanentAddress, sizeof (Nic->Mac));
- Nic->PciLocation = (UINT16)((NicInfo->BusNumber << 8) |
- (NicInfo->DeviceNumber << 3) | NicInfo->FunctionNumber);
- *SectionOffset = (UINT16)((UINTN)Nic - (UINTN)Table);
- SectionOffset++;
- //
- // Fill the Target section.
- //
- Target->Header.StructureId = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_ID;
- Target->Header.Version = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_VERSION;
- Target->Header.Length = (UINT16)sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE);
- Target->Header.Index = (UINT8)Index;
- Target->Header.Flags = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_FLAG_BLOCK_VALID;
- if (Index == 0) {
- Target->Header.Flags |= EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_FLAG_BOOT_SELECTED;
- }
- Target->Port = NvData->TargetPort;
- if (Attempt->AuthenticationType == ISCSI_AUTH_TYPE_CHAP) {
- if (AuthConfig->CHAPType == ISCSI_CHAP_UNI) {
- Target->CHAPType = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_CHAP_TYPE_CHAP;
- } else if (AuthConfig->CHAPType == ISCSI_CHAP_MUTUAL) {
- Target->CHAPType = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_CHAP_TYPE_MUTUAL_CHAP;
- }
- } else if (Attempt->AuthenticationType == ISCSI_AUTH_TYPE_NONE) {
- Target->CHAPType = EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_CHAP_TYPE_NO_CHAP;
- }
- Target->NicIndex = (UINT8)Index;
- if ((NvData->IpMode == IP_MODE_IP4) || (NvData->IpMode == IP_MODE_AUTOCONFIG)) {
- IScsiMapV4ToV6Addr (&NvData->TargetIp.v4, &Target->Ip);
- } else if ((NvData->IpMode == IP_MODE_IP6) || (NvData->IpMode == IP_MODE_AUTOCONFIG)) {
- CopyMem (&Target->Ip, &NvData->TargetIp, sizeof (EFI_IPv6_ADDRESS));
- } else {
- ASSERT (FALSE);
- }
- CopyMem (Target->BootLun, NvData->BootLun, sizeof (Target->BootLun));
- //
- // Target iSCSI Name, CHAP name/secret, reverse CHAP name/secret.
- //
- Length = (UINT16)AsciiStrLen (NvData->TargetName);
- IScsiAddHeapItem (Heap, NvData->TargetName, Length);
- Target->IScsiNameLength = Length;
- Target->IScsiNameOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- if (Attempt->AuthenticationType == ISCSI_AUTH_TYPE_CHAP) {
- //
- // CHAP Name
- //
- Length = (UINT16)AsciiStrLen (AuthConfig->CHAPName);
- IScsiAddHeapItem (Heap, AuthConfig->CHAPName, Length);
- Target->CHAPNameLength = Length;
- Target->CHAPNameOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- //
- // CHAP Secret
- //
- Length = (UINT16)AsciiStrLen (AuthConfig->CHAPSecret);
- IScsiAddHeapItem (Heap, AuthConfig->CHAPSecret, Length);
- Target->CHAPSecretLength = Length;
- Target->CHAPSecretOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- if (Target->CHAPType == EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE_CHAP_TYPE_MUTUAL_CHAP) {
- //
- // Reverse CHAP Name.
- //
- Length = (UINT16)AsciiStrLen (AuthConfig->ReverseCHAPName);
- IScsiAddHeapItem (Heap, AuthConfig->ReverseCHAPName, Length);
- Target->ReverseCHAPNameLength = Length;
- Target->ReverseCHAPNameOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- //
- // Reverse CHAP Secret.
- //
- Length = (UINT16)AsciiStrLen (AuthConfig->ReverseCHAPSecret);
- IScsiAddHeapItem (Heap, AuthConfig->ReverseCHAPSecret, Length);
- Target->ReverseCHAPSecretLength = Length;
- Target->ReverseCHAPSecretOffset = (UINT16)((UINTN)*Heap - (UINTN)Table);
- }
- }
- *SectionOffset = (UINT16)((UINTN)Target - (UINTN)Table);
- SectionOffset++;
- //
- // Advance to the next NIC/Target pair.
- //
- Nic = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE *)((UINTN)Target +
- IBFT_ROUNDUP (sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE)));
- Target = (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_TARGET_STRUCTURE *)((UINTN)Nic +
- IBFT_ROUNDUP (sizeof (EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_NIC_STRUCTURE)));
- Index++;
- }
- }
- /**
- Publish and remove the iSCSI Boot Firmware Table according to the iSCSI
- session status.
- **/
- VOID
- IScsiPublishIbft (
- IN VOID
- )
- {
- EFI_STATUS Status;
- EFI_ACPI_TABLE_PROTOCOL *AcpiTableProtocol;
- EFI_ACPI_ISCSI_BOOT_FIRMWARE_TABLE_HEADER *Table;
- EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER *Rsdp;
- EFI_ACPI_DESCRIPTION_HEADER *Rsdt;
- EFI_ACPI_DESCRIPTION_HEADER *Xsdt;
- UINT8 *Heap;
- UINT8 Checksum;
- Rsdt = NULL;
- Xsdt = NULL;
- Status = gBS->LocateProtocol (&gEfiAcpiTableProtocolGuid, NULL, (VOID **)&AcpiTableProtocol);
- if (EFI_ERROR (Status)) {
- return;
- }
- //
- // Find ACPI table RSD_PTR from the system table.
- //
- Status = EfiGetSystemConfigurationTable (&gEfiAcpiTableGuid, (VOID **)&Rsdp);
- if (EFI_ERROR (Status)) {
- Status = EfiGetSystemConfigurationTable (&gEfiAcpi10TableGuid, (VOID **)&Rsdp);
- }
- if (EFI_ERROR (Status) || (Rsdp == NULL)) {
- return;
- } else if ((Rsdp->Revision >= EFI_ACPI_2_0_ROOT_SYSTEM_DESCRIPTION_POINTER_REVISION) && (Rsdp->XsdtAddress != 0)) {
- Xsdt = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)Rsdp->XsdtAddress;
- } else if (Rsdp->RsdtAddress != 0) {
- Rsdt = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)Rsdp->RsdtAddress;
- }
- if ((Xsdt == NULL) && (Rsdt == NULL)) {
- return;
- }
- if (mIbftInstalled) {
- Status = AcpiTableProtocol->UninstallAcpiTable (
- AcpiTableProtocol,
- mTableKey
- );
- if (EFI_ERROR (Status)) {
- return;
- }
- mIbftInstalled = FALSE;
- }
- //
- // If there is no valid attempt configuration, just return.
- //
- if ((!mPrivate->EnableMpio && (mPrivate->ValidSinglePathCount == 0)) ||
- (mPrivate->EnableMpio && (mPrivate->MpioCount <= mPrivate->Krb5MpioCount)))
- {
- return;
- }
- //
- // Allocate 4k bytes to hold the ACPI table.
- //
- Table = AllocateZeroPool (IBFT_MAX_SIZE);
- if (Table == NULL) {
- return;
- }
- Heap = (UINT8 *)Table + IBFT_HEAP_OFFSET;
- //
- // Fill in the various section of the iSCSI Boot Firmware Table.
- //
- if (Rsdp->Revision >= EFI_ACPI_2_0_ROOT_SYSTEM_DESCRIPTION_POINTER_REVISION) {
- IScsiInitIbfTableHeader (Table, Xsdt->OemId, &Xsdt->OemTableId);
- } else {
- IScsiInitIbfTableHeader (Table, Rsdt->OemId, &Rsdt->OemTableId);
- }
- IScsiInitControlSection (Table);
- IScsiFillInitiatorSection (Table, &Heap);
- IScsiFillNICAndTargetSections (Table, &Heap);
- Checksum = CalculateCheckSum8 ((UINT8 *)Table, Table->Length);
- Table->Checksum = Checksum;
- //
- // Install or update the iBFT table.
- //
- Status = AcpiTableProtocol->InstallAcpiTable (
- AcpiTableProtocol,
- Table,
- Table->Length,
- &mTableKey
- );
- if (EFI_ERROR (Status)) {
- return;
- }
- mIbftInstalled = TRUE;
- FreePool (Table);
- }
|