+/**\r
+\r
+ Migrate Notify Pointers inside an FV from temporary memory to permanent memory.\r
+\r
+ @param PrivateData Pointer to PeiCore's private data structure.\r
+ @param OrgFvHandle Address of FV Handle in temporary memory.\r
+ @param FvHandle Address of FV Handle in permanent memory.\r
+ @param FvSize Size of the FV.\r
+\r
+**/\r
+VOID\r
+ConvertPpiPointersFv (\r
+ IN PEI_CORE_INSTANCE *PrivateData,\r
+ IN UINTN OrgFvHandle,\r
+ IN UINTN FvHandle,\r
+ IN UINTN FvSize\r
+ )\r
+{\r
+ UINT8 Index;\r
+ UINTN Offset;\r
+ BOOLEAN OffsetPositive;\r
+ EFI_PEI_FIRMWARE_VOLUME_INFO_PPI *FvInfoPpi;\r
+ UINT8 GuidIndex;\r
+ EFI_GUID *Guid;\r
+ EFI_GUID *GuidCheckList[2];\r
+\r
+ GuidCheckList[0] = &gEfiPeiFirmwareVolumeInfoPpiGuid;\r
+ GuidCheckList[1] = &gEfiPeiFirmwareVolumeInfo2PpiGuid;\r
+\r
+ if (FvHandle > OrgFvHandle) {\r
+ OffsetPositive = TRUE;\r
+ Offset = FvHandle - OrgFvHandle;\r
+ } else {\r
+ OffsetPositive = FALSE;\r
+ Offset = OrgFvHandle - FvHandle;\r
+ }\r
+\r
+ DEBUG ((DEBUG_VERBOSE, "Converting PPI pointers in FV.\n"));\r
+ DEBUG ((\r
+ DEBUG_VERBOSE,\r
+ " OrgFvHandle at 0x%08x. FvHandle at 0x%08x. FvSize = 0x%x\n",\r
+ (UINTN) OrgFvHandle,\r
+ (UINTN) FvHandle,\r
+ FvSize\r
+ ));\r
+ DEBUG ((\r
+ DEBUG_VERBOSE,\r
+ " OrgFvHandle range: 0x%08x - 0x%08x\n",\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize\r
+ ));\r
+\r
+ for (Index = 0; Index < PrivateData->PpiData.CallbackNotifyList.CurrentCount; Index++) {\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Raw,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Notify->Guid,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Notify->Notify,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ }\r
+\r
+ for (Index = 0; Index < PrivateData->PpiData.DispatchNotifyList.CurrentCount; Index++) {\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Raw,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Notify->Guid,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Notify->Notify,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ }\r
+\r
+ for (Index = 0; Index < PrivateData->PpiData.PpiList.CurrentCount; Index++) {\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.PpiList.PpiPtrs[Index].Raw,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.PpiList.PpiPtrs[Index].Ppi->Guid,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ ConvertPointer (\r
+ (VOID **) &PrivateData->PpiData.PpiList.PpiPtrs[Index].Ppi->Ppi,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+\r
+ Guid = PrivateData->PpiData.PpiList.PpiPtrs[Index].Ppi->Guid;\r
+ for (GuidIndex = 0; GuidIndex < ARRAY_SIZE (GuidCheckList); ++GuidIndex) {\r
+ //\r
+ // Don't use CompareGuid function here for performance reasons.\r
+ // Instead we compare the GUID as INT32 at a time and branch\r
+ // on the first failed comparison.\r
+ //\r
+ if ((((INT32 *)Guid)[0] == ((INT32 *)GuidCheckList[GuidIndex])[0]) &&\r
+ (((INT32 *)Guid)[1] == ((INT32 *)GuidCheckList[GuidIndex])[1]) &&\r
+ (((INT32 *)Guid)[2] == ((INT32 *)GuidCheckList[GuidIndex])[2]) &&\r
+ (((INT32 *)Guid)[3] == ((INT32 *)GuidCheckList[GuidIndex])[3])) {\r
+ FvInfoPpi = PrivateData->PpiData.PpiList.PpiPtrs[Index].Ppi->Ppi;\r
+ DEBUG ((DEBUG_VERBOSE, " FvInfo: %p -> ", FvInfoPpi->FvInfo));\r
+ if ((UINTN)FvInfoPpi->FvInfo == OrgFvHandle) {\r
+ ConvertPointer (\r
+ (VOID **)&FvInfoPpi->FvInfo,\r
+ OrgFvHandle,\r
+ OrgFvHandle + FvSize,\r
+ Offset,\r
+ OffsetPositive\r
+ );\r
+ DEBUG ((DEBUG_VERBOSE, "%p", FvInfoPpi->FvInfo));\r
+ }\r
+ DEBUG ((DEBUG_VERBOSE, "\n"));\r
+ break;\r
+ }\r
+ }\r
+ }\r
+}\r
+\r
+/**\r
+\r
+ Dumps the PPI lists to debug output.\r
+\r
+ @param PrivateData Points to PeiCore's private instance data.\r
+\r
+**/\r
+VOID\r
+DumpPpiList (\r
+ IN PEI_CORE_INSTANCE *PrivateData\r
+ )\r
+{\r
+ DEBUG_CODE_BEGIN ();\r
+ UINTN Index;\r
+\r
+ if (PrivateData == NULL) {\r
+ return;\r
+ }\r
+\r
+ for (Index = 0; Index < PrivateData->PpiData.CallbackNotifyList.CurrentCount; Index++) {\r
+ DEBUG ((\r
+ DEBUG_VERBOSE,\r
+ "CallbackNotify[%2d] {%g} at 0x%x (%a)\n",\r
+ Index,\r
+ PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Notify->Guid,\r
+ (UINTN) PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Raw,\r
+ (\r
+ !(\r
+ ((EFI_PHYSICAL_ADDRESS) (UINTN) PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Raw >= PrivateData->PhysicalMemoryBegin) &&\r
+ (((EFI_PHYSICAL_ADDRESS) ((UINTN) PrivateData->PpiData.CallbackNotifyList.NotifyPtrs[Index].Raw) + sizeof (EFI_PEI_NOTIFY_DESCRIPTOR)) < PrivateData->FreePhysicalMemoryTop)\r
+ )\r
+ ? "CAR" : "Post-Memory"\r
+ )\r
+ ));\r
+ }\r
+ for (Index = 0; Index < PrivateData->PpiData.DispatchNotifyList.CurrentCount; Index++) {\r
+ DEBUG ((DEBUG_VERBOSE,\r
+ "DispatchNotify[%2d] {%g} at 0x%x (%a)\n",\r
+ Index,\r
+ PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Notify->Guid,\r
+ (UINTN) PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Raw,\r
+ (\r
+ !(\r
+ ((EFI_PHYSICAL_ADDRESS) (UINTN) PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Raw >=PrivateData->PhysicalMemoryBegin) &&\r
+ (((EFI_PHYSICAL_ADDRESS) ((UINTN) PrivateData->PpiData.DispatchNotifyList.NotifyPtrs[Index].Raw) + sizeof (EFI_PEI_NOTIFY_DESCRIPTOR)) < PrivateData->FreePhysicalMemoryTop)\r
+ )\r
+ ? "CAR" : "Post-Memory"\r
+ )\r
+ ));\r
+ }\r
+ for (Index = 0; Index < PrivateData->PpiData.PpiList.CurrentCount; Index++) {\r
+ DEBUG ((DEBUG_VERBOSE,\r
+ "PPI[%2d] {%g} at 0x%x (%a)\n",\r
+ Index,\r
+ PrivateData->PpiData.PpiList.PpiPtrs[Index].Ppi->Guid,\r
+ (UINTN) PrivateData->PpiData.PpiList.PpiPtrs[Index].Raw,\r
+ (\r
+ !(\r
+ ((EFI_PHYSICAL_ADDRESS) (UINTN) PrivateData->PpiData.PpiList.PpiPtrs[Index].Raw >= PrivateData->PhysicalMemoryBegin) &&\r
+ (((EFI_PHYSICAL_ADDRESS) ((UINTN) PrivateData->PpiData.PpiList.PpiPtrs[Index].Raw) + sizeof (EFI_PEI_PPI_DESCRIPTOR)) < PrivateData->FreePhysicalMemoryTop)\r
+ )\r
+ ? "CAR" : "Post-Memory"\r
+ )\r
+ ));\r
+ }\r
+ DEBUG_CODE_END ();\r
+}\r
+\r