X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=SecurityPkg%2FTcg%2FOpal%2FOpalPasswordSmm%2FOpalPasswordSmm.c;h=0ea92b15c067720cee0c94bb5a05d186dac36e7d;hb=112e584ba0619695b7da3bb87604b3385ac2cb6d;hp=47b570f343424feb118126bfeba49db26865d53c;hpb=3f250a944d691d2169fa3834c89eed7235b735ae;p=mirror_edk2.git diff --git a/SecurityPkg/Tcg/Opal/OpalPasswordSmm/OpalPasswordSmm.c b/SecurityPkg/Tcg/Opal/OpalPasswordSmm/OpalPasswordSmm.c index 47b570f343..0ea92b15c0 100644 --- a/SecurityPkg/Tcg/Opal/OpalPasswordSmm/OpalPasswordSmm.c +++ b/SecurityPkg/Tcg/Opal/OpalPasswordSmm/OpalPasswordSmm.c @@ -61,9 +61,6 @@ VOID *mBuffer = NULL; // DMA can not read/write Data to smram, s // NVME NVME_CONTEXT mNvmeContext; -EFI_GCD_MEMORY_SPACE_DESCRIPTOR *mGcdMemSpace = NULL; -UINTN mNumberOfDescriptors = 0; - /** Add new bridge node or nvme device info to the device list. @@ -483,6 +480,53 @@ done: return Status; } +/** + The function extracts device information from OpalDeviceList and creat SmmDeviceList used for S3. + + @param[in] OpalDeviceList Opal device list created at POST which contains the information of OPAL_DISK_AND_PASSWORD_INFO + @param[in,out] SmmDeviceList Opal Smm device list to be created and used for unlocking devices at S3 resume. + + @retval EFI_SUCCESS Create SmmDeviceList successfully. + @retval Others Other execution results. +**/ +EFI_STATUS +CreateSmmDeviceList ( + IN LIST_ENTRY *OpalDeviceList, + IN OUT LIST_ENTRY *SmmDeviceList + ) +{ + LIST_ENTRY *Entry; + OPAL_DISK_AND_PASSWORD_INFO *PciDev; + OPAL_SMM_DEVICE *SmmDev; + + for (Entry = OpalDeviceList->ForwardLink; Entry != OpalDeviceList; Entry = Entry->ForwardLink) { + PciDev = BASE_CR (Entry, OPAL_DISK_AND_PASSWORD_INFO, Link); + + SmmDev = AllocateZeroPool (sizeof (OPAL_SMM_DEVICE)); + if (SmmDev == NULL) { + return EFI_OUT_OF_RESOURCES; + } + SmmDev->Signature = OPAL_SMM_DEVICE_SIGNATURE; + + ExtractDeviceInfoFromDevicePath(&PciDev->OpalDevicePath, SmmDev); + + SmmDev->PasswordLength = PciDev->PasswordLength; + CopyMem(&(SmmDev->Password), PciDev->Password, OPAL_PASSWORD_MAX_LENGTH); + + SmmDev->Sscp.ReceiveData = SecurityReceiveData; + SmmDev->Sscp.SendData = SecuritySendData; + + DEBUG ((DEBUG_INFO, "Opal SMM: Insert device node to SmmDeviceList:\n")); + DEBUG ((DEBUG_INFO, "DeviceType:%x, Bus:%d, Dev:%d, Fun:%d\n", \ + SmmDev->DeviceType, SmmDev->BusNum, SmmDev->DevNum, SmmDev->FuncNum)); + DEBUG ((DEBUG_INFO, "SataPort:%x, MultiplierPort:%x, NvmeNamespaceId:%x\n", \ + SmmDev->SataPort, SmmDev->SataPortMultiplierPort, SmmDev->NvmeNamespaceId)); + + InsertHeadList (SmmDeviceList, &SmmDev->Link); + } + + return EFI_SUCCESS; +} /** Main entry point for an SMM handler dispatch or communicate-based callback. @@ -521,7 +565,6 @@ S3SleepEntryCallBack ( UINT64 Address; S3_BOOT_SCRIPT_LIB_WIDTH Width; UINT32 Data; - OPAL_DISK_AND_PASSWORD_INFO *PciDev; OPAL_HC_PCI_REGISTER_SAVE *HcRegisterSaveListPtr; UINTN Count; OPAL_SMM_DEVICE *SmmDev; @@ -530,25 +573,28 @@ S3SleepEntryCallBack ( Status = EFI_SUCCESS; mOpalDeviceList = OpalSupportGetOpalDeviceList(); + if (IsListEmpty (mOpalDeviceList)) { + // + // No Opal enabled device. Do nothing. + // + return EFI_SUCCESS; + } - for (Entry = mOpalDeviceList->ForwardLink; Entry != mOpalDeviceList; Entry = Entry->ForwardLink) { - PciDev = BASE_CR (Entry, OPAL_DISK_AND_PASSWORD_INFO, Link); - - SmmDev = AllocateZeroPool (sizeof (OPAL_SMM_DEVICE)); - if (SmmDev == NULL) { - return EFI_OUT_OF_RESOURCES; + if (IsListEmpty (&mSmmDeviceList)) { + // + // mSmmDeviceList for S3 is empty, creat it by mOpalDeviceList. + // + Status = CreateSmmDeviceList (mOpalDeviceList, &mSmmDeviceList); + if (EFI_ERROR (Status)) { + return Status; } - SmmDev->Signature = OPAL_SMM_DEVICE_SIGNATURE; - - ExtractDeviceInfoFromDevicePath(&PciDev->OpalDevicePath, SmmDev); - - SmmDev->PasswordLength = PciDev->PasswordLength; - CopyMem(&(SmmDev->Password), PciDev->Password, OPAL_PASSWORD_MAX_LENGTH); - - SmmDev->Sscp.ReceiveData = SecurityReceiveData; - SmmDev->Sscp.SendData = SecuritySendData; + } - InsertHeadList (&mSmmDeviceList, &SmmDev->Link); + // + // Go through SmmDeviceList to save register data for S3 + // + for (Entry = mSmmDeviceList.ForwardLink; Entry != &mSmmDeviceList; Entry = Entry->ForwardLink) { + SmmDev = BASE_CR (Entry, OPAL_SMM_DEVICE, Link); if (SmmDev->DeviceType == OPAL_DEVICE_TYPE_NVME) { continue; @@ -592,52 +638,12 @@ S3SleepEntryCallBack ( } } - if (!IsListEmpty (mOpalDeviceList)) { - Status = S3BootScriptSaveIoWrite (S3BootScriptWidthUint8, 0xB2, 1, &mSwSmiValue); - ASSERT_EFI_ERROR (Status); - } + Status = S3BootScriptSaveIoWrite (S3BootScriptWidthUint8, 0xB2, 1, &mSwSmiValue); + ASSERT_EFI_ERROR (Status); return Status; } -/** - OpalPassword Notification for SMM EndOfDxe protocol. - - @param[in] Protocol Points to the protocol's unique identifier. - @param[in] Interface Points to the interface instance. - @param[in] Handle The handle on which the interface was installed. - - @retval EFI_SUCCESS Notification runs successfully. -**/ -EFI_STATUS -EFIAPI -OpalPasswordEndOfDxeNotification ( - IN CONST EFI_GUID *Protocol, - IN VOID *Interface, - IN EFI_HANDLE Handle - ) -{ - UINTN NumberOfDescriptors; - EFI_GCD_MEMORY_SPACE_DESCRIPTOR *MemSpaceMap; - EFI_STATUS Status; - - Status = gDS->GetMemorySpaceMap (&NumberOfDescriptors, &MemSpaceMap); - if (EFI_ERROR (Status)) { - return Status; - } - - mGcdMemSpace = AllocateCopyPool (NumberOfDescriptors * sizeof (EFI_GCD_MEMORY_SPACE_DESCRIPTOR), MemSpaceMap); - if (EFI_ERROR (Status)) { - gBS->FreePool (MemSpaceMap); - return Status; - } - - mNumberOfDescriptors = NumberOfDescriptors; - gBS->FreePool (MemSpaceMap); - - return EFI_SUCCESS; -} - /** Main entry for this driver. @@ -664,7 +670,6 @@ OpalPasswordSmmInit ( EFI_SMM_VARIABLE_PROTOCOL *SmmVariable; OPAL_EXTRA_INFO_VAR OpalExtraInfo; UINTN DataSize; - EFI_EVENT EndOfDxeEvent; EFI_PHYSICAL_ADDRESS Address; mBuffer = NULL; @@ -773,15 +778,6 @@ OpalPasswordSmmInit ( // mSwSmiValue = (UINT8) Context.SwSmiInputValue; - // - // Create event to record GCD descriptors at end of dxe for judging AHCI/NVMe PCI Bar - // is in MMIO space to avoid attack. - // - Status = gSmst->SmmRegisterProtocolNotify (&gEfiSmmEndOfDxeProtocolGuid, OpalPasswordEndOfDxeNotification, &EndOfDxeEvent); - if (EFI_ERROR (Status)) { - DEBUG((DEBUG_ERROR, "OpalPasswordSmm: Register SmmEndOfDxe fail, Status: %r\n", Status)); - goto EXIT; - } Status = gSmst->SmmLocateProtocol (&gEfiSmmVariableProtocolGuid, NULL, (VOID**)&SmmVariable); if (!EFI_ERROR (Status)) { DataSize = sizeof (OPAL_EXTRA_INFO_VAR);