summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRegia König2021-06-21 15:40:13 +0200
committerRegia König2021-06-21 15:40:13 +0200
commit1451a5b95e40b8287474827cd781a0c3f7ffac47 (patch)
treef6f95e7ef8e8a2a3ad73a07c9ac0832a44180aad
parentAdd gitignore file (diff)
parentAdd gitignore file (diff)
downloadmemtest86-1451a5b95e40b8287474827cd781a0c3f7ffac47.tar.gz
memtest86-1451a5b95e40b8287474827cd781a0c3f7ffac47.tar.xz
memtest86-1451a5b95e40b8287474827cd781a0c3f7ffac47.zip
Merge master into page-allocation branch
-rw-r--r--efi_memtest/Makefile176
-rw-r--r--efi_memtest/MemtestEfi.c130
-rw-r--r--efi_memtest/README13
-rw-r--r--efi_memtest/logger_config.h21
-rw-r--r--efi_memtest/memtest86+/bios/dmi.c (renamed from efi_memtest/memtest86+/dmi.c)61
-rw-r--r--efi_memtest/memtest86+/config.c66
-rw-r--r--efi_memtest/memtest86+/controller.c382
-rw-r--r--efi_memtest/memtest86+/cpuid.c6
-rw-r--r--efi_memtest/memtest86+/efi/Include/AutoGen.c327
-rw-r--r--efi_memtest/memtest86+/efi/Include/Efi_Defs.c176
-rw-r--r--efi_memtest/memtest86+/efi/Include/Efi_Defs.h28
-rw-r--r--efi_memtest/memtest86+/efi/Include/Efi_Defs_GUID.h124
-rw-r--r--efi_memtest/memtest86+/efi/Include/Efi_Defs_Pcd.h13
-rw-r--r--efi_memtest/memtest86+/efi/Include/GccBase.lds4
-rw-r--r--efi_memtest/memtest86+/efi/Include/Guid/FileSystemInfo.h9
-rw-r--r--efi_memtest/memtest86+/efi/Include/Guid/GlobalVariable.h181
-rw-r--r--efi_memtest/memtest86+/efi/Include/Guid/HiiFormMapMethodGuid.h19
-rw-r--r--efi_memtest/memtest86+/efi/Include/Guid/PcAnsi.h52
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/BaseMemoryLib.h484
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/DebugPrintErrorLevelLib.h37
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/DevicePathLib.h561
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/MemoryAllocationLib.h487
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/PcdLib.h1736
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/PrintLib.h935
-rw-r--r--efi_memtest/memtest86+/efi/Include/Library/UefiRuntimeServicesTableLib.h26
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/DebugPort.h140
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/DevicePath.h1
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/DevicePathFromText.h66
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/DevicePathToText.h79
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/DevicePathUtilities.h186
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/GraphicsOutput.h5
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/HiiFont.h469
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/HiiImage.h353
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/LoadedImage.h79
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/SimpleFileSystem.h5
-rw-r--r--efi_memtest/memtest86+/efi/Include/Protocol/UgaDraw.h160
-rw-r--r--efi_memtest/memtest86+/efi/Include/Uefi/UefiInternalFormRepresentation.h2
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/BaseDebugPrintErrorLevelLib.libbin5178 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/BaseLib.libbin662358 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/BaseMemoryLib.libbin124112 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/BasePcdLibNull.libbin66314 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/BasePrintLib.libbin70804 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiApplicationEntryPoint.libbin23136 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiBootServicesTableLib.libbin23296 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiDebugLibStdErr.libbin56524 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiDevicePathLib.libbin343348 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiLib.libbin304102 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiMemoryAllocationLib.libbin43016 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/libs/UefiRuntimeServicesTableLib.libbin22494 -> 0 bytes
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/ApplicationEntryPoint.c115
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseDebugPrintErrorLevelLib.c55
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/ARShiftU64.c35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/BaseLibInternals.h869
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/BitField.c1002
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/CheckSum.c626
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/ChkStkGcc.c18
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/Cpu.c59
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/CpuDeadLoop.c34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/DivS64x64Remainder.c47
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32.c39
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32Remainder.c43
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x64Remainder.c43
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/FilePaths.c115
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo32.c38
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo64.c38
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet32.c41
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet64.c49
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU32.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU64.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LShiftU64.c35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LinkedList.c599
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LongJump.c41
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet32.c41
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet64.c44
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/Math64.c362
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/ModU64x32.c39
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/MultS64x64.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x32.c40
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x64.c40
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU32.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU64.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/RShiftU64.c35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SafeString.c3535
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SetJump.c34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/String.c1644
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes16.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes32.c39
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes64.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/SwitchStack.c70
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/Unaligned.c216
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.c140
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.h66
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.nasm31
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuId.nasm58
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuIdEx.nasm60
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuPause.nasm31
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableCache.nasm37
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableInterrupts.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisablePaging64.nasm78
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableCache.nasm37
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableDisableInterrupts.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableInterrupts.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FlushCacheLine.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxRestore.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxSave.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInline.c562
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInlinePriv.c1234
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Invd.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Lfence.nasm31
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/LongJump.nasm77
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Monitor.nasm37
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Mwait.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Non-existing.c147
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/RdRand.nasm77
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr0.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr2.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr3.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr4.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr0.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr1.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr2.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr3.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr4.nasm36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr5.nasm36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr6.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr7.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEflags.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadFs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGdtr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadIdtr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadLdtr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm0.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm1.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm2.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm3.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm4.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm5.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm6.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm7.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.nasm34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadPmc.nasm34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadSs.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTsc.nasm34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SetJump.nasm81
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SwitchStack.nasm45
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Thunk16.nasm319
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/VmgExit.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Wbinvd.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr0.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr2.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr3.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr4.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr0.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr1.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr2.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr3.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr4.nasm37
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr5.nasm37
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr6.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr7.nasm33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteGdtr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteIdtr.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteLdtr.nasm32
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm0.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm1.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm2.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm3.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm4.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm5.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm6.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm7.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.c36
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.nasm35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteTr.nasm31
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/XGetBv.nasm34
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging32.c60
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging64.c57
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging32.c63
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging64.c59
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxRestore.c43
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxSave.c42
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86GetInterruptState.c35
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86MemoryFence.c26
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Msr.c654
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86PatchInstruction.c83
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86RdRand.c73
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadGdtr.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadIdtr.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86SpeculationBarrier.c30
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Thunk.c262
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86UnitTestHost.c2977
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteGdtr.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteIdtr.c33
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CompareMemWrapper.c60
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMem.c148
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMemWrapper.c57
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/IsZeroBufferWrapper.c48
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGeneric.c287
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGuid.c165
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibInternals.h245
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem16Wrapper.c61
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem32Wrapper.c60
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem64Wrapper.c61
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem8Wrapper.c93
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem.c81
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem16Wrapper.c58
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem32Wrapper.c58
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem64Wrapper.c58
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMemWrapper.c85
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ZeroMemWrapper.c50
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLib.c837
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.c1274
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.h271
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/MemoryAllocationLib.c815
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/PcdLib.c1113
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiBootServicesTableLib.c60
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLib.c377
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLibConstructor.c99
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathFromText.c3666
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathToText.c2455
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilities.c865
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesDxeSmm.c51
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesStandaloneMm.c40
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.c354
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.h451
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLibOptionalDevicePathProtocol.c478
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/Acpi.c421
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/Console.c566
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiDriverModel.c2021
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLib.c1921
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibInternal.h38
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibPrint.c817
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiNotTiano.c330
-rw-r--r--efi_memtest/memtest86+/efi/Include/src/UefiRuntimeServicesTableLib.c43
-rw-r--r--efi_memtest/memtest86+/efi/display.c291
-rw-r--r--efi_memtest/memtest86+/efi/dmi.c630
-rw-r--r--efi_memtest/memtest86+/efi/init.c929
-rw-r--r--efi_memtest/memtest86+/efi/logger.c42
-rw-r--r--efi_memtest/memtest86+/efi/memory_tables.c17
-rw-r--r--efi_memtest/memtest86+/efi/test.c131
-rw-r--r--efi_memtest/memtest86+/error.c21
-rw-r--r--efi_memtest/memtest86+/logger.h2
-rw-r--r--efi_memtest/memtest86+/main.c77
-rw-r--r--efi_memtest/memtest86+/memsize.c103
-rw-r--r--efi_memtest/memtest86+/pci.c51
-rw-r--r--efi_memtest/todo8
-rw-r--r--save/Efi_Defs.c168
-rw-r--r--save/Efi_Defs.h30
-rw-r--r--save/Efi_Defs_GUID.h (renamed from efi_memtest/memtest86+/efi/Include/AutoGen.h)44
-rw-r--r--save/Efi_Defs_Pcd.h120
-rw-r--r--test_code/hda-contents/MemtestEfi.efibin69440 -> 0 bytes
-rw-r--r--test_code/hdb-contents/MemtestEfi.efibin9344 -> 0 bytes
-rw-r--r--test_code/hdb-contents/memtest_log1
-rw-r--r--test_code/old_logs/memtest_log_01_Jun_21146
-rwxr-xr-xtest_code/run.sh19
262 files changed, 50460 insertions, 1514 deletions
diff --git a/efi_memtest/Makefile b/efi_memtest/Makefile
index 883bf3e..5a3a9ed 100644
--- a/efi_memtest/Makefile
+++ b/efi_memtest/Makefile
@@ -1,20 +1,32 @@
-# TODO Autogen.obj
-# Difference *.o *.obj
-
-
-
-MAIN_FILE=MemtestEfi
-
-CC=gcc
-
-CFLAGS= -Werror -Wall -fno-builtin -fshort-wchar -fno-common -fno-strict-aliasing -g \
- -Wno-array-bounds -fno-stack-protector -Wno-address -mno-red-zone \
- -fpie -ffunction-sections -fdata-sections -flto -maccumulate-outgoing-args \
- -fno-asynchronous-unwind-tables -nostdlib -fPIC
-
-LINKER=
-
-M64=-m64 -mcmodel=small
+MAIN_FILE = MemtestEfi
+
+CC = gcc
+
+# Warnings
+CFLAGS = -Werror -Wall -Wno-array-bounds -Wno-address
+CFLAGS += -fno-builtin
+# EFI requires -fshort-wchar
+CFLAGS += -fshort-wchar
+CFLAGS += -fno-common
+CFLAGS += -fno-strict-aliasing -g
+# EFI uses Microsoft ABI so no red zone is defined
+CFLAGS += -mno-red-zone
+
+# use %rip-relative addressing wherever possible?? Or not?
+CFLAGS += -fpie
+#CFLAGS += -fno-pie -no-pie -static
+
+CFLAGS += -fPIC
+CFLAGS += -ffunction-sections
+CFLAGS += -fdata-sections
+CFLAGS += -flto
+CFLAGS += -maccumulate-outgoing-args
+CFLAGS += -fno-asynchronous-unwind-tables
+CFLAGS += -nostdlib
+CFLAGS += -mcmodel=small
+#CFLAGS += -fno-stack-protector e
+
+M64=-m64
M32=-m32
@@ -23,31 +35,33 @@ M=$(M64)
PREPROCESSOR=-DUEFI -DUSING_LTO -Os \
-D DISABLE_NEW_DEPRECATED_INTERFACES "-DEFIAPI=__attribute__((ms_abi))"
-INCLUDE_FILES=main cpuid test smp config screen_buffer lib init controller pci \
- spd dmi reloc patn error vmem memsize random logger memory_tables
-
-ADDITIONAL_HEADER=$(addprefix memtest86+/, defs.h efi/stdin.h io.h \
- stdint.h stddef.h serial.h msr.h jedec_id.h elf.h efi/main_asm.h)
-
-OBJS=AutoGen.obj main.o display.o test.o smp.o config.o screen_buffer.o lib.o init.o controller.o \
+OBJS=Efi_Defs.obj main.o display.o test.o smp.o config.o screen_buffer.o lib.o init.o controller.o \
pci.o spd.o dmi.o reloc.o patn.o error.o vmem.o cpuid.o memsize.o \
- random.o MemtestEfi.obj logger.o memory_tables.o page_allocator.o
+ random.o logger.o memory_tables.o BaseLib.o BaseMemoryLib.o BasePrintLib.o \
+ UefiDebugLibStdErr.o UefiDevicePathLib2.o UefiLib2.o ApplicationEntryPoint.o \
+ BaseDebugPrintErrorLevelLib.o UefiMemoryAllocationLib.o BasePcdLibNull.o \
+ UefiRuntimeServicesTableLib.o UefiBootServicesTableLib.o MemtestEfi.obj
+
-LIBS_PATH=memtest86+/efi/Include/libs
+BaseMemoryLib_OBJS=CompareMemWrapper.o CopyMem.o CopyMemWrapper.o IsZeroBufferWrapper.o \
+ MemLibGeneric.o MemLibGuid.o ScanMem16Wrapper.o ScanMem32Wrapper.o ScanMem64Wrapper.o \
+ ScanMem8Wrapper.o SetMem.o SetMem16Wrapper.o SetMem32Wrapper.o SetMem64Wrapper.o \
+ SetMemWrapper.o ZeroMemWrapper.o
-LIBRARIES=OUTPUT/MemtestEfi.lib $(addprefix $(LIBS_PATH)/, BaseDebugPrintErrorLevelLib.lib \
- BaseLib.lib BaseMemoryLib.lib BasePcdLibNull.lib BasePrintLib.lib UefiApplicationEntryPoint.lib \
- UefiBootServicesTableLib.lib UefiDebugLibStdErr.lib UefiDevicePathLib.lib UefiLib.lib \
- UefiMemoryAllocationLib.lib UefiRuntimeServicesTableLib.lib)
+UefiDevicePathLib_OBJS=DevicePathFromText.o DevicePathToText.o DevicePathUtilities.o \
+ DevicePathUtilitiesDxeSmm.o DevicePathUtilitiesStandaloneMm.o UefiDevicePathLib.o \
+ UefiDevicePathLibOptionalDevicePathProtocol.o
+BaseLib_OBJS=ARShiftU64.o BitField.o CheckSum.o CpuDeadLoop.o Cpu.o DivU64x64Remainder.o \
+ DivU64x32Remainder.o DivU64x32.o DivS64x64Remainder.o FilePaths.o GetPowerOfTwo64.o \
+ GetPowerOfTwo32.o HighBitSet64.o HighBitSet32.o LongJump.o LRotU64.o LowBitSet64.o \
+ LowBitSet32.o LRotU32.o LShiftU64.o Math64.o ModU64x32.o MultU64x64.o MultU64x32.o MultS64x64.o \
+ RRotU32.o RRotU64.o RShiftU64.o SafeString.o String.o SetJump.o SwapBytes64.o SwapBytes32.o \
+ SwapBytes16.o SwitchStack.o Unaligned.o
+
-# STATIC_LIBRARY_FILES= libs/BaseLib.lib
-# libs/BaseMemoryLib.lib libs/BasePcdLibNull.lib
-# libs/BaseDebugPrintErrorLevelLib.lib libs/BasePrintLib.lib
-# libs/UefiDebugLibStdErr.lib libs/UefiBootServicesTableLib.lib
-# libs/UefiMemoryAllocationLib.lib libs/UefiRuntimeServicesTableLib.lib
-# libs/UefiDevicePathLib.lib libs/UefiApplicationEntryPoint.lib libs/UefiLib.lib
+LIBRARIES=OUTPUT/MemtestEfi.lib
all: clean MemtestEfi.efi move run
@@ -57,7 +71,7 @@ $(MAIN_FILE).efi: $(MAIN_FILE).dll
$(MAIN_FILE).dll: $(MAIN_FILE).lib
- $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -o $(MAIN_FILE).dll \
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) $(LIBRARIES) -o $(MAIN_FILE).dll \
-nostdlib \
-Wl,-n,-q,--gc-sections \
-Wl,--entry,_ModuleEntryPoint \
@@ -67,41 +81,97 @@ $(MAIN_FILE).dll: $(MAIN_FILE).lib
-Wl,--script=memtest86+/efi/Include/GccBase.lds \
-z common-page-size=0x40 \
-u _ModuleEntryPoint \
- -DSTRING_ARRAY_NAME=${MAIN_FILE}Strings \
- $(LIBRARIES)
+ -DSTRING_ARRAY_NAME=${MAIN_FILE}Strings
objcopy --strip-unneeded -R .eh_frame -v $(MAIN_FILE).dll $(MAIN_FILE).dll
- strip -R .strtab MemtestEfi.dll
-
-
-# -Wl,--start-group,@static_library_files.lst,--end-group \
+ strip -R .strtab MemtestEfi.dll
$(MAIN_FILE).lib: $(OBJS)
- gcc-ar crv OUTPUT/$(MAIN_FILE).lib $(OBJS)
+ gcc-ar crv OUTPUT/$(MAIN_FILE).lib $^
+ #rm $^
$(MAIN_FILE).obj: $(MAIN_FILE).c
$(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -o $(MAIN_FILE).obj \
-MMD -MF OUTPUT/$(MAIN_FILE).obj.deps \
-c \
- -include memtest86+/efi/Include/AutoGen.h \
+ -include memtest86+/efi/Include/Efi_Defs.h \
-DSTRING_ARRAY_NAME=${MAIN_FILE}Strings \
-I . \
-I"memtest86+" \
-I"memtest86+/efi/Include" \
$(MAIN_FILE).c
-AutoGen.obj: memtest86+/efi/Include/AutoGen.c
- $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -o AutoGen.obj \
+Efi_Defs.obj: memtest86+/efi/Include/Efi_Defs.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -o $@ $< \
-c \
- -I"./" \
- -I"memtest86+/efi/Include/" \
- -I"memtest86+/efi/Include/Uefi" \
- -I"memtest86+/efi/Include/Library" \
- memtest86+/efi/Include/AutoGen.c
+ -I"memtest86+/efi/Include"
%.o: memtest86+/%.c
$(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
-I"memtest86+/efi"
+%.o: memtest86+/efi/Include/src/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include" \
+ -I"memtest86+/efi/Include/Library"
+
+%.o: memtest86+/efi/Include/src/UefiLib/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include" \
+ -I"memtest86+/efi/Include/Protocol" \
+ -I"memtest86+/efi/Include/Guid"
+
+BasePcdLibNull.o: memtest86+/efi/Include/src/PcdLib.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+UefiMemoryAllocationLib.o: memtest86+/efi/Include/src/MemoryAllocationLib.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+UefiLib2.o: Acpi.o Console.o UefiDriverModel.o UefiLib.o UefiLibPrint.o UefiNotTiano.o
+ ld -r -o $@ $^
+ rm $^
+
+%.o: memtest86+/efi/Include/src/UefiDebugLibStdErr/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+UefiDebugLibStdErr.o: DebugLib.o DebugLibConstructor.o
+ ld -r -o $@ $^
+ rm $^
+
+%.o: memtest86+/efi/Include/src/BaseMemoryLib/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+BaseMemoryLib.o: $(BaseMemoryLib_OBJS)
+ ld -r -o $@ $^
+ rm $^
+
+%.o: memtest86+/efi/Include/src/BasePrintLib/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+BasePrintLib.o: PrintLib.o PrintLibInternal.o
+ ld -r -o $@ $^
+ rm $^
+
+%.o: memtest86+/efi/Include/src/UefiDevicePathLib/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+UefiDevicePathLib2.o: $(UefiDevicePathLib_OBJS)
+ ld -r -o $@ $^
+ rm $^
+
+%.o: memtest86+/efi/Include/src/BaseLib/%.c
+ $(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
+ -I"memtest86+/efi/Include"
+
+BaseLib.o: $(BaseLib_OBJS)
+ ld -r -o $@ $^
+ rm $^
+
%.o: memtest86+/efi/%.c
$(CC) $(CFLAGS) $(PREPROCESSOR) $(M) -c -o $@ $< \
-I"memtest86+" \
@@ -117,7 +187,7 @@ clean:
rm -f MemtestEfi.dll
rm -f MemtestEfi.efi
rm -f MemtestEfi.txt
- rm -f AutoGen.obj
+ rm -f Efi_Defs.obj
move:
diff --git a/efi_memtest/MemtestEfi.c b/efi_memtest/MemtestEfi.c
index b0511a5..0d2d472 100644
--- a/efi_memtest/MemtestEfi.c
+++ b/efi_memtest/MemtestEfi.c
@@ -3,58 +3,124 @@
#include "Library/UefiLib.h"
#include "Library/UefiApplicationEntryPoint.h"
#include "Guid/FileSystemInfo.h"
+#include "Protocol/LoadedImage.h"
#include "main.h" // TODO move into main dir
#include "memtest86+/logger.h"
#include "memtest86+/display.h"
+#include "logger_config.h"
extern EFI_SYSTEM_TABLE *gST;
-short logflag = 1;
-short log_fine = 0;
-short log_memspeed = 0;
-short log_mem_tbl = 1;
-short log_comp_seg = 0;
-short log_print_pmap = 0;
+// TODO remove
+int global = 1;
+
+void stack_check() {
+ int i;
+ int *p = &i;
+ char log[32] = "stack ptr = ";
+ int length = 12;
+ int_to_charr((unsigned long) p, log, &length);
+ print_log(log, length);
+}
EFI_STATUS
EFIAPI
UefiMain (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- )
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
{
- SystemTable->ConOut->ClearScreen(SystemTable->ConOut);
- SystemTable->ConOut->SetCursorPosition(SystemTable->ConOut, 0, 0);
-
- trace_init("Starting MemtestEfi");
-
+ SystemTable->ConOut->ClearScreen(SystemTable->ConOut);
+ SystemTable->ConOut->SetCursorPosition(SystemTable->ConOut, 0, 0);
- //SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Hello World!!\n");
+ trace_init("Starting MemtestEfi");
- init_logger();
-
- //while(1);
-
-
- if (logflag) {
- char msg[] = "MemtestEfi started";
- print_log(msg, sizeof(msg) - 1);
- }
+ init_logger();
+
+ if (logflag) {
+ char msg[] = "MemtestEfi started";
+ print_log(msg, sizeof(msg) - 1);
+ }
- test_start();
+ if (logflag) {
+ char log[41] = "Address of UefiMain: ";
+ int length = 21;
+ int_to_charr((unsigned long)UefiMain, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag) {
+ char log[43] = "Address of test_start: ";
+ int length = 23;
+ int_to_charr((unsigned long)test_start, log, &length);
+ print_log(log, length);
+ }
+
+ VOID *LoadedImage;
+ EFI_STATUS status = SystemTable->BootServices->OpenProtocol(
+ ImageHandle,
+ &gEfiLoadedImageProtocolGuid,
+ &LoadedImage,
+ ImageHandle,
+ NULL,
+ EFI_OPEN_PROTOCOL_GET_PROTOCOL);
+ if (status != EFI_SUCCESS) {
+ if (logflag) print_log("Failed to open LoadedImage.", 27);
+ } else {
+ VOID *base = ((EFI_LOADED_IMAGE_PROTOCOL *) LoadedImage)->ImageBase;
+ UINT64 size = ((EFI_LOADED_IMAGE_PROTOCOL *) LoadedImage)->ImageSize;
+ if (logflag) {
+ char log[31] = "ImageBase: ";
+ int length = 11;
+ int_to_charr((unsigned long) base, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag) {
+ char log[31] = "ImageSize: ";
+ int length = 11;
+ int_to_charr(size, log, &length);
+ print_log(log, length);
+ }
+ }
+
+ if (logflag) {
+ char log[45] = "Address of SystemTable = ";
+ int length = 25;
+ int_to_charr((unsigned long) SystemTable, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag) {
+ char log[45] = "Current return address = ";
+ int length = 25;
+ int_to_charr((unsigned long) ((unsigned long *) __builtin_return_address(0)), log, &length);
+ print_log(log, length);
+ }
+
+ stack_check();
+
+ if (logflag) {
+ char log[49] = "Address of global variable = ";
+ int length = 29;
+ int_to_charr((unsigned long) &global, log, &length);
+ print_log(log, length);
+ }
+
+ test_start();
- if (logflag) {
- char msg[] = "MemtestEfi finished!\n";
- print_log(msg, sizeof(msg) - 1);
- }
+ if (logflag) {
+ char msg[] = "MemtestEfi finished!\n";
+ print_log(msg, sizeof(msg) - 1);
+ }
- // while(1) {}
+ //while(1) {}
- SystemTable->ConOut->SetCursorPosition(SystemTable->ConOut, 0, 25);
+ SystemTable->ConOut->SetCursorPosition(SystemTable->ConOut, 0, 25);
- return EFI_SUCCESS;
+ return EFI_SUCCESS;
}
diff --git a/efi_memtest/README b/efi_memtest/README
new file mode 100644
index 0000000..d501aac
--- /dev/null
+++ b/efi_memtest/README
@@ -0,0 +1,13 @@
+README
+
+
+DEPENDENCIES
+
+
+
+HOW TO INSTALL
+-- sudo make
+
+
+HOW TO RUN
+-- sudo make run \ No newline at end of file
diff --git a/efi_memtest/logger_config.h b/efi_memtest/logger_config.h
new file mode 100644
index 0000000..26143b0
--- /dev/null
+++ b/efi_memtest/logger_config.h
@@ -0,0 +1,21 @@
+// General
+short logflag = 1;
+short log_fine = 0;
+
+// Timing
+short log_cpuspeed = 0;
+short log_memspeed = 0;
+
+// Memory
+short log_mem_tbl = 1;
+short log_comp_seg = 0;
+short log_print_pmap = 1;
+short log_pmap = 1;
+
+// Hardware Information
+short log_mem_ctrl = 0;
+short log_pci_conf = 0;
+short log_dmi = 0;
+
+// Tests
+short log_tst2 = 1; \ No newline at end of file
diff --git a/efi_memtest/memtest86+/dmi.c b/efi_memtest/memtest86+/bios/dmi.c
index 066e2ce..688d067 100644
--- a/efi_memtest/memtest86+/dmi.c
+++ b/efi_memtest/memtest86+/bios/dmi.c
@@ -8,13 +8,22 @@
* Memtest86+ V4.00 - Added compliance with SMBIOS Spec V2.6.1
*/
+#include "Uefi.h"
+#include "Library/UefiLib.h"
+
+extern EFI_SYSTEM_TABLE *gST;
#include "test.h"
#include "stdint.h"
+#include "logger.h"
+
#define round_up(x,y) (((x) + (y) - 1) & ~((y)-1))
#define round_down(x,y) ((x) & ~((y)-1))
+extern short logflag;
+extern short log_mem_ctrl;
+
struct dmi_eps {
uint8_t anchor[4];
int8_t checksum;
@@ -164,8 +173,11 @@ char * get_tstruct_string(struct tstruct_header *header, int n){
return 0;
}
+int open_dmi(void) {
+
+}
-int open_dmi(void){
+/*int open_dmi(void){
char *dmi, *dmi_search_start, *dmi_start;
int found=0;
struct dmi_eps *eps;
@@ -184,6 +196,7 @@ int open_dmi(void){
}
}
if (!found) {
+ print_log("open_dmi(): dmi not found", 25);
return -1;
}
dmi_start=dmi;
@@ -238,9 +251,12 @@ int open_dmi(void){
return -1;
}
return 0;
-}
+}*/
void init_dmi(void){
+
+ if (logflag) print_log("init_dmi() started", 18);
+
int i;
for(i=0; i < MAX_DMI_MEMDEVS; i++)
dmi_err_cnts[i]=0;
@@ -250,11 +266,14 @@ void init_dmi(void){
void print_dmi_startup_info(void)
{
+
+ if (logflag) print_log("print_dmi_startup_info() started", 32);
+
char *string1;
char *string2;
char *string3;
int dmicol = 78;
- int slenght;
+ int slength;
int sl1, sl2, sl3;
if(!dmi_initialized) { init_dmi(); }
@@ -266,13 +285,41 @@ void print_dmi_startup_info(void)
string3 = get_tstruct_string(&dmi_cpu_info->header,dmi_cpu_info->cpu_socket);
sl3 = mt86_strlen(string3);
- slenght = sl1 + sl2;
- if(sl3 > 2) { slenght += sl3 + 4; } else { slenght++; }
+ if (logflag && log_mem_ctrl) {
+ char log[61] = "print_dmi_startup_info(): manufacturer = ";
+ int length = 41;
+ string_to_charr(string1, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[16] = "sl1 = ";
+ int length = 6;
+ int_to_charr(sl1, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[60] = "print_dmi_startup_info(): productname = ";
+ int length = 40;
+ string_to_charr(string2, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[59] = "print_dmi_startup_info(): cpu_socket = ";
+ int length = 39;
+ string_to_charr(string3, log, &length);
+ print_log(log, length);
+ }
+
+ slength = sl1 + sl2;
+ if(sl3 > 2) { slength += sl3 + 4; } else { slength++; }
if(sl1 && sl2)
{
- //dmicol -= slenght; // right align
- dmicol = 39 - slenght/2; // center align
+ //dmicol -= slength; // right align
+ dmicol = 39 - slength/2; // center align
cprint(LINE_DMI, dmicol, string1);
dmicol += sl1 + 1;
cprint(LINE_DMI, dmicol, string2);
diff --git a/efi_memtest/memtest86+/config.c b/efi_memtest/memtest86+/config.c
index 03e1554..cade5e1 100644
--- a/efi_memtest/memtest86+/config.c
+++ b/efi_memtest/memtest86+/config.c
@@ -12,6 +12,8 @@
#include "dmi.h"
#include "stdint.h"
+#include "logger.h"
+
extern int bail, beepmode;
extern struct tseq tseq[];
extern short e820_nr;
@@ -24,6 +26,9 @@ extern short restart_flag;
extern short onepass;
extern short btflag;
+extern short logflag;
+extern short log_pmap;
+
extern void get_list(int x, int y, int len, char *buf);
char save[2][POP_H][POP_W];
@@ -387,62 +392,21 @@ void get_config()
void popup()
{
-
print_popup();
- /*int i, j;
- char *pp;
-
- for (i=POP_Y; i<POP_Y + POP_H; i++) {
- for (j=POP_X; j<POP_X + POP_W; j++) {
- pp = (char *)(uintptr_t)(SCREEN_ADR + (i * 160) + (j * 2));
- save[0][i-POP_Y][j-POP_X] = *pp; */ /* Save screen */
- /*set_scrn_buf(i, j, ' ');
- *pp = ' '; */ /* Clear */
- /*pp++;
- save[1][i-POP_Y][j-POP_X] = *pp;
- *pp = 0x07; */ /* Change Background to black *//*
- }
- }
- tty_print_region(POP_Y, POP_X, POP_Y+POP_H, POP_X+POP_W);*/
}
void popdown()
{
print_mainscreen();
- /*int i, j;
- char *pp;
-
- for (i=POP_Y; i<POP_Y + POP_H; i++) {
- for (j=POP_X; j<POP_X + POP_W; j++) {
- pp = (char *)(uintptr_t)(SCREEN_ADR + (i * 160) + (j * 2));
- *pp = save[0][i-POP_Y][j-POP_X];*/ /* Restore screen */
- /*set_scrn_buf(i, j, save[0][i-POP_Y][j-POP_X]);
- pp++;
- *pp = save[1][i-POP_Y][j-POP_X];*/ /* Restore color *//*
- }
- }
- tty_print_region(POP_Y, POP_X, POP_Y+POP_H, POP_X+POP_W);*/
}
void popclear()
{
print_popup();
- /*int i, j;
- char *pp;
-
- for (i=POP_Y; i<POP_Y + POP_H; i++) {
- for (j=POP_X; j<POP_X + POP_W; j++) {
- pp = (char *)(uintptr_t)(SCREEN_ADR + (i * 160) + (j * 2));
- *pp = ' ';*/ /* Clear popup */
- /* set_scrn_buf(i, j, ' ');
- pp++;
- }
- }
- tty_print_region(POP_Y, POP_X, POP_Y+POP_H, POP_X+POP_W);*/
}
-void pop2up()
+void pop2up() // TODO when is this needed?
{
int i, j;
char *pp;
@@ -497,6 +461,14 @@ void pop2clear()
void adj_mem(void)
{
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvaaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
int i;
vv->selected_pages = 0;
@@ -504,11 +476,14 @@ void adj_mem(void)
/* Segment inside limits ? */
if (vv->pmap[i].start >= vv->plim_lower &&
vv->pmap[i].end <= vv->plim_upper) {
+
+ if(logflag && log_pmap) print_log(">>>>> 1", 7); // TODO remove
vv->selected_pages += (vv->pmap[i].end - vv->pmap[i].start);
continue;
}
/* Segment starts below limit? */
if (vv->pmap[i].start < vv->plim_lower) {
+ if(1) print_log(">>>>> 2", 7); // TODO remove
/* Also ends below limit? */
if (vv->pmap[i].end < vv->plim_lower) {
continue;
@@ -527,6 +502,13 @@ void adj_mem(void)
}
/* Segment ends above limit? */
if (vv->pmap[i].end > vv->plim_upper) {
+ if(1) print_log(">>>>> 3", 7); // TODO remove
+ if(1) {
+ char log[23] = "plim_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
/* Also starts above limit? */
if (vv->pmap[i].start > vv->plim_upper) {
continue;
diff --git a/efi_memtest/memtest86+/controller.c b/efi_memtest/memtest86+/controller.c
index b4683b6..12eb676 100644
--- a/efi_memtest/memtest86+/controller.c
+++ b/efi_memtest/memtest86+/controller.c
@@ -24,6 +24,11 @@ int nhm_bus = 0x3F;
extern ulong extclock;
extern unsigned long imc_type;
extern struct cpu_ident cpu_id;
+
+extern short logflag;
+extern short log_mem_ctrl;
+
+
/*
#define rdmsr(msr,val1,val2) \
__asm__ __volatile__("rdmsr" \
@@ -117,6 +122,9 @@ void coretemp(void)
void print_cpu_line(float dram_freq, float fsb_freq, int ram_type)
{
+
+ if (logflag) print_log("print_cpu_line() started.", 25);
+
int cur_col = COL_SPEC;
cprint(LINE_CPU, cur_col, "RAM: ");
@@ -126,6 +134,13 @@ void print_cpu_line(float dram_freq, float fsb_freq, int ram_type)
cprint(LINE_CPU, cur_col, "MHz (");
cur_col += 5;
+ if (logflag && log_mem_ctrl) {
+ char log[39] = "print_cpu_line(): ram_type = ";
+ int length = 29;
+ int_to_charr(ram_type, log, &length);
+ print_log(log, length);
+ }
+
switch(ram_type)
{
default:
@@ -141,7 +156,14 @@ void print_cpu_line(float dram_freq, float fsb_freq, int ram_type)
cprint(LINE_CPU, cur_col, "DDR3-");
cur_col += 5;
break;
- }
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[50] = "print_cpu_line(): dram_freq = ";
+ int length = 30;
+ int_to_charr(dram_freq, log, &length);
+ print_log(log, length);
+ }
if(dram_freq < 500)
{
@@ -154,6 +176,13 @@ void print_cpu_line(float dram_freq, float fsb_freq, int ram_type)
cprint(LINE_CPU, cur_col, ")");
cur_col++;
+ if (logflag && log_mem_ctrl) {
+ char log[49] = "print_cpu_line(): fsb_freq = ";
+ int length = 29;
+ int_to_charr(fsb_freq, log, &length);
+ print_log(log, length);
+ }
+
if(fsb_freq > 10)
{
cprint(LINE_CPU, cur_col, " - BCLK: ");
@@ -235,6 +264,8 @@ void print_ram_line(float cas, int rcd, int rp, int ras, int chan)
static void poll_fsb_nothing(void)
{
+ if (logflag) print_log("poll_fsb_nothing", 16);
+
char *name;
/* Print the controller name */
@@ -271,6 +302,9 @@ static void poll_nothing(void)
static void setup_wmr(void)
{
+
+ if (logflag) print_log("setup_wmr() started.", 20);
+
ulong dev0;
// Activate MMR I/O
@@ -1433,6 +1467,10 @@ static float getSNBmultiplier(void)
static void poll_fsb_ct(void)
{
+
+ print_log("poll_fsb_ct", 16);
+
+
unsigned long mcr, mdr;
double dramratio, dramclock, fsb;
float coef = getP4PMmultiplier();
@@ -1469,6 +1507,9 @@ static void poll_fsb_ct(void)
static void poll_fsb_amd64(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned int mcgsrl;
unsigned int mcgsth;
unsigned long fid, temp2;
@@ -1560,6 +1601,9 @@ static void poll_fsb_amd64(void) {
static void poll_fsb_k10(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned int mcgsrl;
unsigned int mcgsth;
unsigned long temp2;
@@ -1639,6 +1683,9 @@ static void poll_fsb_k10(void) {
static void poll_fsb_k12(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned long temp2;
unsigned long dramchr;
double dramratio, dramclock, fsb, did;
@@ -1722,6 +1769,9 @@ static void poll_fsb_k12(void) {
static void poll_fsb_k16(void)
{
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned long dramchr;
double dramratio, dramclock, fsb;
@@ -1768,6 +1818,9 @@ static void poll_fsb_k16(void)
static void poll_fsb_k15(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned long temp2;
unsigned long dramchr;
double dramratio, dramclock, fsb;
@@ -1828,6 +1881,9 @@ static void poll_fsb_k15(void) {
static void poll_fsb_k14(void)
{
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned long dramchr;
double dramratio, dramclock, fsb;
@@ -1863,6 +1919,9 @@ static void poll_fsb_k14(void)
static void poll_fsb_i925(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, mchcfg2, dev0, drc, idetect;
float coef = getP4PMmultiplier();
@@ -1919,6 +1978,9 @@ static void poll_fsb_i925(void) {
static void poll_fsb_i945(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0;
float coef = getP4PMmultiplier();
@@ -1950,6 +2012,9 @@ static void poll_fsb_i945(void) {
static void poll_fsb_i945gme(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0, fsb_mch;
float coef = getP4PMmultiplier();
@@ -2008,6 +2073,9 @@ static void poll_fsb_i945gme(void) {
static void poll_fsb_i975(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0, fsb_mch;
float coef = getP4PMmultiplier();
@@ -2067,6 +2135,9 @@ static void poll_fsb_i975(void) {
static void poll_fsb_i965(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0, fsb_mch;
float coef = getP4PMmultiplier();
@@ -2151,6 +2222,9 @@ static void poll_fsb_i965(void) {
static void poll_fsb_p35(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0, fsb_mch, Device_ID, Memory_Check, c0ckectrl, offset;
float coef = getP4PMmultiplier();
@@ -2271,6 +2345,9 @@ static void poll_fsb_p35(void) {
static void poll_fsb_im965(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, dev0, fsb_mch;
float coef = getP4PMmultiplier();
@@ -2339,6 +2416,9 @@ static void poll_fsb_im965(void) {
static void poll_fsb_5400(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long ambase_low, ambase_high, ddrfrq;
float coef = getP4PMmultiplier();
@@ -2380,6 +2460,9 @@ static void poll_fsb_5400(void) {
static void poll_fsb_nf4ie(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
float mratio, nratio;
unsigned long reg74, reg60;
@@ -2413,6 +2496,9 @@ static void poll_fsb_nf4ie(void) {
static void poll_fsb_i875(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mchcfg, smfs;
float coef = getP4PMmultiplier();
@@ -2446,6 +2532,9 @@ static void poll_fsb_i875(void) {
static void poll_fsb_p4(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
ulong fsb, idetect;
float coef = getP4PMmultiplier();
char *name;
@@ -2486,6 +2575,9 @@ static void poll_fsb_p4(void) {
static void poll_fsb_i855(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb ;
unsigned int msr_lo, msr_hi;
ulong mchcfg, idetect;
@@ -2536,6 +2628,9 @@ static void poll_fsb_i855(void) {
static void poll_fsb_amd32(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned int mcgsrl;
unsigned int mcgsth;
unsigned long temp;
@@ -2582,6 +2677,9 @@ static void poll_fsb_amd32(void) {
static void poll_fsb_nf2(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
unsigned int mcgsrl;
unsigned int mcgsth;
unsigned long temp, mempll;
@@ -2620,6 +2718,9 @@ static void poll_fsb_nf2(void) {
static void poll_fsb_us15w(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long msr;
@@ -2673,6 +2774,9 @@ static void poll_fsb_us15w(void) {
static void poll_fsb_nhm(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long mc_dimm_clk_ratio;
float coef = getNHMmultiplier();
@@ -2717,6 +2821,8 @@ static void poll_fsb_nhm(void) {
static void poll_fsb_nhm32(void) {
+ print_log("poll_fsb_nothing", 16);
+
double dramclock, dramratio, fsb;
unsigned long mc_dimm_clk_ratio;
float coef = getNHMmultiplier();
@@ -2760,6 +2866,8 @@ static void poll_fsb_nhm32(void) {
static void poll_fsb_wmr(void) {
+ print_log("poll_fsb_nothing", 16);
+
double dramclock, dramratio, fsb;
unsigned long dev0;
float coef = getNHMmultiplier();
@@ -2786,6 +2894,8 @@ static void poll_fsb_wmr(void) {
static void poll_fsb_snb(void) {
+ print_log("poll_fsb_nothing", 16);
+
double dramclock, dramratio, fsb;
unsigned long dev0;
float coef = getSNBmultiplier();
@@ -2812,6 +2922,8 @@ static void poll_fsb_snb(void) {
static void poll_fsb_ivb(void) {
+ print_log("poll_fsb_ivb", 12);
+
double dramclock, dramratio, fsb;
unsigned long dev0, mchcfg;
float coef = getSNBmultiplier();
@@ -2847,6 +2959,9 @@ static void poll_fsb_ivb(void) {
static void poll_fsb_snbe(void) {
+ print_log("poll_fsb_nothing", 16);
+
+
double dramclock, dramratio, fsb;
unsigned long dev0;
float coef = getSNBmultiplier();
@@ -4074,71 +4189,106 @@ struct pci_memory_controller controllers[] = {
{ 0xFFFF, 0x0105, "AMD K16 IMC","", 0, poll_fsb_k16, poll_timings_k16, setup_apu, poll_nothing }
};
-/*static void print_memory_controller(void)
+static void print_memory_controller(void)
{
- {
- char log[] = "\nprint_memory_controller() started.";
- print_log(log, sizeof(log) - 1);
- }*/
+
+
+
+ // TODO REMOVE
+ /* Print advanced caracteristics */
+ col2 = 0;
+
+ if (logflag && log_mem_ctrl) {
+ char log[23] = "ctrl.index = ";
+ int length = 13;
+ int_to_charr(ctrl.index, log, &length);
+ print_log(log, length);
+ }
+
+ //int index = ctrl.index;
+ //int index = 127;
+ //controllers[index].poll_fsb();
+ poll_fsb_ivb();
+ //controllers[127].poll_fsb();
+
+ print_log("print_controller(): 2nd", 23);
+ // TODO REMOVE UNTIL HERE
+
+
+ if (logflag && log_mem_ctrl) {
+ char log[] = "\nprint_memory_controller() started.";
+ print_log(log, sizeof(log) - 1);
+ }
/* Print memory controller info */
- /* if (ctrl.index == 0) {
+ if (ctrl.index == 0) {
+ if (logflag && log_mem_ctrl) {
+ print_log("ctrl.index = 0", 14);
+ }
return;
- }*/
+ }
/* Now print the memory controller capabilities */
- /*
- cprint(LINE_CPU+5, col, " "); col++;
- if (ctrl.cap == ECC_UNKNOWN) {
- return;
- }
- if (ctrl.cap & __ECC_DETECT) {
- int on;
- on = ctrl.mode & __ECC_DETECT;
- cprint(LINE_CPU+5, col, "(ECC : ");
- cprint(LINE_CPU+5, col +7, on?"Detect":"Disabled)");
- on?(col += 13):(col += 16);
- }
- if (ctrl.mode & __ECC_CORRECT) {
- int on;
- on = ctrl.mode & __ECC_CORRECT;
- cprint(LINE_CPU+5, col, " / ");
- if (ctrl.cap & __ECC_CHIPKILL) {
- cprint(LINE_CPU+5, col +3, on?"Correct -":"");
- on?(col += 12):(col +=3);
- } else {
- cprint(LINE_CPU+5, col +3, on?"Correct)":"");
- on?(col += 11):(col +=3);
- }
- }
- if (ctrl.mode & __ECC_DETECT) {
- if (ctrl.cap & __ECC_CHIPKILL) {
- int on;
- on = ctrl.mode & __ECC_CHIPKILL;
- cprint(LINE_CPU+5, col, " Chipkill : ");
- cprint(LINE_CPU+5, col +12, on?"On)":"Off)");
- on?(col += 15):(col +=16);
- }}
- if (ctrl.mode & __ECC_SCRUB) {
- int on;
- on = ctrl.mode & __ECC_SCRUB;
- cprint(LINE_CPU+5, col, " Scrub");
- cprint(LINE_CPU+5, col +6, on?"+ ":"- ");
- col += 7;
- }
- if (ctrl.cap & __ECC_UNEXPECTED) {
- int on;
- on = ctrl.mode & __ECC_UNEXPECTED;
- cprint(LINE_CPU+5, col, "Unknown");
- cprint(LINE_CPU+5, col +7, on?"+ ":"- ");
- col += 9;
- }
- */
+ cprint(LINE_CPU+5, col, " "); col++;
+ if (ctrl.cap == ECC_UNKNOWN) {
+ if (logflag && log_mem_ctrl) {
+ print_log("ctrl.cap == ECC_UNKNOWN", 23);
+ }
+ return;
+ }
+
+ if (ctrl.cap & __ECC_DETECT) {
+ int on;
+ on = ctrl.mode & __ECC_DETECT;
+ cprint(LINE_CPU+5, col, "(ECC : ");
+ cprint(LINE_CPU+5, col +7, on?"Detect":"Disabled)");
+ on?(col += 13):(col += 16);
+ }
+
+ if (ctrl.mode & __ECC_CORRECT) {
+ int on;
+ on = ctrl.mode & __ECC_CORRECT;
+ cprint(LINE_CPU+5, col, " / ");
+
+ if (ctrl.cap & __ECC_CHIPKILL) {
+ cprint(LINE_CPU+5, col +3, on?"Correct -":"");
+ on?(col += 12):(col +=3);
+ } else {
+ cprint(LINE_CPU+5, col +3, on?"Correct)":"");
+ on?(col += 11):(col +=3);
+ }
+ }
+
+ if (ctrl.mode & __ECC_DETECT) {
+ if (ctrl.cap & __ECC_CHIPKILL) {
+ int on;
+ on = ctrl.mode & __ECC_CHIPKILL;
+ cprint(LINE_CPU+5, col, " Chipkill : ");
+ cprint(LINE_CPU+5, col +12, on?"On)":"Off)");
+ on?(col += 15):(col +=16);
+ }}
+
+ if (ctrl.mode & __ECC_SCRUB) {
+ int on;
+ on = ctrl.mode & __ECC_SCRUB;
+ cprint(LINE_CPU+5, col, " Scrub");
+ cprint(LINE_CPU+5, col +6, on?"+ ":"- ");
+ col += 7;
+ }
+
+ if (ctrl.cap & __ECC_UNEXPECTED) {
+ int on;
+ on = ctrl.mode & __ECC_UNEXPECTED;
+ cprint(LINE_CPU+5, col, "Unknown");
+ cprint(LINE_CPU+5, col +7, on?"+ ":"- ");
+ col += 9;
+ }
+
/* Print advanced caracteristics */
- /*col2 = 0;
+ col2 = 0;
print_log("print_controller(): 1sd", 22);
@@ -4151,13 +4301,13 @@ struct pci_memory_controller controllers[] = {
print_log("print_controller(): 3sd", 22);
}
-*/
+
void find_controller(void)
{
- {
- char log[] = "\nfind_controller(): started.";
- print_log(log, sizeof(log) - 1);
+ if (logflag && log_mem_ctrl) {
+ char log[] = "\nfind_controller(): started.";
+ print_log(log, sizeof(log) - 1);
}
unsigned long vendor;
@@ -4166,24 +4316,40 @@ void find_controller(void)
int result;
result = pci_conf_read(ctrl.bus, ctrl.dev, ctrl.fn, PCI_VENDOR_ID, 2, &vendor);
- {
- char log[48] = "find_controller(): vendor = ";
- int length = 28;
- int_to_charr(vendor, log, &length);
- print_log(log, length);
+
+ if (logflag && log_mem_ctrl) {
+ char log[68] = "find_controller(): vendor by pci_conf = ";
+ int length = 40;
+ int_to_charr(vendor, log, &length);
+ print_log(log, length);
}
result = pci_conf_read(ctrl.bus, ctrl.dev, ctrl.fn, PCI_DEVICE_ID, 2, &device);
- {
- char log[48] = "find_controller(): device = ";
- int length = 28;
- int_to_charr(device, log, &length);
- print_log(log, length);
+
+ if (logflag && log_mem_ctrl) {
+ char log[60] = "find_controller(): device by pci_conf = ";
+ int length = 40;
+ int_to_charr(device, log, &length);
+ print_log(log, length);
}
// Detect IMC by CPUID
if(imc_type) { vendor = 0xFFFF; device = imc_type; }
if(vv->fail_safe & 1) { vendor = 0xFFFF; device = 0xFFFF; }
+
+ if (logflag && log_mem_ctrl) {
+ char log[57] = "find_controller(): vendor by cpuid = ";
+ int length = 37;
+ int_to_charr(vendor, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[57] = "find_controller(): device by cpuid = ";
+ int length = 37;
+ int_to_charr(device, log, &length);
+ print_log(log, length);
+ }
//hprint(11,0,vendor); hprint(11,10,device);
@@ -4197,36 +4363,57 @@ void find_controller(void)
}
}
- {
- char log[42] = "find_controller(): ctrl.index = ";
- int length = 32;
- int_to_charr(ctrl.index, log, &length);
- print_log(log, length);
+ if (logflag && log_mem_ctrl) {
+ char log[42] = "find_controller(): ctrl.index = ";
+ int length = 32;
+ int_to_charr(ctrl.index, log, &length);
+ print_log(log, length);
}
- /* {
- char log[70] = "find_controller(): pci_memory_controller.name = ";
- int length = 48;
- string_to_charr(controllers[ctrl.index].name, log, &length);
- print_log(log, length);
+ if (logflag && log_mem_ctrl) {
+ char log[30] = "Pointer = ";
+ int length = 10;
+ int_to_charr((unsigned long int)controllers[ctrl.index].name, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[30] = "Pointer = ";
+ int length = 10;
+ int_to_charr((unsigned long int)controllers[127].name, log, &length);
+ print_log(log, length);
}
- */
- controllers[ctrl.index].setup_ecc();
-
- print_log("4m.bm", 5);
- print_log("4m.bm", 5);
- print_log("4m.bm", 5);
- print_log("4m.bm", 5);
- print_log("4m.bm", 5);
+ if (logflag && log_mem_ctrl) {
+ char log[70] = "find_controller(): pci_memory_controller.name = XXXXXXXXXXXXXXXXXXXX";
+ int length = 48;
+ string_to_charr(controllers[127].name, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_mem_ctrl) {
+ char log[49] = "find_controller(): controller length = ";
+ int length = 39;
+ int ctrl_size = sizeof(controllers) / sizeof(controllers[0]);
+ int_to_charr(ctrl_size, log, &length);
+ print_log(log, length);
+ }
+
+ controllers[127].setup_ecc();
/* Don't enable ECC polling by default unless it has
* been well tested.
*/
- //set_ecc_polling(-1);
- //print_memory_controller();
-
- print_log("5mbm", 4);
+ // TODO this function contains a variable 'COL_ECC' which is defined nowhere
+ // set_ecc_polling(-1);
+ print_memory_controller();
+
+ if (logflag && log_mem_ctrl) {
+ char log[40] = "find_controller(): imc_type = ";
+ int length = 30;
+ int_to_charr(imc_type, log, &length);
+ print_log(log, length);
+ }
if(imc_type) { print_dmi_startup_info(); }
@@ -4234,13 +4421,16 @@ void find_controller(void)
void poll_errors(void)
{
+ if (logflag && log_mem_ctrl) {
+ print_log("poll_errors() started", 21);
+ }
if (ctrl.poll) {
controllers[ctrl.index].poll_errors();
}
}
-/*
- void set_ecc_polling(int val)
+
+/* void set_ecc_polling(int val)
{
int tested = controllers[ctrl.index].tested;
if (val == -1) {
@@ -4253,6 +4443,6 @@ void poll_errors(void)
ctrl.poll = 0;
cprint(LINE_INFO, COL_ECC, "off");
}
- }
-*/
+ }*/
+
diff --git a/efi_memtest/memtest86+/cpuid.c b/efi_memtest/memtest86+/cpuid.c
index 6edaf4d..b3030a5 100644
--- a/efi_memtest/memtest86+/cpuid.c
+++ b/efi_memtest/memtest86+/cpuid.c
@@ -85,9 +85,9 @@ void get_cpuid()
}
if (logflag) {
- char vendor[26] = "get_cpuid(): Vendor ID = ";
- vendor[25] = cpu_id.vend_id.char_array[0];
- print_log(vendor, sizeof(vendor));
+ char vendor[26] = "get_cpuid(): Vendor ID = ";
+ vendor[25] = cpu_id.vend_id.char_array[0];
+ print_log(vendor, sizeof(vendor));
}
/* Get cache information */
diff --git a/efi_memtest/memtest86+/efi/Include/AutoGen.c b/efi_memtest/memtest86+/efi/Include/AutoGen.c
deleted file mode 100644
index 9a8642a..0000000
--- a/efi_memtest/memtest86+/efi/Include/AutoGen.c
+++ /dev/null
@@ -1,327 +0,0 @@
-/**
- DO NOT EDIT
- FILE auto-generated
- Module name:
- AutoGen.c
- Abstract: Auto-generated AutoGen.c for building module or library.
-**/
-#include "Uefi.h"
-#include "Library/BaseLib.h"
-#include "Library/DebugLib.h"
-#include "Library/UefiBootServicesTableLib.h"
-#include "Library/UefiApplicationEntryPoint.h"
-
-GLOBAL_REMOVE_IF_UNREFERENCED GUID gEfiCallerIdGuid = {0x51d8cae0, 0x272a, 0x661f, {0xa8, 0xd9, 0x84, 0x51, 0xdf, 0xf0, 0xeb, 0xd0}};
-
-GLOBAL_REMOVE_IF_UNREFERENCED CHAR8 *gEfiCallerBaseName = "MemtestEfi";
-
-// Guids
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiMdePkgTokenSpaceGuid = { 0x914AEBE7, 0x4635, 0x459b, { 0xAA, 0x1C, 0x11, 0xE2, 0x19, 0xB0, 0x3A, 0x10 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVTUTF8Guid = { 0xAD15A0D6, 0x8BEC, 0x4ACF, { 0xA0, 0x73, 0xD0, 0x1D, 0xE7, 0x7E, 0x2D, 0x88 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVT100Guid = { 0xDFA66065, 0xB419, 0x11D3, { 0x9A, 0x2D, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVT100PlusGuid = { 0x7BAEC70B, 0x57E0, 0x4C76, { 0x8E, 0x87, 0x2F, 0x9E, 0x28, 0x08, 0x83, 0x43 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPcAnsiGuid = { 0xE0C14753, 0xF9BE, 0x11D2, { 0x9A, 0x0C, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiUartDevicePathGuid = { 0x37499a9d, 0x542f, 0x4c89, { 0xa0, 0x26, 0x35, 0xda, 0x14, 0x20, 0x94, 0xe4 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSasDevicePathGuid = { 0xd487ddb4, 0x008b, 0x11d9, { 0xaf, 0xdc, 0x00, 0x10, 0x83, 0xff, 0xca, 0x4d }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualDiskGuid = { 0x77AB535A, 0x45FC, 0x624B, {0x55, 0x60, 0xF7, 0xB2, 0x81, 0xD1, 0xF9, 0x6E }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualCdGuid = { 0x3D5ABD30, 0x4175, 0x87CE, {0x6D, 0x64, 0xD2, 0xAD, 0xE5, 0x23, 0xC4, 0xBB }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualDiskGuid = { 0x5CEA02C9, 0x4D07, 0x69D3, {0x26, 0x9F ,0x44, 0x96, 0xFB, 0xE0, 0x96, 0xF9 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualCdGuid = { 0x08018188, 0x42CD, 0xBB48, {0x10, 0x0F, 0x53, 0x87, 0xD5, 0x3D, 0xED, 0x3D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiEventReadyToBootGuid = { 0x7CE88FB3, 0x4BD7, 0x4679, { 0x87, 0xA8, 0xA8, 0xD8, 0xDE, 0xE5, 0x0D, 0x2B }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiEventLegacyBootGuid = { 0x2A571201, 0x4966, 0x47F6, { 0x8B, 0x86, 0xF3, 0x1E, 0x41, 0xF3, 0x2F, 0x10 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiGlobalVariableGuid = { 0x8BE4DF61, 0x93CA, 0x11D2, { 0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8C }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiAcpi20TableGuid = { 0x8868E871, 0xE4F1, 0x11D3, { 0xBC, 0x22, 0x00, 0x80, 0xC7, 0x3C, 0x88, 0x81 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiAcpi10TableGuid = { 0xEB9D2D30, 0x2D88, 0x11D3, { 0x9A, 0x16, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-
-// Protocols
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDevicePathProtocolGuid = { 0x09576E91, 0x6D3F, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDebugPortProtocolGuid = { 0xEBA4E8D2, 0x3858, 0x41EC, { 0xA2, 0x81, 0x26, 0x47, 0xBA, 0x96, 0x60, 0xD0 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverBindingProtocolGuid = { 0x18A031AB, 0xB443, 0x4D1A, { 0xA5, 0xC0, 0x0C, 0x09, 0x26, 0x1E, 0x9F, 0x71 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSimpleTextOutProtocolGuid = { 0x387477C2, 0x69C7, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiGraphicsOutputProtocolGuid = { 0x9042A9DE, 0x23DC, 0x4A38, { 0x96, 0xFB, 0x7A, 0xDE, 0xD0, 0x80, 0x51, 0x6A }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiHiiFontProtocolGuid = {0xe9ca4775, 0x8657, 0x47fc, {0x97, 0xe7, 0x7e, 0xd6, 0x5a, 0x08, 0x43, 0x24}};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSimpleFileSystemProtocolGuid = { 0x964E5B22, 0x6459, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiUgaDrawProtocolGuid = { 0x982C298B, 0xF4FA, 0x41CB, { 0xB8, 0x38, 0x77, 0xAA, 0x68, 0x8F, 0xB8, 0x39 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentNameProtocolGuid = { 0x107A772C, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentName2ProtocolGuid = { 0x6A7A5CFF, 0xE8D9, 0x4F70, { 0xBA, 0xDA, 0x75, 0xAB, 0x30, 0x25, 0xCE, 0x14 }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfigurationProtocolGuid = { 0x107A772B, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfiguration2ProtocolGuid = { 0xBFD7DC1D, 0x24F1, 0x40D9, { 0x82, 0xE7, 0x2E, 0x09, 0xBB, 0x6B, 0x4E, 0xBE }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnosticsProtocolGuid = { 0x0784924F, 0xE296, 0x11D4, { 0x9A, 0x49, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
-GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnostics2ProtocolGuid = { 0x4D330321, 0x025F, 0x4AAC, { 0x90, 0xD8, 0x5E, 0xD9, 0x00, 0x17, 0x3B, 0x63 }};
-
-// Definition of SkuId Array
-GLOBAL_REMOVE_IF_UNREFERENCED UINT64 _gPcd_SkuId_Array[] = {0x0};
-
-// Definition of PCDs used in libraries
-
-#define _PCD_TOKEN_PcdVerifyNodeInList 17U
-#define _PCD_SIZE_PcdVerifyNodeInList 1
-#define _PCD_GET_MODE_SIZE_PcdVerifyNodeInList _PCD_SIZE_PcdVerifyNodeInList
-#define _PCD_VALUE_PcdVerifyNodeInList ((BOOLEAN)0U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdVerifyNodeInList = _PCD_VALUE_PcdVerifyNodeInList;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdVerifyNodeInList;
-#define _PCD_GET_MODE_BOOL_PcdVerifyNodeInList _gPcd_FixedAtBuild_PcdVerifyNodeInList
-//#define _PCD_SET_MODE_BOOL_PcdVerifyNodeInList ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdMaximumLinkedListLength 12U
-#define _PCD_SIZE_PcdMaximumLinkedListLength 4
-#define _PCD_GET_MODE_SIZE_PcdMaximumLinkedListLength _PCD_SIZE_PcdMaximumLinkedListLength
-#define _PCD_VALUE_PcdMaximumLinkedListLength 1000000U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdMaximumLinkedListLength = _PCD_VALUE_PcdMaximumLinkedListLength;
-extern const UINT32 _gPcd_FixedAtBuild_PcdMaximumLinkedListLength;
-#define _PCD_GET_MODE_32_PcdMaximumLinkedListLength _gPcd_FixedAtBuild_PcdMaximumLinkedListLength
-//#define _PCD_SET_MODE_32_PcdMaximumLinkedListLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdMaximumAsciiStringLength 10U
-#define _PCD_SIZE_PcdMaximumAsciiStringLength 4
-#define _PCD_GET_MODE_SIZE_PcdMaximumAsciiStringLength _PCD_SIZE_PcdMaximumAsciiStringLength
-#define _PCD_VALUE_PcdMaximumAsciiStringLength 1000000U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdMaximumAsciiStringLength = _PCD_VALUE_PcdMaximumAsciiStringLength;
-extern const UINT32 _gPcd_FixedAtBuild_PcdMaximumAsciiStringLength;
-#define _PCD_GET_MODE_32_PcdMaximumAsciiStringLength _gPcd_FixedAtBuild_PcdMaximumAsciiStringLength
-//#define _PCD_SET_MODE_32_PcdMaximumAsciiStringLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdMaximumUnicodeStringLength 13U
-#define _PCD_SIZE_PcdMaximumUnicodeStringLength 4
-#define _PCD_GET_MODE_SIZE_PcdMaximumUnicodeStringLength _PCD_SIZE_PcdMaximumUnicodeStringLength
-#define _PCD_VALUE_PcdMaximumUnicodeStringLength 1000000U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdMaximumUnicodeStringLength = _PCD_VALUE_PcdMaximumUnicodeStringLength;
-extern const UINT32 _gPcd_FixedAtBuild_PcdMaximumUnicodeStringLength;
-#define _PCD_GET_MODE_32_PcdMaximumUnicodeStringLength _gPcd_FixedAtBuild_PcdMaximumUnicodeStringLength
-//#define _PCD_SET_MODE_32_PcdMaximumUnicodeStringLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdControlFlowEnforcementPropertyMask 3U
-#define _PCD_SIZE_PcdControlFlowEnforcementPropertyMask 4
-#define _PCD_GET_MODE_SIZE_PcdControlFlowEnforcementPropertyMask _PCD_SIZE_PcdControlFlowEnforcementPropertyMask
-#define _PCD_VALUE_PcdControlFlowEnforcementPropertyMask 0x0U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask = _PCD_VALUE_PcdControlFlowEnforcementPropertyMask;
-extern const UINT32 _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask;
-#define _PCD_GET_MODE_32_PcdControlFlowEnforcementPropertyMask _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask
-//#define _PCD_SET_MODE_32_PcdControlFlowEnforcementPropertyMask ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdSpeculationBarrierType 14U
-#define _PCD_SIZE_PcdSpeculationBarrierType 1
-#define _PCD_GET_MODE_SIZE_PcdSpeculationBarrierType _PCD_SIZE_PcdSpeculationBarrierType
-#define _PCD_VALUE_PcdSpeculationBarrierType 0x01U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gPcd_FixedAtBuild_PcdSpeculationBarrierType = _PCD_VALUE_PcdSpeculationBarrierType;
-extern const UINT8 _gPcd_FixedAtBuild_PcdSpeculationBarrierType;
-#define _PCD_GET_MODE_8_PcdSpeculationBarrierType _gPcd_FixedAtBuild_PcdSpeculationBarrierType
-//#define _PCD_SET_MODE_8_PcdSpeculationBarrierType ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdDebugPrintErrorLevel 5U
-#define _PCD_SIZE_PcdDebugPrintErrorLevel 4
-#define _PCD_GET_MODE_SIZE_PcdDebugPrintErrorLevel _PCD_SIZE_PcdDebugPrintErrorLevel
-#define _PCD_VALUE_PcdDebugPrintErrorLevel 0x80000000U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdDebugPrintErrorLevel = _PCD_VALUE_PcdDebugPrintErrorLevel;
-extern const UINT32 _gPcd_FixedAtBuild_PcdDebugPrintErrorLevel;
-#define _PCD_GET_MODE_32_PcdDebugPrintErrorLevel _gPcd_FixedAtBuild_PcdDebugPrintErrorLevel
-//#define _PCD_SET_MODE_32_PcdDebugPrintErrorLevel ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdDebugClearMemoryValue 4U
-#define _PCD_SIZE_PcdDebugClearMemoryValue 1
-#define _PCD_GET_MODE_SIZE_PcdDebugClearMemoryValue _PCD_SIZE_PcdDebugClearMemoryValue
-#define _PCD_VALUE_PcdDebugClearMemoryValue 0xAFU
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gPcd_FixedAtBuild_PcdDebugClearMemoryValue = _PCD_VALUE_PcdDebugClearMemoryValue;
-extern const UINT8 _gPcd_FixedAtBuild_PcdDebugClearMemoryValue;
-#define _PCD_GET_MODE_8_PcdDebugClearMemoryValue _gPcd_FixedAtBuild_PcdDebugClearMemoryValue
-//#define _PCD_SET_MODE_8_PcdDebugClearMemoryValue ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdDebugPropertyMask 6U
-#define _PCD_SIZE_PcdDebugPropertyMask 1
-#define _PCD_GET_MODE_SIZE_PcdDebugPropertyMask _PCD_SIZE_PcdDebugPropertyMask
-#define _PCD_VALUE_PcdDebugPropertyMask 0U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gPcd_FixedAtBuild_PcdDebugPropertyMask = _PCD_VALUE_PcdDebugPropertyMask;
-extern const UINT8 _gPcd_FixedAtBuild_PcdDebugPropertyMask;
-#define _PCD_GET_MODE_8_PcdDebugPropertyMask _gPcd_FixedAtBuild_PcdDebugPropertyMask
-//#define _PCD_SET_MODE_8_PcdDebugPropertyMask ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdFixedDebugPrintErrorLevel 9U
-#define _PCD_SIZE_PcdFixedDebugPrintErrorLevel 4
-#define _PCD_GET_MODE_SIZE_PcdFixedDebugPrintErrorLevel _PCD_SIZE_PcdFixedDebugPrintErrorLevel
-#define _PCD_VALUE_PcdFixedDebugPrintErrorLevel 0xFFFFFFFFU
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdFixedDebugPrintErrorLevel = _PCD_VALUE_PcdFixedDebugPrintErrorLevel;
-extern const UINT32 _gPcd_FixedAtBuild_PcdFixedDebugPrintErrorLevel;
-#define _PCD_GET_MODE_32_PcdFixedDebugPrintErrorLevel _gPcd_FixedAtBuild_PcdFixedDebugPrintErrorLevel
-//#define _PCD_SET_MODE_32_PcdFixedDebugPrintErrorLevel ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdMaximumDevicePathNodeCount 11U
-#define _PCD_SIZE_PcdMaximumDevicePathNodeCount 4
-#define _PCD_GET_MODE_SIZE_PcdMaximumDevicePathNodeCount _PCD_SIZE_PcdMaximumDevicePathNodeCount
-#define _PCD_VALUE_PcdMaximumDevicePathNodeCount 0U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdMaximumDevicePathNodeCount = _PCD_VALUE_PcdMaximumDevicePathNodeCount;
-extern const UINT32 _gPcd_FixedAtBuild_PcdMaximumDevicePathNodeCount;
-#define _PCD_GET_MODE_32_PcdMaximumDevicePathNodeCount _gPcd_FixedAtBuild_PcdMaximumDevicePathNodeCount
-//#define _PCD_SET_MODE_32_PcdMaximumDevicePathNodeCount ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdDriverDiagnosticsDisable 8U
-#define _PCD_SIZE_PcdDriverDiagnosticsDisable 1
-#define _PCD_GET_MODE_SIZE_PcdDriverDiagnosticsDisable _PCD_SIZE_PcdDriverDiagnosticsDisable
-#define _PCD_VALUE_PcdDriverDiagnosticsDisable ((BOOLEAN)0U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdDriverDiagnosticsDisable = _PCD_VALUE_PcdDriverDiagnosticsDisable;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdDriverDiagnosticsDisable;
-#define _PCD_GET_MODE_BOOL_PcdDriverDiagnosticsDisable _gPcd_FixedAtBuild_PcdDriverDiagnosticsDisable
-//#define _PCD_SET_MODE_BOOL_PcdDriverDiagnosticsDisable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdComponentNameDisable 2U
-#define _PCD_SIZE_PcdComponentNameDisable 1
-#define _PCD_GET_MODE_SIZE_PcdComponentNameDisable _PCD_SIZE_PcdComponentNameDisable
-#define _PCD_VALUE_PcdComponentNameDisable ((BOOLEAN)0U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdComponentNameDisable = _PCD_VALUE_PcdComponentNameDisable;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdComponentNameDisable;
-#define _PCD_GET_MODE_BOOL_PcdComponentNameDisable _gPcd_FixedAtBuild_PcdComponentNameDisable
-//#define _PCD_SET_MODE_BOOL_PcdComponentNameDisable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdDriverDiagnostics2Disable 7U
-#define _PCD_SIZE_PcdDriverDiagnostics2Disable 1
-#define _PCD_GET_MODE_SIZE_PcdDriverDiagnostics2Disable _PCD_SIZE_PcdDriverDiagnostics2Disable
-#define _PCD_VALUE_PcdDriverDiagnostics2Disable ((BOOLEAN)0U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdDriverDiagnostics2Disable = _PCD_VALUE_PcdDriverDiagnostics2Disable;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdDriverDiagnostics2Disable;
-#define _PCD_GET_MODE_BOOL_PcdDriverDiagnostics2Disable _gPcd_FixedAtBuild_PcdDriverDiagnostics2Disable
-//#define _PCD_SET_MODE_BOOL_PcdDriverDiagnostics2Disable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdComponentName2Disable 1U
-#define _PCD_SIZE_PcdComponentName2Disable 1
-#define _PCD_GET_MODE_SIZE_PcdComponentName2Disable _PCD_SIZE_PcdComponentName2Disable
-#define _PCD_VALUE_PcdComponentName2Disable ((BOOLEAN)0U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdComponentName2Disable = _PCD_VALUE_PcdComponentName2Disable;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdComponentName2Disable;
-#define _PCD_GET_MODE_BOOL_PcdComponentName2Disable _gPcd_FixedAtBuild_PcdComponentName2Disable
-//#define _PCD_SET_MODE_BOOL_PcdComponentName2Disable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdUgaConsumeSupport 16U
-#define _PCD_SIZE_PcdUgaConsumeSupport 1
-#define _PCD_GET_MODE_SIZE_PcdUgaConsumeSupport _PCD_SIZE_PcdUgaConsumeSupport
-#define _PCD_VALUE_PcdUgaConsumeSupport ((BOOLEAN)1U)
-GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdUgaConsumeSupport = _PCD_VALUE_PcdUgaConsumeSupport;
-extern const BOOLEAN _gPcd_FixedAtBuild_PcdUgaConsumeSupport;
-#define _PCD_GET_MODE_BOOL_PcdUgaConsumeSupport _gPcd_FixedAtBuild_PcdUgaConsumeSupport
-//#define _PCD_SET_MODE_BOOL_PcdUgaConsumeSupport ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-#define _PCD_TOKEN_PcdUefiLibMaxPrintBufferSize 15U
-#define _PCD_SIZE_PcdUefiLibMaxPrintBufferSize 4
-#define _PCD_GET_MODE_SIZE_PcdUefiLibMaxPrintBufferSize _PCD_SIZE_PcdUefiLibMaxPrintBufferSize
-#define _PCD_VALUE_PcdUefiLibMaxPrintBufferSize 320U
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdUefiLibMaxPrintBufferSize = _PCD_VALUE_PcdUefiLibMaxPrintBufferSize;
-extern const UINT32 _gPcd_FixedAtBuild_PcdUefiLibMaxPrintBufferSize;
-#define _PCD_GET_MODE_32_PcdUefiLibMaxPrintBufferSize _gPcd_FixedAtBuild_PcdUefiLibMaxPrintBufferSize
-//#define _PCD_SET_MODE_32_PcdUefiLibMaxPrintBufferSize ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
-
-extern EFI_STATUS
-EFIAPI
-UefiMain (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-EFI_STATUS
-EFIAPI
-DxeDebugLibConstructor (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-EFI_STATUS
-EFIAPI
-UefiBootServicesTableLibConstructor (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-EFI_STATUS
-EFIAPI
-UefiRuntimeServicesTableLibConstructor (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-EFI_STATUS
-EFIAPI
-UefiLibConstructor (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-
-VOID
-EFIAPI
-ProcessLibraryConstructorList (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- )
-{
- EFI_STATUS Status;
-
- Status = DxeDebugLibConstructor (ImageHandle, SystemTable);
- ASSERT_EFI_ERROR (Status);
-
- Status = UefiBootServicesTableLibConstructor (ImageHandle, SystemTable);
- ASSERT_EFI_ERROR (Status);
-
- Status = UefiRuntimeServicesTableLibConstructor (ImageHandle, SystemTable);
- ASSERT_EFI_ERROR (Status);
-
- Status = UefiLibConstructor (ImageHandle, SystemTable);
- ASSERT_EFI_ERROR (Status);
-
-}
-
-
-EFI_STATUS
-EFIAPI
-DxeDebugLibDestructor (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-
-VOID
-EFIAPI
-ProcessLibraryDestructorList (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- )
-{
- EFI_STATUS Status;
-
- Status = DxeDebugLibDestructor (ImageHandle, SystemTable);
- ASSERT_EFI_ERROR (Status);
-
-}
-
-const UINT32 _gUefiDriverRevision = 0x00000000U;
-
-
-EFI_STATUS
-EFIAPI
-ProcessModuleEntryPointList (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- )
-
-{
- return UefiMain (ImageHandle, SystemTable);
-}
-
-VOID
-EFIAPI
-ExitDriver (
- IN EFI_STATUS Status
- )
-{
- if (EFI_ERROR (Status)) {
- ProcessLibraryDestructorList (gImageHandle, gST);
- }
- gBS->Exit (gImageHandle, Status, 0, NULL);
-}
-
-GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gDriverUnloadImageCount = 0U;
-
-EFI_STATUS
-EFIAPI
-ProcessModuleUnloadList (
- IN EFI_HANDLE ImageHandle
- )
-{
- return EFI_SUCCESS;
-}
diff --git a/efi_memtest/memtest86+/efi/Include/Efi_Defs.c b/efi_memtest/memtest86+/efi/Include/Efi_Defs.c
new file mode 100644
index 0000000..6b3bda2
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Efi_Defs.c
@@ -0,0 +1,176 @@
+#include "Efi_Defs.h"
+#include "Efi_Defs_GUID.h"
+#include "Uefi.h"
+#include "Library/BaseLib.h"
+#include "Library/DebugLib.h"
+#include "Library/UefiBootServicesTableLib.h"
+#include "Library/UefiApplicationEntryPoint.h"
+
+EFI_GUID gEfiCallerIdGuid = EFI_CALLER_ID_GUID;
+
+CHAR8 *gEfiCallerBaseName = "MemtestEfi";
+
+// Guids
+EFI_GUID gEfiAcpiTableGuid = EFI_ACPI_TABLE_GUID;
+EFI_GUID gEfiAcpi20TableGuid = EFI_ACPI_20_TABLE_GUID;
+EFI_GUID gEfiAcpi10TableGuid = EFI_ACPI_10_TABLE_GUID;
+EFI_GUID gEfiEventReadyToBootGuid = EFI_EVENT_GROUP_READY_TO_BOOT;
+EFI_GUID gEfiEventLegacyBootGuid = EFI_EVENT_LEGACY_BOOT_GUID;
+EFI_GUID gEfiGlobalVariableGuid = EFI_GLOBAL_VARIABLE;
+EFI_GUID gEfiPcAnsiGuid = EFI_PC_ANSI_GUID;
+EFI_GUID gEfiVT100Guid = EFI_VT_100_GUID;
+EFI_GUID gEfiVT100PlusGuid = EFI_VT_100_PLUS_GUID;
+EFI_GUID gEfiVTUTF8Guid = EFI_VT_UTF8_GUID;
+EFI_GUID gEfiUartDevicePathGuid = DEVICE_PATH_MESSAGING_UART_FLOW_CONTROL;
+EFI_GUID gEfiSasDevicePathGuid = EFI_SAS_DEVICE_PATH_GUID;
+EFI_GUID gEfiSmbiosGuid = SMBIOS_TABLE_GUID;
+EFI_GUID gEfiSmbios3Guid = SMBIOS3_TABLE_GUID;
+
+// Protocols
+EFI_GUID gEfiSimpleFileSystemProtocolGuid = EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_GUID;
+EFI_GUID gEfiFileSystemInfoGuid = EFI_FILE_SYSTEM_INFO_ID;
+EFI_GUID gEfiLoadedImageProtocolGuid = EFI_LOADED_IMAGE_PROTOCOL_GUID;
+
+// Guids
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiMdePkgTokenSpaceGuid = { 0x914AEBE7, 0x4635, 0x459b, { 0xAA, 0x1C, 0x11, 0xE2, 0x19, 0xB0, 0x3A, 0x10 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualDiskGuid = { 0x77AB535A, 0x45FC, 0x624B, {0x55, 0x60, 0xF7, 0xB2, 0x81, 0xD1, 0xF9, 0x6E }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualCdGuid = { 0x3D5ABD30, 0x4175, 0x87CE, {0x6D, 0x64, 0xD2, 0xAD, 0xE5, 0x23, 0xC4, 0xBB }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualDiskGuid = { 0x5CEA02C9, 0x4D07, 0x69D3, {0x26, 0x9F ,0x44, 0x96, 0xFB, 0xE0, 0x96, 0xF9 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualCdGuid = { 0x08018188, 0x42CD, 0xBB48, {0x10, 0x0F, 0x53, 0x87, 0xD5, 0x3D, 0xED, 0x3D }};
+
+// Protocols
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDevicePathProtocolGuid = { 0x09576E91, 0x6D3F, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDebugPortProtocolGuid = { 0xEBA4E8D2, 0x3858, 0x41EC, { 0xA2, 0x81, 0x26, 0x47, 0xBA, 0x96, 0x60, 0xD0 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverBindingProtocolGuid = { 0x18A031AB, 0xB443, 0x4D1A, { 0xA5, 0xC0, 0x0C, 0x09, 0x26, 0x1E, 0x9F, 0x71 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSimpleTextOutProtocolGuid = { 0x387477C2, 0x69C7, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiGraphicsOutputProtocolGuid = { 0x9042A9DE, 0x23DC, 0x4A38, { 0x96, 0xFB, 0x7A, 0xDE, 0xD0, 0x80, 0x51, 0x6A }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiHiiFontProtocolGuid = {0xe9ca4775, 0x8657, 0x47fc, {0x97, 0xe7, 0x7e, 0xd6, 0x5a, 0x08, 0x43, 0x24}};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiUgaDrawProtocolGuid = { 0x982C298B, 0xF4FA, 0x41CB, { 0xB8, 0x38, 0x77, 0xAA, 0x68, 0x8F, 0xB8, 0x39 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentNameProtocolGuid = { 0x107A772C, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentName2ProtocolGuid = { 0x6A7A5CFF, 0xE8D9, 0x4F70, { 0xBA, 0xDA, 0x75, 0xAB, 0x30, 0x25, 0xCE, 0x14 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfigurationProtocolGuid = { 0x107A772B, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfiguration2ProtocolGuid = { 0xBFD7DC1D, 0x24F1, 0x40D9, { 0x82, 0xE7, 0x2E, 0x09, 0xBB, 0x6B, 0x4E, 0xBE }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnosticsProtocolGuid = { 0x0784924F, 0xE296, 0x11D4, { 0x9A, 0x49, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnostics2ProtocolGuid = { 0x4D330321, 0x025F, 0x4AAC, { 0x90, 0xD8, 0x5E, 0xD9, 0x00, 0x17, 0x3B, 0x63 }};
+
+// Definition of SkuId Array
+//GLOBAL_REMOVE_IF_UNREFERENCED UINT64 _gPcd_SkuId_Array[] = {0x0};
+
+extern EFI_STATUS
+EFIAPI
+UefiMain (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+DxeDebugLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiBootServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiRuntimeServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+VOID
+EFIAPI
+ProcessLibraryConstructorList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ Status = DxeDebugLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiBootServicesTableLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiRuntimeServicesTableLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+}
+
+
+EFI_STATUS
+EFIAPI
+DxeDebugLibDestructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+VOID
+EFIAPI
+ProcessLibraryDestructorList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ Status = DxeDebugLibDestructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+}
+
+const UINT32 _gUefiDriverRevision = 0x00000000U;
+
+
+EFI_STATUS
+EFIAPI
+ProcessModuleEntryPointList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+
+{
+ return UefiMain (ImageHandle, SystemTable);
+}
+
+VOID
+EFIAPI
+ExitDriver (
+ IN EFI_STATUS Status
+ )
+{
+ if (EFI_ERROR (Status)) {
+ ProcessLibraryDestructorList (gImageHandle, gST);
+ }
+ gBS->Exit (gImageHandle, Status, 0, NULL);
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gDriverUnloadImageCount = 0U;
+
+EFI_STATUS
+EFIAPI
+ProcessModuleUnloadList (
+ IN EFI_HANDLE ImageHandle
+ )
+{
+ return EFI_SUCCESS;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/Efi_Defs.h b/efi_memtest/memtest86+/efi/Include/Efi_Defs.h
new file mode 100644
index 0000000..a99287d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Efi_Defs.h
@@ -0,0 +1,28 @@
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include "Uefi.h"
+
+extern GUID gEfiCallerIdGuid;
+extern CHAR8 *gEfiCallerBaseName;
+
+
+
+// Definition of SkuId Array
+/*extern UINT64 _gPcd_SkuId_Array[];
+*/
+
+EFI_STATUS
+EFIAPI
+UefiMain (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+
+#ifdef __cplusplus
+}
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Efi_Defs_GUID.h b/efi_memtest/memtest86+/efi/Include/Efi_Defs_GUID.h
new file mode 100644
index 0000000..f468b54
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Efi_Defs_GUID.h
@@ -0,0 +1,124 @@
+#ifndef __EFI_DEFS_GUID_H__
+#define __EFI_DEFS_GUID_H__
+
+/*
+ * Guids
+ */
+#define ACPI_TABLE_GUID {0xEB9D2D30, 0x2D88, 0x11D3, { 0x9A, 0x16, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D}}
+extern EFI_GUID gEfiAcpiTableGuid;
+
+#define EFI_ACPI_TABLE_GUID {0x8868E871, 0xE4F1, 0x11D3, { 0xBC, 0x22, 0x00, 0x80, 0xC7, 0x3C, 0x88, 0x81}}
+
+#define EFI_ACPI_10_TABLE_GUID ACPI_TABLE_GUID
+extern EFI_GUID gEfiAcpi10TableGuid;
+
+// ACPI 2.0 or newer tables should use EFI_ACPI_TABLE_GUID.
+#define EFI_ACPI_20_TABLE_GUID EFI_ACPI_TABLE_GUID
+extern EFI_GUID gEfiAcpi20TableGuid;
+
+#define EFI_CALLER_ID_GUID {0x51d8cae0, 0x272a, 0x661f, {0xa8, 0xd9, 0x84, 0x51, 0xdf, 0xf0, 0xeb, 0xd0}}
+extern EFI_GUID gEfiCallerIdGUID;
+
+#define EFI_EVENT_GROUP_READY_TO_BOOT { 0x7ce88fb3, 0x4bd7, 0x4679, { 0x87, 0xa8, 0xa8, 0xd8, 0xde, 0xe5, 0x0d, 0x2b }}
+extern EFI_GUID gEfiEventReadyToBootGuid;
+
+#define EFI_EVENT_LEGACY_BOOT_GUID { 0x2a571201, 0x4966, 0x47f6, {0x8b, 0x86, 0xf3, 0x1e, 0x41, 0xf3, 0x2f, 0x10 }}
+extern EFI_GUID gEfiEventLegacyBootGuid;
+
+#define EFI_GLOBAL_VARIABLE { 0x8BE4DF61, 0x93CA, 0x11d2, {0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8C }}
+extern EFI_GUID gEfiGlobalVariableGuid;
+
+#define EFI_PC_ANSI_GUID { 0xe0c14753, 0xf9be, 0x11d2, {0x9a, 0x0c, 0x00, 0x90, 0x27, 0x3f, 0xc1, 0x4d }}
+extern EFI_GUID gEfiPcAnsiGuid;
+
+#define EFI_VT_100_GUID { 0xdfa66065, 0xb419, 0x11d3, {0x9a, 0x2d, 0x00, 0x90, 0x27, 0x3f, 0xc1, 0x4d }}
+extern EFI_GUID gEfiVT100Guid;
+
+#define EFI_VT_100_PLUS_GUID { 0x7baec70b, 0x57e0, 0x4c76, {0x8e, 0x87, 0x2f, 0x9e, 0x28, 0x08, 0x83, 0x43 }}
+extern EFI_GUID gEfiVT100PlusGuid;
+
+#define EFI_VT_UTF8_GUID { 0xad15a0d6, 0x8bec, 0x4acf, {0xa0, 0x73, 0xd0, 0x1d, 0xe7, 0x7e, 0x2d, 0x88 }}
+extern EFI_GUID gEfiVTUTF8Guid;
+
+#define DEVICE_PATH_MESSAGING_UART_FLOW_CONTROL { 0x37499a9d, 0x542f, 0x4c89, {0xa0, 0x26, 0x35, 0xda, 0x14, 0x20, 0x94, 0xe4 }}
+extern EFI_GUID gEfiUartDevicePathGuid;
+
+#define EFI_SAS_DEVICE_PATH_GUID { 0xd487ddb4, 0x008b, 0x11d9, {0xaf, 0xdc, 0x00, 0x10, 0x83, 0xff, 0xca, 0x4d }}
+extern EFI_GUID gEfiSasDevicePathGuid;
+
+#define SMBIOS_TABLE_GUID {0xeb9d2d31,0x2d88,0x11d3, {0x9a,0x16,0x0,0x90,0x27,0x3f,0xc1,0x4d}};
+extern EFI_GUID gEfiSmbiosGuid;
+
+#define SMBIOS3_TABLE_GUID {0xf2fd1544, 0x9794, 0x4a2c, {0x99,0x2e,0xe5,0xbb,0xcf,0x20,0xe3,0x94}}
+extern EFI_GUID gEfiSmbios3Guid;
+
+/*
+ * Protocols
+ */
+#define EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_GUID { 0x964E5B22, 0x6459, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }}
+extern EFI_GUID gEfiSimpleFileSystemProtocolGuid;
+
+#define EFI_FILE_SYSTEM_INFO_ID { 0x9576e93, 0x6d3f, 0x11d2, {0x8e, 0x39, 0x0, 0xa0, 0xc9, 0x69, 0x72, 0x3b }}
+extern EFI_GUID gEfiFileSystemInfoGuid;
+
+#define EFI_LOADED_IMAGE_PROTOCOL_GUID {0x5B1B31A1,0x9562,0x11d2,{0x8E,0x3F,0x00,0xA0,0xC9,0x69,0x72,0x3B}}
+extern EFI_GUID gEfiLoadedImageProtocolGuid;
+
+
+#endif
+
+// Guids
+/*extern EFI_GUID gEfiMdePkgTokenSpaceGuid;
+extern EFI_GUID gEfiVirtualDiskGuid;
+extern EFI_GUID gEfiVirtualCdGuid;
+extern EFI_GUID gEfiPersistentVirtualDiskGuid;
+extern EFI_GUID gEfiPersistentVirtualCdGuid;
+extern EFI_GUID gEfiEventReadyToBootGuid;
+extern EFI_GUID gEfiEventLegacyBootGuid;
+*/
+
+
+
+// Protocols
+/*extern EFI_GUID gEfiDevicePathProtocolGuid;
+extern EFI_GUID gEfiDebugPortProtocolGuid;
+extern EFI_GUID gEfiDriverBindingProtocolGuid;
+extern EFI_GUID gEfiSimpleTextOutProtocolGuid;
+extern EFI_GUID gEfiGraphicsOutputProtocolGuid;
+extern EFI_GUID gEfiHiiFontProtocolGuid; */
+/*
+extern EFI_GUID gEfiUgaDrawProtocolGuid;
+extern EFI_GUID gEfiComponentNameProtocolGuid;
+extern EFI_GUID gEfiComponentName2ProtocolGuid;
+extern EFI_GUID gEfiDriverConfigurationProtocolGuid;
+extern EFI_GUID gEfiDriverConfiguration2ProtocolGuid;
+extern EFI_GUID gEfiDriverDiagnosticsProtocolGuid;
+extern EFI_GUID gEfiDriverDiagnostics2ProtocolGuid;*/
+
+
+/*#ifndef __EVENT_GROUP_GUID__
+#define __EVENT_GROUP_GUID__
+#define EFI_EVENT_GROUP_EXIT_BOOT_SERVICES \
+ { 0x27abf055, 0xb1b8, 0x4c26, { 0x80, 0x48, 0x74, 0x8f, 0x37, 0xba, 0xa2, 0xdf } }
+extern EFI_GUID gEfiEventExitBootServicesGuid;
+#define EFI_EVENT_GROUP_VIRTUAL_ADDRESS_CHANGE \
+ { 0x13fa7698, 0xc831, 0x49c7, { 0x87, 0xea, 0x8f, 0x43, 0xfc, 0xc2, 0x51, 0x96 } }
+extern EFI_GUID gEfiEventVirtualAddressChangeGuid;
+#define EFI_EVENT_GROUP_MEMORY_MAP_CHANGE \
+ { 0x78bee926, 0x692f, 0x48fd, { 0x9e, 0xdb, 0x1, 0x42, 0x2e, 0xf0, 0xd7, 0xab } }
+extern EFI_GUID gEfiEventMemoryMapChangeGuid;
+#define EFI_EVENT_GROUP_DXE_DISPATCH_GUID \
+ { 0x7081e22f, 0xcac6, 0x4053, { 0x94, 0x68, 0x67, 0x57, 0x82, 0xcf, 0x88, 0xe5 }}
+extern EFI_GUID gEfiEventDxeDispatchGuid;
+#define EFI_END_OF_DXE_EVENT_GROUP_GUID \
+ { 0x2ce967a, 0xdd7e, 0x4ffc, { 0x9e, 0xe7, 0x81, 0xc, 0xf0, 0x47, 0x8, 0x80 } }
+extern EFI_GUID gEfiEndOfDxeEventGroupGuid;
+#endif*/
+
+/*#ifndef __EFI_HII_FORMMAP_GUID_H__
+#define __EFI_HII_FORMMAP_GUID_H__
+#define EFI_HII_STANDARD_FORM_GUID \
+ { 0x3bd2f4ec, 0xe524, 0x46e4, { 0xa9, 0xd8, 0x51, 0x1, 0x17, 0x42, 0x55, 0x62 } }
+extern EFI_GUID gEfiHiiStandardFormGuid;
+#endif*/
+
diff --git a/efi_memtest/memtest86+/efi/Include/Efi_Defs_Pcd.h b/efi_memtest/memtest86+/efi/Include/Efi_Defs_Pcd.h
new file mode 100644
index 0000000..7f756d1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Efi_Defs_Pcd.h
@@ -0,0 +1,13 @@
+#define _PCD_GET_MODE_32_PcdMaximumAsciiStringLength 1000000U
+#define _PCD_GET_MODE_32_PcdMaximumUnicodeStringLength 1000000U
+#define _PCD_GET_MODE_32_PcdDebugPrintErrorLevel 0x80000000U
+#define _PCD_GET_MODE_8_PcdDebugClearMemoryValue 0xAFU
+#define _PCD_GET_MODE_8_PcdDebugPropertyMask 0U
+#define _PCD_GET_MODE_32_PcdFixedDebugPrintErrorLevel 0xFFFFFFFFU
+#define _PCD_GET_MODE_32_PcdMaximumDevicePathNodeCount 0U
+#define _PCD_GET_MODE_BOOL_PcdDriverDiagnosticsDisable ((BOOLEAN)0U)
+#define _PCD_GET_MODE_BOOL_PcdComponentNameDisable ((BOOLEAN)0U)
+#define _PCD_GET_MODE_BOOL_PcdDriverDiagnostics2Disable ((BOOLEAN)0U)
+#define _PCD_GET_MODE_BOOL_PcdComponentName2Disable ((BOOLEAN)0U)
+#define _PCD_GET_MODE_BOOL_PcdUgaConsumeSupport ((BOOLEAN)1U)
+#define _PCD_GET_MODE_32_PcdUefiLibMaxPrintBufferSize 320U \ No newline at end of file
diff --git a/efi_memtest/memtest86+/efi/Include/GccBase.lds b/efi_memtest/memtest86+/efi/Include/GccBase.lds
index a9dd213..86d4eed 100644
--- a/efi_memtest/memtest86+/efi/Include/GccBase.lds
+++ b/efi_memtest/memtest86+/efi/Include/GccBase.lds
@@ -26,14 +26,14 @@ SECTIONS {
*(.got .got.*)
/*
- * The contents of AutoGen.c files are mostly constant from the POV of the
+ * The contents of Efi_Defs.c files are mostly constant from the POV of the
* program, but most of it ends up in .data or .bss by default since few of
* the variable definitions that get emitted are declared as CONST.
* Unfortunately, we cannot pull it into the .text section entirely, since
* patchable PCDs are also emitted here, but we can at least move all of the
* emitted GUIDs here.
*/
- *:AutoGen.obj(.data.g*Guid)
+ *:Efi_Defs.obj(.data.g*Guid)
}
/*
diff --git a/efi_memtest/memtest86+/efi/Include/Guid/FileSystemInfo.h b/efi_memtest/memtest86+/efi/Include/Guid/FileSystemInfo.h
index 762cb94..ad14ec4 100644
--- a/efi_memtest/memtest86+/efi/Include/Guid/FileSystemInfo.h
+++ b/efi_memtest/memtest86+/efi/Include/Guid/FileSystemInfo.h
@@ -8,14 +8,11 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
**/
+#include "Efi_Defs_GUID.h"
+
#ifndef __FILE_SYSTEM_INFO_H__
#define __FILE_SYSTEM_INFO_H__
-#define EFI_FILE_SYSTEM_INFO_ID \
- { \
- 0x9576e93, 0x6d3f, 0x11d2, {0x8e, 0x39, 0x0, 0xa0, 0xc9, 0x69, 0x72, 0x3b } \
- }
-
typedef struct {
///
/// The size of the EFI_FILE_SYSTEM_INFO structure, including the Null-terminated VolumeLabel string.
@@ -52,6 +49,4 @@ typedef struct {
///
#define SIZE_OF_EFI_FILE_SYSTEM_INFO OFFSET_OF (EFI_FILE_SYSTEM_INFO, VolumeLabel)
-extern EFI_GUID gEfiFileSystemInfoGuid;
-
#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Guid/GlobalVariable.h b/efi_memtest/memtest86+/efi/Include/Guid/GlobalVariable.h
new file mode 100644
index 0000000..3a1b1ef
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Guid/GlobalVariable.h
@@ -0,0 +1,181 @@
+/** @file
+ GUID for EFI (NVRAM) Variables.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+ @par Revision Reference:
+ GUID defined in UEFI 2.1
+**/
+
+#ifndef __GLOBAL_VARIABLE_GUID_H__
+#define __GLOBAL_VARIABLE_GUID_H__
+
+#include "Efi_Defs_GUID.h"
+
+//
+// Follow UEFI 2.4 spec:
+// To prevent name collisions with possible future globally defined variables,
+// other internal firmware data variables that are not defined here must be
+// saved with a unique VendorGuid other than EFI_GLOBAL_VARIABLE or
+// any other GUID defined by the UEFI Specification. Implementations must
+// only permit the creation of variables with a UEFI Specification-defined
+// VendorGuid when these variables are documented in the UEFI Specification.
+//
+// Note: except the globally defined variables defined below, the spec also defines
+// L"Boot####" - A boot load option.
+// L"Driver####" - A driver load option.
+// L"SysPrep####" - A System Prep application load option.
+// L"Key####" - Describes hot key relationship with a Boot#### load option.
+// The attribute for them is NV+BS+RT, #### is a printed hex value, and no 0x or h
+// is included in the hex value. They can not be expressed as a #define like other globally
+// defined variables, it is because we can not list the Boot0000, Boot0001, etc one by one.
+//
+
+///
+/// The language codes that the firmware supports. This value is deprecated.
+/// Its attribute is BS+RT.
+///
+#define EFI_LANG_CODES_VARIABLE_NAME L"LangCodes"
+///
+/// The language code that the system is configured for. This value is deprecated.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_LANG_VARIABLE_NAME L"Lang"
+///
+/// The firmware's boot managers timeout, in seconds, before initiating the default boot selection.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_TIME_OUT_VARIABLE_NAME L"Timeout"
+///
+/// The language codes that the firmware supports.
+/// Its attribute is BS+RT.
+///
+#define EFI_PLATFORM_LANG_CODES_VARIABLE_NAME L"PlatformLangCodes"
+///
+/// The language code that the system is configured for.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_PLATFORM_LANG_VARIABLE_NAME L"PlatformLang"
+///
+/// The device path of the default input/output/error output console.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_CON_IN_VARIABLE_NAME L"ConIn"
+#define EFI_CON_OUT_VARIABLE_NAME L"ConOut"
+#define EFI_ERR_OUT_VARIABLE_NAME L"ErrOut"
+///
+/// The device path of all possible input/output/error output devices.
+/// Its attribute is BS+RT.
+///
+#define EFI_CON_IN_DEV_VARIABLE_NAME L"ConInDev"
+#define EFI_CON_OUT_DEV_VARIABLE_NAME L"ConOutDev"
+#define EFI_ERR_OUT_DEV_VARIABLE_NAME L"ErrOutDev"
+///
+/// The ordered boot option load list.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_BOOT_ORDER_VARIABLE_NAME L"BootOrder"
+///
+/// The boot option for the next boot only.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_BOOT_NEXT_VARIABLE_NAME L"BootNext"
+///
+/// The boot option that was selected for the current boot.
+/// Its attribute is BS+RT.
+///
+#define EFI_BOOT_CURRENT_VARIABLE_NAME L"BootCurrent"
+///
+/// The types of boot options supported by the boot manager. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_BOOT_OPTION_SUPPORT_VARIABLE_NAME L"BootOptionSupport"
+///
+/// The ordered driver load option list.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_DRIVER_ORDER_VARIABLE_NAME L"DriverOrder"
+///
+/// The ordered System Prep Application load option list.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_SYS_PREP_ORDER_VARIABLE_NAME L"SysPrepOrder"
+///
+/// Identifies the level of hardware error record persistence
+/// support implemented by the platform. This variable is
+/// only modified by firmware and is read-only to the OS.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_HW_ERR_REC_SUPPORT_VARIABLE_NAME L"HwErrRecSupport"
+///
+/// Whether the system is operating in setup mode (1) or not (0).
+/// All other values are reserved. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_SETUP_MODE_NAME L"SetupMode"
+///
+/// The Key Exchange Key Signature Database.
+/// Its attribute is NV+BS+RT+AT.
+///
+#define EFI_KEY_EXCHANGE_KEY_NAME L"KEK"
+///
+/// The public Platform Key.
+/// Its attribute is NV+BS+RT+AT.
+///
+#define EFI_PLATFORM_KEY_NAME L"PK"
+///
+/// Array of GUIDs representing the type of signatures supported
+/// by the platform firmware. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_SIGNATURE_SUPPORT_NAME L"SignatureSupport"
+///
+/// Whether the platform firmware is operating in Secure boot mode (1) or not (0).
+/// All other values are reserved. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_SECURE_BOOT_MODE_NAME L"SecureBoot"
+///
+/// The OEM's default Key Exchange Key Signature Database. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_KEK_DEFAULT_VARIABLE_NAME L"KEKDefault"
+///
+/// The OEM's default public Platform Key. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_PK_DEFAULT_VARIABLE_NAME L"PKDefault"
+///
+/// The OEM's default secure boot signature store. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_DB_DEFAULT_VARIABLE_NAME L"dbDefault"
+///
+/// The OEM's default secure boot blacklist signature store. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_DBX_DEFAULT_VARIABLE_NAME L"dbxDefault"
+///
+/// The OEM's default secure boot timestamp signature store. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_DBT_DEFAULT_VARIABLE_NAME L"dbtDefault"
+///
+/// Allows the firmware to indicate supported features and actions to the OS.
+/// Its attribute is BS+RT.
+///
+#define EFI_OS_INDICATIONS_SUPPORT_VARIABLE_NAME L"OsIndicationsSupported"
+///
+/// Allows the OS to request the firmware to enable certain features and to take certain actions.
+/// Its attribute is NV+BS+RT.
+///
+#define EFI_OS_INDICATIONS_VARIABLE_NAME L"OsIndications"
+///
+/// Whether the system is configured to use only vendor provided
+/// keys or not. Should be treated as read-only.
+/// Its attribute is BS+RT.
+///
+#define EFI_VENDOR_KEYS_VARIABLE_NAME L"VendorKeys"
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Guid/HiiFormMapMethodGuid.h b/efi_memtest/memtest86+/efi/Include/Guid/HiiFormMapMethodGuid.h
deleted file mode 100644
index 4ff22a8..0000000
--- a/efi_memtest/memtest86+/efi/Include/Guid/HiiFormMapMethodGuid.h
+++ /dev/null
@@ -1,19 +0,0 @@
-/** @file
- Guid used to identify HII FormMap configuration method.
-
- Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.<BR>
- SPDX-License-Identifier: BSD-2-Clause-Patent
-
- @par Revision Reference:
- GUID defined in UEFI 2.2 spec.
-**/
-
-#ifndef __EFI_HII_FORMMAP_GUID_H__
-#define __EFI_HII_FORMMAP_GUID_H__
-
-#define EFI_HII_STANDARD_FORM_GUID \
- { 0x3bd2f4ec, 0xe524, 0x46e4, { 0xa9, 0xd8, 0x51, 0x1, 0x17, 0x42, 0x55, 0x62 } }
-
-extern EFI_GUID gEfiHiiStandardFormGuid;
-
-#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Guid/PcAnsi.h b/efi_memtest/memtest86+/efi/Include/Guid/PcAnsi.h
deleted file mode 100644
index fd1f055..0000000
--- a/efi_memtest/memtest86+/efi/Include/Guid/PcAnsi.h
+++ /dev/null
@@ -1,52 +0,0 @@
-/** @file
- Terminal Device Path Vendor Guid.
-
- Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
- SPDX-License-Identifier: BSD-2-Clause-Patent
-
- @par Revision Reference:
- GUIDs defined in UEFI 2.0 spec.
-
-**/
-
-#ifndef __PC_ANSI_H__
-#define __PC_ANSI_H__
-
-#define EFI_PC_ANSI_GUID \
- { \
- 0xe0c14753, 0xf9be, 0x11d2, {0x9a, 0x0c, 0x00, 0x90, 0x27, 0x3f, 0xc1, 0x4d } \
- }
-
-#define EFI_VT_100_GUID \
- { \
- 0xdfa66065, 0xb419, 0x11d3, {0x9a, 0x2d, 0x00, 0x90, 0x27, 0x3f, 0xc1, 0x4d } \
- }
-
-#define EFI_VT_100_PLUS_GUID \
- { \
- 0x7baec70b, 0x57e0, 0x4c76, {0x8e, 0x87, 0x2f, 0x9e, 0x28, 0x08, 0x83, 0x43 } \
- }
-
-#define EFI_VT_UTF8_GUID \
- { \
- 0xad15a0d6, 0x8bec, 0x4acf, {0xa0, 0x73, 0xd0, 0x1d, 0xe7, 0x7e, 0x2d, 0x88 } \
- }
-
-#define DEVICE_PATH_MESSAGING_UART_FLOW_CONTROL \
- { \
- 0x37499a9d, 0x542f, 0x4c89, {0xa0, 0x26, 0x35, 0xda, 0x14, 0x20, 0x94, 0xe4 } \
- }
-
-#define EFI_SAS_DEVICE_PATH_GUID \
- { \
- 0xd487ddb4, 0x008b, 0x11d9, {0xaf, 0xdc, 0x00, 0x10, 0x83, 0xff, 0xca, 0x4d } \
- }
-
-extern EFI_GUID gEfiPcAnsiGuid;
-extern EFI_GUID gEfiVT100Guid;
-extern EFI_GUID gEfiVT100PlusGuid;
-extern EFI_GUID gEfiVTUTF8Guid;
-extern EFI_GUID gEfiUartDevicePathGuid;
-extern EFI_GUID gEfiSasDevicePathGuid;
-
-#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/BaseMemoryLib.h b/efi_memtest/memtest86+/efi/Include/Library/BaseMemoryLib.h
new file mode 100644
index 0000000..a378ed1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/BaseMemoryLib.h
@@ -0,0 +1,484 @@
+/** @file
+ Provides copy memory, fill memory, zero memory, and GUID functions.
+
+ The Base Memory Library provides optimized implementations for common memory-based operations.
+ These functions should be used in place of coding your own loops to do equivalent common functions.
+ This allows optimized library implementations to help increase performance.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#include "Base.h"
+
+#ifndef __BASE_MEMORY_LIB__
+#define __BASE_MEMORY_LIB__
+
+/**
+ Copies a source buffer to a destination buffer, and returns the destination buffer.
+
+ This function copies Length bytes from SourceBuffer to DestinationBuffer, and returns
+ DestinationBuffer. The implementation must be reentrant, and it must handle the case
+ where SourceBuffer overlaps DestinationBuffer.
+
+ If Length is greater than (MAX_ADDRESS - DestinationBuffer + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - SourceBuffer + 1), then ASSERT().
+
+ @param DestinationBuffer The pointer to the destination buffer of the memory copy.
+ @param SourceBuffer The pointer to the source buffer of the memory copy.
+ @param Length The number of bytes to copy from SourceBuffer to DestinationBuffer.
+
+ @return DestinationBuffer.
+
+**/
+VOID *
+EFIAPI
+CopyMem (
+ OUT VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ );
+
+/**
+ Fills a target buffer with a byte value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with Value, and returns Buffer.
+
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The memory to set.
+ @param Length The number of bytes to set.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ );
+
+/**
+ Fills a target buffer with a 16-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 16-bit value specified by
+ Value, and returns Buffer. Value is repeated every 16-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem16 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ );
+
+/**
+ Fills a target buffer with a 32-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 32-bit value specified by
+ Value, and returns Buffer. Value is repeated every 32-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem32 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ );
+
+/**
+ Fills a target buffer with a 64-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 64-bit value specified by
+ Value, and returns Buffer. Value is repeated every 64-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem64 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ );
+
+/**
+ Fills a target buffer with a value that is size UINTN, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the UINTN sized value specified by
+ Value, and returns Buffer. Value is repeated every sizeof(UINTN) bytes for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a UINTN boundary, then ASSERT().
+ If Length is not aligned on a UINTN boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMemN (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINTN Value
+ );
+
+/**
+ Fills a target buffer with zeros, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with zeros, and returns Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill with zeros.
+ @param Length The number of bytes in Buffer to fill with zeros.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+ZeroMem (
+ OUT VOID *Buffer,
+ IN UINTN Length
+ );
+
+/**
+ Compares the contents of two buffers.
+
+ This function compares Length bytes of SourceBuffer to Length bytes of DestinationBuffer.
+ If all Length bytes of the two buffers are identical, then 0 is returned. Otherwise, the
+ value returned is the first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+ If Length > 0 and DestinationBuffer is NULL, then ASSERT().
+ If Length > 0 and SourceBuffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - DestinationBuffer + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - SourceBuffer + 1), then ASSERT().
+
+ @param DestinationBuffer The pointer to the destination buffer to compare.
+ @param SourceBuffer The pointer to the source buffer to compare.
+ @param Length The number of bytes to compare.
+
+ @return 0 All Length bytes of the two buffers are identical.
+ @retval Non-zero The first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+**/
+INTN
+EFIAPI
+CompareMem (
+ IN CONST VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ );
+
+/**
+ Scans a target buffer for an 8-bit value, and returns a pointer to the matching 8-bit value
+ in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from the lowest
+ address to the highest address for an 8-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanMem8 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ );
+
+/**
+ Scans a target buffer for a 16-bit value, and returns a pointer to the matching 16-bit value
+ in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 16-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanMem16 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ );
+
+/**
+ Scans a target buffer for a 32-bit value, and returns a pointer to the matching 32-bit value
+ in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 32-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanMem32 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ );
+
+/**
+ Scans a target buffer for a 64-bit value, and returns a pointer to the matching 64-bit value
+ in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 64-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanMem64 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ );
+
+/**
+ Scans a target buffer for a UINTN sized value, and returns a pointer to the matching
+ UINTN sized value in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from the lowest
+ address to the highest address for a UINTN sized value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a UINTN boundary, then ASSERT().
+ If Length is not aligned on a UINTN boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanMemN (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINTN Value
+ );
+
+/**
+ Copies a source GUID to a destination GUID.
+
+ This function copies the contents of the 128-bit GUID specified by SourceGuid to
+ DestinationGuid, and returns DestinationGuid.
+
+ If DestinationGuid is NULL, then ASSERT().
+ If SourceGuid is NULL, then ASSERT().
+
+ @param DestinationGuid The pointer to the destination GUID.
+ @param SourceGuid The pointer to the source GUID.
+
+ @return DestinationGuid.
+
+**/
+GUID *
+EFIAPI
+CopyGuid (
+ OUT GUID *DestinationGuid,
+ IN CONST GUID *SourceGuid
+ );
+
+/**
+ Compares two GUIDs.
+
+ This function compares Guid1 to Guid2. If the GUIDs are identical then TRUE is returned.
+ If there are any bit differences in the two GUIDs, then FALSE is returned.
+
+ If Guid1 is NULL, then ASSERT().
+ If Guid2 is NULL, then ASSERT().
+
+ @param Guid1 A pointer to a 128 bit GUID.
+ @param Guid2 A pointer to a 128 bit GUID.
+
+ @retval TRUE Guid1 and Guid2 are identical.
+ @retval FALSE Guid1 and Guid2 are not identical.
+
+**/
+BOOLEAN
+EFIAPI
+CompareGuid (
+ IN CONST GUID *Guid1,
+ IN CONST GUID *Guid2
+ );
+
+/**
+ Scans a target buffer for a GUID, and returns a pointer to the matching GUID
+ in the target buffer.
+
+ This function searches target the buffer specified by Buffer and Length from
+ the lowest address to the highest address at 128-bit increments for the 128-bit
+ GUID value that matches Guid. If a match is found, then a pointer to the matching
+ GUID in the target buffer is returned. If no match is found, then NULL is returned.
+ If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 128-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Guid The value to search for in the target buffer.
+
+ @return A pointer to the matching Guid in the target buffer, otherwise NULL.
+
+**/
+VOID *
+EFIAPI
+ScanGuid (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN CONST GUID *Guid
+ );
+
+/**
+ Checks if the given GUID is a zero GUID.
+
+ This function checks whether the given GUID is a zero GUID. If the GUID is
+ identical to a zero GUID then TRUE is returned. Otherwise, FALSE is returned.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid The pointer to a 128 bit GUID.
+
+ @retval TRUE Guid is a zero GUID.
+ @retval FALSE Guid is not a zero GUID.
+
+**/
+BOOLEAN
+EFIAPI
+IsZeroGuid (
+ IN CONST GUID *Guid
+ );
+
+/**
+ Checks if the contents of a buffer are all zeros.
+
+ This function checks whether the contents of a buffer are all zeros. If the
+ contents are all zeros, return TRUE. Otherwise, return FALSE.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to be checked.
+ @param Length The size of the buffer (in bytes) to be checked.
+
+ @retval TRUE Contents of the buffer are all zeros.
+ @retval FALSE Contents of the buffer are not all zeros.
+
+**/
+BOOLEAN
+EFIAPI
+IsZeroBuffer (
+ IN CONST VOID *Buffer,
+ IN UINTN Length
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/DebugPrintErrorLevelLib.h b/efi_memtest/memtest86+/efi/Include/Library/DebugPrintErrorLevelLib.h
new file mode 100644
index 0000000..6992ec8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/DebugPrintErrorLevelLib.h
@@ -0,0 +1,37 @@
+/** @file
+ Debug Print Error Level Library class
+
+ Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#ifndef _DEBUG_PRINT_ERROR_LEVEL_LIB_H_
+#define _DEBUG_PRINT_ERROR_LEVEL_LIB_H_
+
+/**
+ Returns the debug print error level mask for the current module.
+
+ @return Debug print error level mask for the current module.
+
+**/
+UINT32
+EFIAPI
+GetDebugPrintErrorLevel (
+ VOID
+ );
+
+/**
+ Sets the global debug print error level mask fpr the entire platform.
+
+ @param ErrorLevel Global debug print error level
+
+ @retval TRUE The debug print error level mask was successfully set.
+ @retval FALSE The debug print error level mask could not be set.
+
+**/
+BOOLEAN
+EFIAPI
+SetDebugPrintErrorLevel (
+ UINT32 ErrorLevel
+ );
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/DevicePathLib.h b/efi_memtest/memtest86+/efi/Include/Library/DevicePathLib.h
new file mode 100644
index 0000000..26361fe
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/DevicePathLib.h
@@ -0,0 +1,561 @@
+/** @file
+ Provides library functions to construct and parse UEFI Device Paths.
+
+ This library provides defines, macros, and functions to help create and parse
+ EFI_DEVICE_PATH_PROTOCOL structures.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __DEVICE_PATH_LIB_H__
+#define __DEVICE_PATH_LIB_H__
+
+#define END_DEVICE_PATH_LENGTH (sizeof (EFI_DEVICE_PATH_PROTOCOL))
+
+/**
+ Determine whether a given device path is valid.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param MaxSize The maximum size of the device path data structure.
+
+ @retval TRUE DevicePath is valid.
+ @retval FALSE DevicePath is NULL.
+ @retval FALSE Maxsize is less than sizeof(EFI_DEVICE_PATH_PROTOCOL).
+ @retval FALSE The length of any node node in the DevicePath is less
+ than sizeof (EFI_DEVICE_PATH_PROTOCOL).
+ @retval FALSE If MaxSize is not zero, the size of the DevicePath
+ exceeds MaxSize.
+ @retval FALSE If PcdMaximumDevicePathNodeCount is not zero, the node
+ count of the DevicePath exceeds PcdMaximumDevicePathNodeCount.
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathValid (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN UINTN MaxSize
+ );
+
+/**
+ Returns the Type field of a device path node.
+
+ Returns the Type field of the device path node specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The Type field of the device path node specified by Node.
+
+**/
+UINT8
+EFIAPI
+DevicePathType (
+ IN CONST VOID *Node
+ );
+
+/**
+ Returns the SubType field of a device path node.
+
+ Returns the SubType field of the device path node specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The SubType field of the device path node specified by Node.
+
+**/
+UINT8
+EFIAPI
+DevicePathSubType (
+ IN CONST VOID *Node
+ );
+
+/**
+ Returns the 16-bit Length field of a device path node.
+
+ Returns the 16-bit Length field of the device path node specified by Node.
+ Node is not required to be aligned on a 16-bit boundary, so it is recommended
+ that a function such as ReadUnaligned16() be used to extract the contents of
+ the Length field.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The 16-bit Length field of the device path node specified by Node.
+
+**/
+UINTN
+EFIAPI
+DevicePathNodeLength (
+ IN CONST VOID *Node
+ );
+
+/**
+ Returns a pointer to the next node in a device path.
+
+ Returns a pointer to the device path node that follows the device path node specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return a pointer to the device path node that follows the device path node specified by Node.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+NextDevicePathNode (
+ IN CONST VOID *Node
+ );
+
+/**
+ Determines if a device path node is an end node of a device path.
+ This includes nodes that are the end of a device path instance and nodes that
+ are the end of an entire device path.
+
+ Determines if the device path node specified by Node is an end node of a device path.
+ This includes nodes that are the end of a device path instance and nodes that are the
+ end of an entire device path. If Node represents an end node of a device path,
+ then TRUE is returned. Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is an end node of a device path.
+ @retval FALSE The device path node specified by Node is not an end node of a device path.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEndType (
+ IN CONST VOID *Node
+ );
+
+/**
+ Determines if a device path node is an end node of an entire device path.
+
+ Determines if a device path node specified by Node is an end node of an entire device path.
+ If Node represents the end of an entire device path, then TRUE is returned.
+ Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is the end of an entire device path.
+ @retval FALSE The device path node specified by Node is not the end of an entire device path.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEnd (
+ IN CONST VOID *Node
+ );
+
+/**
+ Determines if a device path node is an end node of a device path instance.
+
+ Determines if a device path node specified by Node is an end node of a device path instance.
+ If Node represents the end of a device path instance, then TRUE is returned.
+ Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is the end of a device path instance.
+ @retval FALSE The device path node specified by Node is not the end of a device path instance.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEndInstance (
+ IN CONST VOID *Node
+ );
+
+/**
+ Sets the length, in bytes, of a device path node.
+
+ Sets the length of the device path node specified by Node to the value specified
+ by NodeLength. NodeLength is returned. Node is not required to be aligned on
+ a 16-bit boundary, so it is recommended that a function such as WriteUnaligned16()
+ be used to set the contents of the Length field.
+
+ If Node is NULL, then ASSERT().
+ If NodeLength >= 0x10000, then ASSERT().
+ If NodeLength < sizeof (EFI_DEVICE_PATH_PROTOCOL), then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+ @param Length The length, in bytes, of the device path node.
+
+ @return Length
+
+**/
+UINT16
+EFIAPI
+SetDevicePathNodeLength (
+ IN OUT VOID *Node,
+ IN UINTN Length
+ );
+
+/**
+ Fills in all the fields of a device path node that is the end of an entire device path.
+
+ Fills in all the fields of a device path node specified by Node so Node represents
+ the end of an entire device path. The Type field of Node is set to
+ END_DEVICE_PATH_TYPE, the SubType field of Node is set to
+ END_ENTIRE_DEVICE_PATH_SUBTYPE, and the Length field of Node is set to
+ END_DEVICE_PATH_LENGTH. Node is not required to be aligned on a 16-bit boundary,
+ so it is recommended that a function such as WriteUnaligned16() be used to set
+ the contents of the Length field.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+**/
+VOID
+EFIAPI
+SetDevicePathEndNode (
+ OUT VOID *Node
+ );
+
+/**
+ Returns the size of a device path in bytes.
+
+ This function returns the size, in bytes, of the device path data structure
+ specified by DevicePath including the end of device path node.
+ If DevicePath is NULL or invalid, then 0 is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval 0 If DevicePath is NULL or invalid.
+ @retval Others The size of a device path in bytes.
+
+**/
+UINTN
+EFIAPI
+GetDevicePathSize (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Creates a new copy of an existing device path.
+
+ This function allocates space for a new copy of the device path specified by DevicePath. If
+ DevicePath is NULL, then NULL is returned. If the memory is successfully allocated, then the
+ contents of DevicePath are copied to the newly allocated buffer, and a pointer to that buffer
+ is returned. Otherwise, NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval NULL DevicePath is NULL or invalid.
+ @retval Others A pointer to the duplicated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DuplicateDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Creates a new device path by appending a second device path to a first device path.
+
+ This function creates a new device path by appending a copy of SecondDevicePath to a copy of
+ FirstDevicePath in a newly allocated buffer. Only the end-of-device-path device node from
+ SecondDevicePath is retained. The newly created device path is returned.
+ If FirstDevicePath is NULL, then it is ignored, and a duplicate of SecondDevicePath is returned.
+ If SecondDevicePath is NULL, then it is ignored, and a duplicate of FirstDevicePath is returned.
+ If both FirstDevicePath and SecondDevicePath are NULL, then a copy of an end-of-device-path is
+ returned.
+ If there is not enough memory for the newly allocated buffer, then NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory. It is the
+ responsibility of the caller to free the memory allocated.
+
+ @param FirstDevicePath A pointer to a device path data structure.
+ @param SecondDevicePath A pointer to a device path data structure.
+
+ @retval NULL If there is not enough memory for the newly allocated buffer.
+ @retval NULL If FirstDevicePath or SecondDevicePath is invalid.
+ @retval Others A pointer to the new device path if success.
+ Or a copy an end-of-device-path if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *FirstDevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath OPTIONAL
+ );
+
+/**
+ Creates a new path by appending the device node to the device path.
+
+ This function creates a new device path by appending a copy of the device node specified by
+ DevicePathNode to a copy of the device path specified by DevicePath in an allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device node.
+ If DevicePathNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DevicePathNode, followed by an end-of-device path device
+ node is returned.
+ If both DevicePathNode and DevicePath are NULL then a copy of an end-of-device-path device node
+ is returned.
+ If there is not enough memory to allocate space for the new device path, then NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility of the caller to
+ free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathNode A pointer to a single device path node.
+
+ @retval NULL There is not enough memory for the new device path.
+ @retval Others A pointer to the new device path if success.
+ A copy of DevicePathNode followed by an end-of-device-path node
+ if both FirstDevicePath and SecondDevicePath are NULL.
+ A copy of an end-of-device-path node if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathNode (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL
+ );
+
+/**
+ Creates a new device path by appending the specified device path instance to the specified device
+ path.
+
+ This function creates a new device path by appending a copy of the device path instance specified
+ by DevicePathInstance to a copy of the device path secified by DevicePath in a allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device path instance
+ and a new end-of-device-path-instance node is inserted between.
+ If DevicePath is NULL, then a copy if DevicePathInstance is returned.
+ If DevicePathInstance is NULL, then NULL is returned.
+ If DevicePath or DevicePathInstance is invalid, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility of the caller to
+ free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathInstance A pointer to a device path instance.
+
+ @return A pointer to the new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance OPTIONAL
+ );
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ This function creates a copy of the current device path instance. It also updates DevicePath to
+ point to the next device path instance in the device path (or NULL if no more) and updates Size
+ to hold the size of the device path instance copy.
+ If DevicePath is NULL, then NULL is returned.
+ If DevicePath points to a invalid device path, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility of the caller to
+ free the memory allocated.
+ If Size is NULL, then ASSERT().
+
+ @param DevicePath On input, this holds the pointer to the current device path
+ instance. On output, this holds the pointer to the next device
+ path instance or NULL if there are no more device path
+ instances in the device path pointer to a device path data
+ structure.
+ @param Size On output, this holds the size of the device path instance, in
+ bytes or zero, if DevicePath is NULL.
+
+ @return A pointer to the current device path instance.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+GetNextDevicePathInstance (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
+ OUT UINTN *Size
+ );
+
+/**
+ Creates a device node.
+
+ This function creates a new device node in a newly allocated buffer of size NodeLength and
+ initializes the device path node header with NodeType and NodeSubType. The new device path node
+ is returned.
+ If NodeLength is smaller than a device path header, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility of the caller to
+ free the memory allocated.
+
+ @param NodeType The device node type for the new device node.
+ @param NodeSubType The device node sub-type for the new device node.
+ @param NodeLength The length of the new device node.
+
+ @return The new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+CreateDeviceNode (
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+ );
+
+/**
+ Determines if a device path is single or multi-instance.
+
+ This function returns TRUE if the device path specified by DevicePath is multi-instance.
+ Otherwise, FALSE is returned.
+ If DevicePath is NULL or invalid, then FALSE is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval TRUE DevicePath is multi-instance.
+ @retval FALSE DevicePath is not multi-instance, or DevicePath is NULL or invalid.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathMultiInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Retrieves the device path protocol from a handle.
+
+ This function returns the device path protocol from the handle specified by Handle. If Handle is
+ NULL or Handle does not contain a device path protocol, then NULL is returned.
+
+ @param Handle The handle from which to retrieve the device path protocol.
+
+ @return The device path protocol from the handle specified by Handle.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DevicePathFromHandle (
+ IN EFI_HANDLE Handle
+ );
+
+/**
+ Allocates a device path for a file and appends it to an existing device path.
+
+ If Device is a valid device handle that contains a device path protocol, then a device path for
+ the file specified by FileName is allocated and appended to the device path associated with the
+ handle Device. The allocated device path is returned. If Device is NULL or Device is a handle
+ that does not support the device path protocol, then a device path containing a single device
+ path node for the file specified by FileName is allocated and returned.
+ The memory for the new device path is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ If FileName is NULL, then ASSERT().
+ If FileName is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param Device A pointer to a device handle. This parameter is optional and
+ may be NULL.
+ @param FileName A pointer to a Null-terminated Unicode string.
+
+ @return The allocated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+FileDevicePath (
+ IN EFI_HANDLE Device, OPTIONAL
+ IN CONST CHAR16 *FileName
+ );
+
+/**
+ Converts a device path to its text representation.
+
+ @param DevicePath A Pointer to the device to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device path or
+ NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDevicePathToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+/**
+ Converts a device node to its string representation.
+
+ @param DeviceNode A Pointer to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device node or NULL if DeviceNode
+ is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDeviceNodeToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was
+ insufficient memory or text unsupported.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDeviceNode (
+ IN CONST CHAR16 *TextDeviceNode
+ );
+
+/**
+ Convert text to the binary representation of a device path.
+
+ @param TextDevicePath TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or
+ there was insufficient memory.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDevicePath (
+ IN CONST CHAR16 *TextDevicePath
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/MemoryAllocationLib.h b/efi_memtest/memtest86+/efi/Include/Library/MemoryAllocationLib.h
new file mode 100644
index 0000000..65a30cf
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/MemoryAllocationLib.h
@@ -0,0 +1,487 @@
+/** @file
+ Provides services to allocate and free memory buffers of various memory types and alignments.
+
+ The Memory Allocation Library abstracts various common memory allocation operations. This library
+ allows code to be written in a phase-independent manner because the allocation of memory in PEI, DXE,
+ and SMM (for example) is done via a different mechanism. Using a common library interface makes it
+ much easier to port algorithms from phase to phase.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __MEMORY_ALLOCATION_LIB_H__
+#define __MEMORY_ALLOCATION_LIB_H__
+
+/**
+ Allocates one or more 4KB pages of type EfiBootServicesData.
+
+ Allocates the number of 4KB pages of type EfiBootServicesData and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocatePages (
+ IN UINTN Pages
+ );
+
+/**
+ Allocates one or more 4KB pages of type EfiRuntimeServicesData.
+
+ Allocates the number of 4KB pages of type EfiRuntimeServicesData and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimePages (
+ IN UINTN Pages
+ );
+
+/**
+ Allocates one or more 4KB pages of type EfiReservedMemoryType.
+
+ Allocates the number of 4KB pages of type EfiReservedMemoryType and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedPages (
+ IN UINTN Pages
+ );
+
+/**
+ Frees one or more 4KB pages that were previously allocated with one of the page allocation
+ functions in the Memory Allocation Library.
+
+ Frees the number of 4KB pages specified by Pages from the buffer specified by Buffer. Buffer
+ must have been allocated on a previous call to the page allocation services of the Memory
+ Allocation Library. If it is not possible to free allocated pages, then this function will
+ perform no actions.
+
+ If Buffer was not allocated with a page allocation function in the Memory Allocation Library,
+ then ASSERT().
+ If Pages is zero, then ASSERT().
+
+ @param Buffer Pointer to the buffer of pages to free.
+ @param Pages The number of 4 KB pages to free.
+
+**/
+VOID
+EFIAPI
+FreePages (
+ IN VOID *Buffer,
+ IN UINTN Pages
+ );
+
+/**
+ Allocates one or more 4KB pages of type EfiBootServicesData at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiBootServicesData with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedPages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ );
+
+/**
+ Allocates one or more 4KB pages of type EfiRuntimeServicesData at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiRuntimeServicesData with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedRuntimePages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ );
+
+/**
+ Allocates one or more 4KB pages of type EfiReservedMemoryType at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiReservedMemoryType with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedReservedPages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ );
+
+/**
+ Frees one or more 4KB pages that were previously allocated with one of the aligned page
+ allocation functions in the Memory Allocation Library.
+
+ Frees the number of 4KB pages specified by Pages from the buffer specified by Buffer. Buffer
+ must have been allocated on a previous call to the aligned page allocation services of the Memory
+ Allocation Library. If it is not possible to free allocated pages, then this function will
+ perform no actions.
+
+ If Buffer was not allocated with an aligned page allocation function in the Memory Allocation
+ Library, then ASSERT().
+ If Pages is zero, then ASSERT().
+
+ @param Buffer Pointer to the buffer of pages to free.
+ @param Pages The number of 4 KB pages to free.
+
+**/
+VOID
+EFIAPI
+FreeAlignedPages (
+ IN VOID *Buffer,
+ IN UINTN Pages
+ );
+
+/**
+ Allocates a buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData and returns a
+ pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocatePool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Allocates a buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData and returns
+ a pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimePool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Allocates a buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType and returns
+ a pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedPool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Allocates and zeros a buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateZeroPool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Allocates and zeros a buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimeZeroPool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Allocates and zeros a buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedZeroPool (
+ IN UINTN AllocationSize
+ );
+
+/**
+ Copies a buffer to an allocated buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Copies a buffer to an allocated buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimeCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Copies a buffer to an allocated buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Reallocates a buffer of type EfiBootServicesData.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiBootServicesData. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocatePool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ );
+
+/**
+ Reallocates a buffer of type EfiRuntimeServicesData.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiRuntimeServicesData. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocateRuntimePool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ );
+
+/**
+ Reallocates a buffer of type EfiReservedMemoryType.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiReservedMemoryType. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocateReservedPool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ );
+
+/**
+ Frees a buffer that was previously allocated with one of the pool allocation functions in the
+ Memory Allocation Library.
+
+ Frees the buffer specified by Buffer. Buffer must have been allocated on a previous call to the
+ pool allocation services of the Memory Allocation Library. If it is not possible to free pool
+ resources, then this function will perform no actions.
+
+ If Buffer was not allocated with a pool allocation function in the Memory Allocation Library,
+ then ASSERT().
+
+ @param Buffer Pointer to the buffer to free.
+
+**/
+VOID
+EFIAPI
+FreePool (
+ IN VOID *Buffer
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/PcdLib.h b/efi_memtest/memtest86+/efi/Include/Library/PcdLib.h
new file mode 100644
index 0000000..e8fd172
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/PcdLib.h
@@ -0,0 +1,1736 @@
+/** @file
+ Provides library services to get and set Platform Configuration Database entries.
+
+ PCD Library Class provides a PCD usage macro interface for all PCD types.
+ It should be included in any module that uses PCD. If a module uses dynamic/dynamicex
+ PCD, module should be linked to a PEIM/DXE library instance to access that PCD.
+ If a module uses PatchableInModule type PCD, it also needs the library instance to produce
+ LibPatchPcdSetPtr() interface. For FeatureFlag/Fixed PCD, the macro interface is
+ translated to a variable or macro that is auto-generated by build tool in
+ module's autogen.h/autogen.c.
+ The PcdGetXX(), PcdSetXX(), PcdToken(), and PcdGetNextTokenSpace() operations are
+ only available prior to ExitBootServices(). If access to PCD values are required
+ at runtime, then their values must be collected prior to ExitBootServices().
+ There are no restrictions on the use of FeaturePcd(), FixedPcdGetXX(),
+ PatchPcdGetXX(), and PatchPcdSetXX().
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "Efi_Defs_Pcd.h"
+
+#ifndef __PCD_LIB_H__
+#define __PCD_LIB_H__
+
+
+/**
+ Retrieves a token number based on a token name.
+
+ Returns the token number associated with the PCD token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve the token number for.
+
+ @return The token number associated with the PCD.
+
+**/
+#define PcdToken(TokenName) _PCD_TOKEN_##TokenName
+
+
+/**
+ Retrieves a Boolean PCD feature flag based on a token name.
+
+ Returns the Boolean value for the PCD feature flag specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a feature flag PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return Boolean value for the PCD feature flag.
+
+**/
+#define FeaturePcdGet(TokenName) _PCD_GET_MODE_BOOL_##TokenName
+
+
+/**
+ Retrieves an 8-bit fixed PCD token value based on a token name.
+
+ Returns the 8-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 8-bit value for the token specified by TokenName.
+
+**/
+#define FixedPcdGet8(TokenName) _PCD_VALUE_##TokenName
+
+
+/**
+ Retrieves a 16-bit fixed PCD token value based on a token name.
+
+ Returns the 16-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 16-bit value for the token specified by TokenName.
+
+**/
+#define FixedPcdGet16(TokenName) _PCD_VALUE_##TokenName
+
+
+/**
+ Retrieves a 32-bit fixed PCD token value based on a token name.
+
+ Returns the 32-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 32-bit value for the token specified by TokenName.
+
+**/
+#define FixedPcdGet32(TokenName) _PCD_VALUE_##TokenName
+
+
+/**
+ Retrieves a 64-bit fixed PCD token value based on a token name.
+
+ Returns the 64-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 64-bit value for the token specified by TokenName.
+
+**/
+#define FixedPcdGet64(TokenName) _PCD_VALUE_##TokenName
+
+
+/**
+ Retrieves a Boolean fixed PCD token value based on a token name.
+
+ Returns the Boolean value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return The Boolean value for the token.
+
+**/
+#define FixedPcdGetBool(TokenName) _PCD_VALUE_##TokenName
+
+
+/**
+ Retrieves a pointer to a fixed PCD token buffer based on a token name.
+
+ Returns a pointer to the buffer for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a fixed at build PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A pointer to the buffer.
+
+**/
+#define FixedPcdGetPtr(TokenName) ((VOID *)_PCD_VALUE_##TokenName)
+
+
+/**
+ Retrieves an 8-bit binary patchable PCD token value based on a token name.
+
+ Returns the 8-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return An 8-bit binary patchable PCD token value.
+
+**/
+#define PatchPcdGet8(TokenName) _gPcd_BinaryPatch_##TokenName
+
+/**
+ Retrieves a 16-bit binary patchable PCD token value based on a token name.
+
+ Returns the 16-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 16-bit binary patchable PCD token value.
+
+**/
+#define PatchPcdGet16(TokenName) _gPcd_BinaryPatch_##TokenName
+
+
+/**
+ Retrieves a 32-bit binary patchable PCD token value based on a token name.
+
+ Returns the 32-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 32-bit binary patchable PCD token value.
+
+**/
+#define PatchPcdGet32(TokenName) _gPcd_BinaryPatch_##TokenName
+
+
+/**
+ Retrieves a 64-bit binary patchable PCD token value based on a token name.
+
+ Returns the 64-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 64-bit binary patchable PCD token value.
+
+**/
+#define PatchPcdGet64(TokenName) _gPcd_BinaryPatch_##TokenName
+
+
+/**
+ Retrieves a Boolean binary patchable PCD token value based on a token name.
+
+ Returns the Boolean value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return The Boolean value for the token.
+
+**/
+#define PatchPcdGetBool(TokenName) _gPcd_BinaryPatch_##TokenName
+
+
+/**
+ Retrieves a pointer to a binary patchable PCD token buffer based on a token name.
+
+ Returns a pointer to the buffer for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A pointer to the buffer for the token.
+
+**/
+#define PatchPcdGetPtr(TokenName) ((VOID *)_gPcd_BinaryPatch_##TokenName)
+
+
+/**
+ Sets an 8-bit binary patchable PCD token value based on a token name.
+
+ Sets the 8-bit value for the token specified by TokenName. Value is returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param Value The 8-bit value to set.
+
+ @return Return the Value that was set.
+
+**/
+#define PatchPcdSet8(TokenName, Value) (_gPcd_BinaryPatch_##TokenName = (Value))
+
+
+/**
+ Sets a 16-bit binary patchable PCD token value based on a token name.
+
+ Sets the 16-bit value for the token specified by TokenName. Value is returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param Value The 16-bit value to set.
+
+ @return Return the Value that was set.
+
+**/
+#define PatchPcdSet16(TokenName, Value) (_gPcd_BinaryPatch_##TokenName = (Value))
+
+
+/**
+ Sets a 32-bit binary patchable PCD token value based on a token name.
+
+ Sets the 32-bit value for the token specified by TokenName. Value is returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param Value The 32-bit value to set.
+
+ @return Return the Value that was set.
+
+**/
+#define PatchPcdSet32(TokenName, Value) (_gPcd_BinaryPatch_##TokenName = (Value))
+
+
+/**
+ Sets a 64-bit binary patchable PCD token value based on a token name.
+
+ Sets the 64-bit value for the token specified by TokenName. Value is returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param Value The 64-bit value to set.
+
+ @return Return the Value that was set.
+
+**/
+#define PatchPcdSet64(TokenName, Value) (_gPcd_BinaryPatch_##TokenName = (Value))
+
+
+/**
+ Sets a Boolean binary patchable PCD token value based on a token name.
+
+ Sets the Boolean value for the token specified by TokenName. Value is returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param Value The boolean value to set.
+
+ @return Return the Value that was set.
+
+**/
+#define PatchPcdSetBool(TokenName, Value) (_gPcd_BinaryPatch_##TokenName = (Value))
+
+
+/**
+ Sets a pointer to a binary patchable PCD token buffer based on a token name.
+
+ Sets the buffer for the token specified by TokenName. Buffer is returned.
+ If SizeOfBuffer is greater than the maximum size supported by TokenName, then set SizeOfBuffer
+ to the maximum size supported by TokenName and return NULL to indicate that the set operation
+ was not actually performed. If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be
+ set to the maximum size supported by TokenName and NULL must be returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+ If TokenName is not a patchable in module PCD, then the module will not build.
+
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param TokenName The name of the binary patchable PCD token to set the current value for.
+ @param SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param Buffer Pointer to the value to set.
+
+ @return Return the pointer to the Buffer that was set.
+
+**/
+#define PatchPcdSetPtr(TokenName, Size, Buffer) \
+ LibPatchPcdSetPtrAndSize ( \
+ (VOID *)_gPcd_BinaryPatch_##TokenName, \
+ &_gPcd_BinaryPatch_Size_##TokenName, \
+ (UINTN)_PCD_PATCHABLE_##TokenName##_SIZE, \
+ (Size), \
+ (Buffer) \
+ )
+/**
+ Retrieves an 8-bit PCD token value based on a token name.
+
+ Returns the 8-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 8-bit value for the token specified by TokenName.
+
+**/
+#define PcdGet8(TokenName) _PCD_GET_MODE_8_##TokenName
+
+
+/**
+ Retrieves a 16-bit PCD token value based on a token name.
+
+ Returns the 16-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 16-bit value for the token specified by TokenName.
+
+**/
+#define PcdGet16(TokenName) _PCD_GET_MODE_16_##TokenName
+
+
+/**
+ Retrieves a 32-bit PCD token value based on a token name.
+
+ Returns the 32-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 32-bit value for the token specified by TokenName.
+
+**/
+#define PcdGet32(TokenName) _PCD_GET_MODE_32_##TokenName
+
+
+/**
+ Retrieves a 64-bit PCD token value based on a token name.
+
+ Returns the 64-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return 64-bit value for the token specified by TokenName.
+
+**/
+#define PcdGet64(TokenName) _PCD_GET_MODE_64_##TokenName
+
+
+/**
+ Retrieves a pointer to a PCD token buffer based on a token name.
+
+ Returns a pointer to the buffer for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A pointer to the buffer.
+
+**/
+#define PcdGetPtr(TokenName) _PCD_GET_MODE_PTR_##TokenName
+
+
+/**
+ Retrieves a Boolean PCD token value based on a token name.
+
+ Returns the Boolean value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A Boolean PCD token value.
+
+**/
+#define PcdGetBool(TokenName) _PCD_GET_MODE_BOOL_##TokenName
+
+
+/**
+ Retrieves the size of a fixed PCD token based on a token name.
+
+ Returns the size of the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param[in] TokenName The name of the PCD token to retrieve a current value size for.
+
+ @return Return the size
+
+**/
+#define FixedPcdGetSize(TokenName) _PCD_SIZE_##TokenName
+
+
+/**
+ Retrieves the size of a binary patchable PCD token based on a token name.
+
+ Returns the size of the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param[in] TokenName The name of the PCD token to retrieve a current value size for.
+
+ @return Return the size
+
+**/
+#define PatchPcdGetSize(TokenName) _gPcd_BinaryPatch_Size_##TokenName
+
+
+/**
+ Retrieves the size of the PCD token based on a token name.
+
+ Returns the size of the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param[in] TokenName The name of the PCD token to retrieve a current value size for.
+
+ @return Return the size
+
+**/
+#define PcdGetSize(TokenName) _PCD_GET_MODE_SIZE_##TokenName
+
+
+/**
+ Retrieve the size of a given PCD token.
+
+ Returns the size of the token specified by TokenNumber and Guid.
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value size for.
+
+ @return Return the size.
+
+**/
+#define PcdGetExSize(Guid, TokenName) LibPcdGetExSize ((Guid), PcdTokenEx(Guid,TokenName))
+
+/**
+ Sets a 8-bit PCD token value based on a token name.
+
+ Sets the 8-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+ @param Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSet8S(TokenName, Value) _PCD_SET_MODE_8_S_##TokenName ((Value))
+
+/**
+ Sets a 16-bit PCD token value based on a token name.
+
+ Sets the 16-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+ @param Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSet16S(TokenName, Value) _PCD_SET_MODE_16_S_##TokenName ((Value))
+
+/**
+ Sets a 32-bit PCD token value based on a token name.
+
+ Sets the 32-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+ @param Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSet32S(TokenName, Value) _PCD_SET_MODE_32_S_##TokenName ((Value))
+
+/**
+ Sets a 64-bit PCD token value based on a token name.
+
+ Sets the 64-bit value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+ @param Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSet64S(TokenName, Value) _PCD_SET_MODE_64_S_##TokenName ((Value))
+
+/**
+ Sets a pointer to a PCD token buffer based on a token name.
+
+ Sets the buffer for the token specified by TokenName.
+ If SizeOfBuffer is greater than the maximum size supported by TokenName,
+ then set SizeOfBuffer to the maximum size supported by TokenName and return
+ RETURN_INVALID_PARAMETER to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to the maximum size
+ supported by TokenName and RETURN_INVALID_PARAMETER must be returned.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param TokenName The name of the PCD token to set the current value for.
+ @param SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param Buffer A pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetPtrS(TokenName, SizeOfBuffer, Buffer) \
+ _PCD_SET_MODE_PTR_S_##TokenName ((SizeOfBuffer), (Buffer))
+
+
+
+/**
+ Sets a boolean PCD token value based on a token name.
+
+ Sets the boolean value for the token specified by TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param TokenName The name of the PCD token to retrieve a current value for.
+ @param Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetBoolS(TokenName, Value) _PCD_SET_MODE_BOOL_S_##TokenName ((Value))
+
+/**
+ Retrieves a token number based on a GUID and a token name.
+
+ Returns the token number for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space, then the module will not build.
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return Return the token number.
+
+**/
+#define PcdTokenEx(Guid,TokenName) _PCD_TOKEN_EX_##TokenName(Guid)
+
+/**
+ Retrieves an 8-bit PCD token value based on a GUID and a token name.
+
+ Returns the 8-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return An 8-bit PCD token value.
+
+**/
+#define PcdGetEx8(Guid, TokenName) LibPcdGetEx8 ((Guid), PcdTokenEx(Guid,TokenName))
+
+/**
+ Retrieves a 16-bit PCD token value based on a GUID and a token name.
+
+ Returns the 16-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 16-bit PCD token value.
+
+**/
+#define PcdGetEx16(Guid, TokenName) LibPcdGetEx16 ((Guid), PcdTokenEx(Guid,TokenName))
+
+
+/**
+ Retrieves a 32-bit PCD token value based on a GUID and a token name.
+
+ Returns the 32-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 32-bit PCD token value.
+
+**/
+#define PcdGetEx32(Guid, TokenName) LibPcdGetEx32 ((Guid), PcdTokenEx(Guid,TokenName))
+
+
+/**
+ Retrieves a 64-bit PCD token value based on a GUID and a token name.
+
+ Returns the 64-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A 64-bit PCD token value.
+
+**/
+#define PcdGetEx64(Guid, TokenName) LibPcdGetEx64 ((Guid), PcdTokenEx(Guid,TokenName))
+
+
+/**
+ Retrieves a pointer to a PCD token buffer based on a GUID and a token name.
+
+ Returns a pointer to the buffer for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A pointer to a PCD token buffer.
+
+**/
+#define PcdGetExPtr(Guid, TokenName) LibPcdGetExPtr ((Guid), PcdTokenEx(Guid,TokenName))
+
+
+/**
+ Retrieves a Boolean PCD token value based on a GUID and a token name.
+
+ Returns the Boolean value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to retrieve a current value for.
+
+ @return A Boolean PCD token value.
+
+**/
+#define PcdGetExBool(Guid, TokenName) LibPcdGetExBool ((Guid), PcdTokenEx(Guid,TokenName))
+
+
+
+/**
+ Sets an 8-bit PCD token value based on a GUID and a token name.
+
+ Sets the 8-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetEx8S(Guid, TokenName, Value) LibPcdSetEx8S ((Guid), PcdTokenEx(Guid,TokenName), (Value))
+
+/**
+ Sets an 16-bit PCD token value based on a GUID and a token name.
+
+ Sets the 16-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetEx16S(Guid, TokenName, Value) LibPcdSetEx16S ((Guid), PcdTokenEx(Guid,TokenName), (Value))
+
+/**
+ Sets an 32-bit PCD token value based on a GUID and a token name.
+
+ Sets the 32-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetEx32S(Guid, TokenName, Value) LibPcdSetEx32S ((Guid), PcdTokenEx(Guid,TokenName), (Value))
+
+/**
+ Sets an 64-bit PCD token value based on a GUID and a token name.
+
+ Sets the 64-bit value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetEx64S(Guid, TokenName, Value) LibPcdSetEx64S ((Guid), PcdTokenEx(Guid,TokenName), (Value))
+
+/**
+ Sets a pointer to a PCD token buffer based on a GUID and a token name.
+
+ Sets the buffer for the token specified by Guid and TokenName.
+ If SizeOfBuffer is greater than the maximum size supported by Guid and TokenName,
+ then set SizeOfBuffer to the maximum size supported by Guid and TokenName and return
+ RETURN_INVALID_PARAMETER to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to the maximum size
+ supported by Guid and TokenName and RETURN_INVALID_PARAMETER must be returned.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param Buffer Pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetExPtrS(Guid, TokenName, SizeOfBuffer, Buffer) \
+ LibPcdSetExPtrS ((Guid), PcdTokenEx(Guid,TokenName), (SizeOfBuffer), (Buffer))
+
+
+/**
+ Sets an boolean PCD token value based on a GUID and a token name.
+
+ Sets the boolean value for the token specified by Guid and TokenName.
+ If TokenName is not a valid token in the token space specified by Guid,
+ then the module will not build.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param TokenName The name of the PCD token to set the current value for.
+ @param Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+#define PcdSetExBoolS(Guid, TokenName, Value) \
+ LibPcdSetExBoolS ((Guid), PcdTokenEx(Guid,TokenName), (Value))
+
+/**
+ This function provides a means by which SKU support can be established in the PCD infrastructure.
+
+ Sets the current SKU in the PCD database to the value specified by SkuId. SkuId is returned.
+
+ @param SkuId The SKU value that will be used when the PCD service retrieves and sets values
+ associated with a PCD token.
+
+ @return Return the SKU ID that was set.
+
+**/
+UINTN
+EFIAPI
+LibPcdSetSku (
+ IN UINTN SkuId
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 8-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 8-bit value for the token specified by TokenNumber.
+
+**/
+UINT8
+EFIAPI
+LibPcdGet8 (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 16-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 16-bit value for the token specified by TokenNumber.
+
+**/
+UINT16
+EFIAPI
+LibPcdGet16 (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 32-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 32-bit value for the token specified by TokenNumber.
+
+**/
+UINT32
+EFIAPI
+LibPcdGet32 (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 64-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 64-bit value for the token specified by TokenNumber.
+
+**/
+UINT64
+EFIAPI
+LibPcdGet64 (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the pointer to the buffer of the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the pointer to the token specified by TokenNumber.
+
+**/
+VOID *
+EFIAPI
+LibPcdGetPtr (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the Boolean value of the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the Boolean value of the token specified by TokenNumber.
+
+**/
+BOOLEAN
+EFIAPI
+LibPcdGetBool (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve the size of a given PCD token.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the size of the token specified by TokenNumber.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetSize (
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 8-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT8.
+
+**/
+UINT8
+EFIAPI
+LibPcdGetEx8 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 16-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT16.
+
+**/
+UINT16
+EFIAPI
+LibPcdGetEx16 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ Returns the 32-bit value for the token specified by TokenNumber and Guid.
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT32.
+
+**/
+UINT32
+EFIAPI
+LibPcdGetEx32 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 64-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT64.
+
+**/
+UINT64
+EFIAPI
+LibPcdGetEx64 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the pointer to the buffer of token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the VOID* pointer.
+
+**/
+VOID *
+EFIAPI
+LibPcdGetExPtr (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the Boolean value of the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the BOOLEAN.
+
+**/
+BOOLEAN
+EFIAPI
+LibPcdGetExBool (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to retrieve the size of a given PCD token.
+
+ Returns the size of the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the size.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetExSize (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ );
+
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 8-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet8S (
+ IN UINTN TokenNumber,
+ IN UINT8 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 16-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet16S (
+ IN UINTN TokenNumber,
+ IN UINT16 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 32-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet32S (
+ IN UINTN TokenNumber,
+ IN UINT32 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 64-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet64S (
+ IN UINTN TokenNumber,
+ IN UINT64 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets a buffer for the token specified by TokenNumber to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than the maximum size
+ support by TokenNumber, then set SizeOfBuffer to the maximum size supported by
+ TokenNumber and return RETURN_INVALID_PARAMETER to indicate that the set operation
+ was not actually performed.
+
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to the
+ maximum size supported by TokenName and RETURN_INVALID_PARAMETER must be returned.
+
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in, out] SizeOfBuffer The size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetPtrS (
+ IN UINTN TokenNumber,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the boolean value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetBoolS (
+ IN UINTN TokenNumber,
+ IN BOOLEAN Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 8-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx8S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT8 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 16-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx16S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT16 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 32-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx32S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT32 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 64-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx64S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT64 Value
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets a buffer for the token specified by TokenNumber to the value specified by
+ Buffer and SizeOfBuffer. If SizeOfBuffer is greater than the maximum size
+ support by TokenNumber, then set SizeOfBuffer to the maximum size supported by
+ TokenNumber and return RETURN_INVALID_PARAMETER to indicate that the set operation
+ was not actually performed.
+
+ If Guid is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in, out] SizeOfBuffer The size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetExPtrS (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN OUT UINTN *SizeOfBuffer,
+ IN VOID *Buffer
+ );
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the boolean value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetExBoolS (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN BOOLEAN Value
+ );
+
+/**
+ This notification function serves two purposes.
+
+ Firstly, it notifies the module that did the registration that the value of this
+ PCD token has been set.
+ Secondly, it provides a mechanism for the module that did the registration to intercept
+ the set operation and override the value been set if necessary. After the invocation of
+ the callback function, TokenData will be used by PCD service PEIM or driver to modify th
+ internal data in PCD database.
+
+ @param[in] CallBackGuid The PCD token GUID being set.
+ @param[in] CallBackToken The PCD token number being set.
+ @param[in, out] TokenData A pointer to the token data being set.
+ @param[in] TokenDataSize The size, in bytes, of the data being set.
+
+**/
+typedef
+VOID
+(EFIAPI *PCD_CALLBACK)(
+ IN CONST GUID *CallBackGuid, OPTIONAL
+ IN UINTN CallBackToken,
+ IN OUT VOID *TokenData,
+ IN UINTN TokenDataSize
+ );
+
+
+/**
+ Set up a notification function that is called when a specified token is set.
+
+ When the token specified by TokenNumber and Guid is set,
+ then notification function specified by NotificationFunction is called.
+ If Guid is NULL, then the default token space is used.
+ If NotificationFunction is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates which
+ namespace to set a value from. If NULL, then the default
+ token space is used.
+ @param[in] TokenNumber The PCD token number to monitor.
+ @param[in] NotificationFunction The function to call when the token
+ specified by Guid and TokenNumber is set.
+
+**/
+VOID
+EFIAPI
+LibPcdCallbackOnSet (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber,
+ IN PCD_CALLBACK NotificationFunction
+ );
+
+
+/**
+ Disable a notification function that was established with LibPcdCallbackonSet().
+
+ Disable a notification function that was previously established with LibPcdCallbackOnSet().
+ If NotificationFunction is NULL, then ASSERT().
+ If LibPcdCallbackOnSet() was not previously called with Guid, TokenNumber,
+ and NotificationFunction, then ASSERT().
+
+ @param[in] Guid Specify the GUID token space.
+ @param[in] TokenNumber Specify the token number.
+ @param[in] NotificationFunction The callback function to be unregistered.
+
+**/
+VOID
+EFIAPI
+LibPcdCancelCallback (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber,
+ IN PCD_CALLBACK NotificationFunction
+ );
+
+
+/**
+ Retrieves the next token in a token space.
+
+ Retrieves the next PCD token number from the token space specified by Guid.
+ If Guid is NULL, then the default token space is used. If TokenNumber is 0,
+ then the first token number is returned. Otherwise, the token number that
+ follows TokenNumber in the token space is returned. If TokenNumber is the last
+ token number in the token space, then 0 is returned.
+
+ If TokenNumber is not 0 and is not in the token space specified by Guid, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that designates which namespace
+ to set a value from. If NULL, then the default token space is used.
+ @param[in] TokenNumber The previous PCD token number. If 0, then retrieves the first PCD
+ token number.
+
+ @return The next valid token number.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetNextToken (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber
+ );
+
+
+
+/**
+ Used to retrieve the list of available PCD token space GUIDs.
+
+ Returns the PCD token space GUID that follows TokenSpaceGuid in the list of token spaces
+ in the platform.
+ If TokenSpaceGuid is NULL, then a pointer to the first PCD token spaces returned.
+ If TokenSpaceGuid is the last PCD token space GUID in the list, then NULL is returned.
+
+ @param TokenSpaceGuid Pointer to the a PCD token space GUID
+
+ @return The next valid token namespace.
+
+**/
+GUID *
+EFIAPI
+LibPcdGetNextTokenSpace (
+ IN CONST GUID *TokenSpaceGuid
+ );
+
+
+/**
+ Sets a value of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified by Buffer
+ and SizeOfBuffer. Buffer is returned. If SizeOfBuffer is greater than
+ MaximumDatumSize, then set SizeOfBuffer to MaximumDatumSize and return
+ NULL to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and NULL must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return Return the pointer to the Buffer that was set.
+
+**/
+VOID *
+EFIAPI
+LibPatchPcdSetPtr (
+ OUT VOID *PatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Sets a value of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than MaximumDatumSize,
+ then set SizeOfBuffer to MaximumDatumSize and return RETURN_INVALID_PARAMETER
+ to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and RETURN_INVALID_PARAMETER must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPatchPcdSetPtrS (
+ OUT VOID *PatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Sets a value and size of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified by Buffer
+ and SizeOfBuffer. Buffer is returned. If SizeOfBuffer is greater than
+ MaximumDatumSize, then set SizeOfBuffer to MaximumDatumSize and return
+ NULL to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and NULL must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfPatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[out] SizeOfPatchVariable A pointer to the size, in bytes, of PatchVariable.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return Return the pointer to the Buffer that was set.
+
+**/
+VOID *
+EFIAPI
+LibPatchPcdSetPtrAndSize (
+ OUT VOID *PatchVariable,
+ OUT UINTN *SizeOfPatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ );
+
+/**
+ Sets a value and size of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than MaximumDatumSize,
+ then set SizeOfBuffer to MaximumDatumSize and return RETURN_INVALID_PARAMETER
+ to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and RETURN_INVALID_PARAMETER must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfPatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[out] SizeOfPatchVariable A pointer to the size, in bytes, of PatchVariable.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPatchPcdSetPtrAndSizeS (
+ OUT VOID *PatchVariable,
+ OUT UINTN *SizeOfPatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ );
+
+typedef enum {
+ PCD_TYPE_8,
+ PCD_TYPE_16,
+ PCD_TYPE_32,
+ PCD_TYPE_64,
+ PCD_TYPE_BOOL,
+ PCD_TYPE_PTR
+} PCD_TYPE;
+
+typedef struct {
+ ///
+ /// The returned information associated with the requested TokenNumber. If
+ /// TokenNumber is 0, then PcdType is set to PCD_TYPE_8.
+ ///
+ PCD_TYPE PcdType;
+ ///
+ /// The size of the data in bytes associated with the TokenNumber specified. If
+ /// TokenNumber is 0, then PcdSize is set 0.
+ ///
+ UINTN PcdSize;
+ ///
+ /// The null-terminated ASCII string associated with a given token. If the
+ /// TokenNumber specified was 0, then this field corresponds to the null-terminated
+ /// ASCII string associated with the token's namespace Guid. If NULL, there is no
+ /// name associated with this request.
+ ///
+ CHAR8 *PcdName;
+} PCD_INFO;
+
+
+/**
+ Retrieve additional information associated with a PCD token.
+
+ This includes information such as the type of value the TokenNumber is associated with as well as possible
+ human readable name that is associated with the token.
+
+ If TokenNumber is not in the default token space specified, then ASSERT().
+
+ @param[in] TokenNumber The PCD token number.
+ @param[out] PcdInfo The returned information associated with the requested TokenNumber.
+ The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
+**/
+VOID
+EFIAPI
+LibPcdGetInfo (
+ IN UINTN TokenNumber,
+ OUT PCD_INFO *PcdInfo
+ );
+
+/**
+ Retrieve additional information associated with a PCD token.
+
+ This includes information such as the type of value the TokenNumber is associated with as well as possible
+ human readable name that is associated with the token.
+
+ If TokenNumber is not in the token space specified by Guid, then ASSERT().
+
+ @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
+ @param[in] TokenNumber The PCD token number.
+ @param[out] PcdInfo The returned information associated with the requested TokenNumber.
+ The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
+**/
+VOID
+EFIAPI
+LibPcdGetInfoEx (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ OUT PCD_INFO *PcdInfo
+ );
+
+/**
+ Retrieve the currently set SKU Id.
+
+ @return The currently set SKU Id. If the platform has not set at a SKU Id, then the
+ default SKU Id value of 0 is returned. If the platform has set a SKU Id, then the currently set SKU
+ Id is returned.
+**/
+UINTN
+EFIAPI
+LibPcdGetSku (
+ VOID
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/PrintLib.h b/efi_memtest/memtest86+/efi/Include/Library/PrintLib.h
new file mode 100644
index 0000000..0b38da6
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/PrintLib.h
@@ -0,0 +1,935 @@
+/** @file
+ Provides services to print a formatted string to a buffer. All combinations of
+ Unicode and ASCII strings are supported.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+ The Print Library functions provide a simple means to produce formatted output
+ strings. Many of the output functions use a format string to describe how to
+ format the output of variable arguments. The format string consists of normal
+ text and argument descriptors. There are no restrictions for how the normal
+ text and argument descriptors can be mixed. The following end of line(EOL)
+ translations must be performed on the contents of the format string:
+
+ - '\\r' is translated to '\\r'
+ - '\\r\\n' is translated to '\\r\\n'
+ - '\\n' is translated to '\\r\\n'
+ - '\\n\\r' is translated to '\\r\\n'
+
+ This does not follow the ANSI C standard for sprint(). The format of argument
+ descriptors is described below. The ANSI C standard for sprint() has been
+ followed for some of the format types, and has not been followed for others.
+ The exceptions are noted below.
+
+ %[flags][width][.precision]type
+
+ [flags]:
+ - -
+ - The field is left justified. If not flag is not specified, then the
+ field is right justified.
+ - space
+ - Prefix a space character to a number. Only valid for types X, x, and d.
+ - +
+ - Prefix a plus character to a number. Only valid for types X, x, and d.
+ If both space and + are specified, then space is ignored.
+ - 0
+ - Pad with 0 characters to the left of a number. Only valid for types
+ X, x, and d.
+ - ,
+ - Place a comma every 3rd digit of the number. Only valid for type d.
+ If 0 is also specified, then 0 is ignored.
+ - L, l
+ - The number being printed is size UINT64. Only valid for types X, x, and d.
+ If this flag is not specified, then the number being printed is size int.
+ - NOTE: All invalid flags are ignored.
+
+ [width]:
+
+ - *
+ - The width of the field is specified by a UINTN argument in the
+ argument list.
+ - number
+ - The number specified as a decimal value represents the width of
+ the field.
+ - NOTE: If [width] is not specified, then a field width of 0 is assumed.
+
+ [.precision]:
+
+ - *
+ - The precision of the field is specified by a UINTN argument in the
+ argument list.
+ - number
+ - The number specified as a decimal value represents the precision of
+ the field.
+ - NOTE: If [.precision] is not specified, then a precision of 0 is assumed.
+
+ type:
+
+ - %
+ - Print a %%.
+ - c
+ - The argument is a Unicode character. ASCII characters can be printed
+ using this type too by making sure bits 8..15 of the argument are set to 0.
+ - x
+ - The argument is an unsigned hexadecimal number. The characters used are 0..9 and
+ A..F. If the flag 'L' is not specified, then the argument is assumed
+ to be size int. This does not follow ANSI C.
+ - X
+ - The argument is an unsigned hexadecimal number and the number is padded with
+ zeros. This is equivalent to a format string of "0x". If the flag
+ 'L' is not specified, then the argument is assumed to be size int.
+ This does not follow ANSI C.
+ - d
+ - The argument is a signed decimal number. If the flag 'L' is not specified,
+ then the argument is assumed to be size int.
+ - u
+ - The argument is a unsigned decimal number. If the flag 'L' is not specified,
+ then the argument is assumed to be size int.
+ - p
+ - The argument is a pointer that is a (VOID *), and it is printed as an
+ unsigned hexadecimal number The characters used are 0..9 and A..F.
+ - a
+ - The argument is a pointer to an ASCII string.
+ This does not follow ANSI C.
+ - S, s
+ - The argument is a pointer to a Unicode string.
+ This does not follow ANSI C.
+ - g
+ - The argument is a pointer to a GUID structure. The GUID is printed
+ in the format XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX.
+ This does not follow ANSI C.
+ - t
+ - The argument is a pointer to an EFI_TIME structure. The time and
+ date are printed in the format "mm/dd/yyyy hh:mm" where mm is the
+ month zero padded, dd is the day zero padded, yyyy is the year zero
+ padded, hh is the hour zero padded, and mm is minutes zero padded.
+ This does not follow ANSI C.
+ - r
+ - The argument is a RETURN_STATUS value. This value is converted to
+ a string following the table below. This does not follow ANSI C.
+ - RETURN_SUCCESS
+ - "Success"
+ - RETURN_LOAD_ERROR
+ - "Load Error"
+ - RETURN_INVALID_PARAMETER
+ - "Invalid Parameter"
+ - RETURN_UNSUPPORTED
+ - "Unsupported"
+ - RETURN_BAD_BUFFER_SIZE
+ - "Bad Buffer Size"
+ - RETURN_BUFFER_TOO_SMALL
+ - "Buffer Too Small"
+ - RETURN_NOT_READY
+ - "Not Ready"
+ - RETURN_DEVICE_ERROR
+ - "Device Error"
+ - RETURN_WRITE_PROTECTED
+ - "Write Protected"
+ - RETURN_OUT_OF_RESOURCES
+ - "Out of Resources"
+ - RETURN_VOLUME_CORRUPTED
+ - "Volume Corrupt"
+ - RETURN_VOLUME_FULL
+ - "Volume Full"
+ - RETURN_NO_MEDIA
+ - "No Media"
+ - RETURN_MEDIA_CHANGED
+ - "Media changed"
+ - RETURN_NOT_FOUND
+ - "Not Found"
+ - RETURN_ACCESS_DENIED
+ - "Access Denied"
+ - RETURN_NO_RESPONSE
+ - "No Response"
+ - RETURN_NO_MAPPING
+ - "No mapping"
+ - RETURN_TIMEOUT
+ - "Time out"
+ - RETURN_NOT_STARTED
+ - "Not started"
+ - RETURN_ALREADY_STARTED
+ - "Already started"
+ - RETURN_ABORTED
+ - "Aborted"
+ - RETURN_ICMP_ERROR
+ - "ICMP Error"
+ - RETURN_TFTP_ERROR
+ - "TFTP Error"
+ - RETURN_PROTOCOL_ERROR
+ - "Protocol Error"
+ - RETURN_WARN_UNKNOWN_GLYPH
+ - "Warning Unknown Glyph"
+ - RETURN_WARN_DELETE_FAILURE
+ - "Warning Delete Failure"
+ - RETURN_WARN_WRITE_FAILURE
+ - "Warning Write Failure"
+ - RETURN_WARN_BUFFER_TOO_SMALL
+ - "Warning Buffer Too Small"
+
+**/
+
+#ifndef __PRINT_LIB_H__
+#define __PRINT_LIB_H__
+
+///
+/// Define the maximum number of characters that are required to
+/// encode with a NULL terminator a decimal, hexadecimal, GUID,
+/// or TIME value.
+///
+/// Maximum Length Decimal String = 28
+/// "-9,223,372,036,854,775,808"
+/// Maximum Length Hexadecimal String = 17
+/// "FFFFFFFFFFFFFFFF"
+/// Maximum Length GUID = 37
+/// "00000000-0000-0000-0000-000000000000"
+/// Maximum Length TIME = 18
+/// "12/12/2006 12:12"
+///
+#define MAXIMUM_VALUE_CHARACTERS 38
+
+///
+/// Flags bitmask values use in UnicodeValueToString() and
+/// AsciiValueToString()
+///
+#define LEFT_JUSTIFY 0x01
+#define COMMA_TYPE 0x08
+#define PREFIX_ZERO 0x20
+#define RADIX_HEX 0x80
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on
+ a Null-terminated Unicode format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeVSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on
+ a Null-terminated Unicode format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeBSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN BASE_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ Unicode format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ ...
+ );
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeVSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeBSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN BASE_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ ...
+ );
+
+/**
+ Converts a decimal value to a Null-terminated Unicode string.
+
+ Converts the decimal number specified by Value to a Null-terminated Unicode
+ string specified by Buffer containing at most Width characters. No padding of
+ spaces is ever performed. If Width is 0 then a width of
+ MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more than
+ Width characters, then only the first Width characters are placed in Buffer.
+ Additional conversion parameters are specified in Flags.
+
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If RADIX_HEX is set in Flags, then the output buffer will be formatted in
+ hexadecimal format.
+ If Value is < 0 and RADIX_HEX is not set in Flags, then the fist character in
+ Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored, then
+ Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If an error would be returned, then the function will also ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated Unicode string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of Unicode characters to place in
+ Buffer, not including the Null-terminator.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and BufferSize is greater than
+ (PcdMaximumUnicodeStringLength *
+ sizeof (CHAR16) + 1).
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+EFIAPI
+UnicodeValueToStringS (
+ IN OUT CHAR16 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiVSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiBSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN BASE_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ ...
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiVSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiBSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN BASE_LIST Marker
+ );
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ ...
+ );
+
+
+/**
+ Converts a decimal value to a Null-terminated Ascii string.
+
+ Converts the decimal number specified by Value to a Null-terminated Ascii
+ string specified by Buffer containing at most Width characters. No padding of
+ spaces is ever performed. If Width is 0 then a width of
+ MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more than
+ Width characters, then only the first Width characters are placed in Buffer.
+ Additional conversion parameters are specified in Flags.
+
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If RADIX_HEX is set in Flags, then the output buffer will be formatted in
+ hexadecimal format.
+ If Value is < 0 and RADIX_HEX is not set in Flags, then the fist character in
+ Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored, then
+ Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If an error would be returned, then the function will ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated Ascii string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of Ascii characters to place in
+ Buffer, not including the Null-terminator.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If PcdMaximumAsciiStringLength is not
+ zero, and BufferSize is greater than
+ PcdMaximumAsciiStringLength.
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiValueToStringS (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width
+ );
+
+/**
+ Returns the number of characters that would be produced by if the formatted
+ output were produced not including the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If FormatString is NULL, then ASSERT() and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more
+ than PcdMaximumUnicodeStringLength Unicode characters not including the
+ Null-terminator, then ASSERT() and 0 is returned.
+
+ @param[in] FormatString A Null-terminated Unicode format string.
+ @param[in] Marker VA_LIST marker for the variable argument list.
+
+ @return The number of characters that would be produced, not including the
+ Null-terminator.
+**/
+UINTN
+EFIAPI
+SPrintLength (
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ );
+
+/**
+ Returns the number of characters that would be produced by if the formatted
+ output were produced not including the Null-terminator.
+
+ If FormatString is NULL, then ASSERT() and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more
+ than PcdMaximumAsciiStringLength Ascii characters not including the
+ Null-terminator, then ASSERT() and 0 is returned.
+
+ @param[in] FormatString A Null-terminated ASCII format string.
+ @param[in] Marker VA_LIST marker for the variable argument list.
+
+ @return The number of characters that would be produced, not including the
+ Null-terminator.
+**/
+UINTN
+EFIAPI
+SPrintLengthAsciiFormat (
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Library/UefiRuntimeServicesTableLib.h b/efi_memtest/memtest86+/efi/Include/Library/UefiRuntimeServicesTableLib.h
new file mode 100644
index 0000000..39212ee
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Library/UefiRuntimeServicesTableLib.h
@@ -0,0 +1,26 @@
+/** @file
+ Provides a service to retrieve a pointer to the EFI Runtime Services Table.
+
+ This library does not contain any functions or macros. It simply exports the
+ global variable gRT that is a pointer to the EFI Runtime Services Table as defined
+ in the UEFI Specification. The global variable gRT must be preinitialized to NULL.
+ The library constructor must set gRT to point at the EFI Runtime Services Table so
+ it is available at the module's entry point. Since there is overhead in initializing
+ this global variable, only those modules that actually require access to the EFI
+ Runtime Services Table should use this library.
+ Only available to DXE and UEFI module types.
+
+Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __UEFI_RUNTIME_SERVICES_TABLE_LIB_H__
+#define __UEFI_RUNTIME_SERVICES_TABLE_LIB_H__
+
+///
+/// Cached copy of the EFI Runtime Services Table
+///
+extern EFI_RUNTIME_SERVICES *gRT;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/DebugPort.h b/efi_memtest/memtest86+/efi/Include/Protocol/DebugPort.h
new file mode 100644
index 0000000..d6accb5
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/DebugPort.h
@@ -0,0 +1,140 @@
+/** @file
+
+ The file defines the EFI Debugport protocol.
+ This protocol is used by debug agent to communicate with the
+ remote debug host.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __DEBUG_PORT_H__
+#define __DEBUG_PORT_H__
+
+
+///
+/// DebugPortIo protocol {EBA4E8D2-3858-41EC-A281-2647BA9660D0}
+///
+#define EFI_DEBUGPORT_PROTOCOL_GUID \
+ { \
+ 0xEBA4E8D2, 0x3858, 0x41EC, {0xA2, 0x81, 0x26, 0x47, 0xBA, 0x96, 0x60, 0xD0 } \
+ }
+
+extern EFI_GUID gEfiDebugPortProtocolGuid;
+
+typedef struct _EFI_DEBUGPORT_PROTOCOL EFI_DEBUGPORT_PROTOCOL;
+
+//
+// DebugPort member functions
+//
+
+/**
+ Resets the debugport.
+
+ @param This A pointer to the EFI_DEBUGPORT_PROTOCOL instance.
+
+ @retval EFI_SUCCESS The debugport device was reset and is in usable state.
+ @retval EFI_DEVICE_ERROR The debugport device could not be reset and is unusable.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_DEBUGPORT_RESET)(
+ IN EFI_DEBUGPORT_PROTOCOL *This
+ );
+
+/**
+ Writes data to the debugport.
+
+ @param This A pointer to the EFI_DEBUGPORT_PROTOCOL instance.
+ @param Timeout The number of microseconds to wait before timing out a write operation.
+ @param BufferSize On input, the requested number of bytes of data to write. On output, the
+ number of bytes of data actually written.
+ @param Buffer A pointer to a buffer containing the data to write.
+
+ @retval EFI_SUCCESS The data was written.
+ @retval EFI_DEVICE_ERROR The device reported an error.
+ @retval EFI_TIMEOUT The data write was stopped due to a timeout.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_DEBUGPORT_WRITE)(
+ IN EFI_DEBUGPORT_PROTOCOL *This,
+ IN UINT32 Timeout,
+ IN OUT UINTN *BufferSize,
+ IN VOID *Buffer
+ );
+
+/**
+ Reads data from the debugport.
+
+ @param This A pointer to the EFI_DEBUGPORT_PROTOCOL instance.
+ @param Timeout The number of microseconds to wait before timing out a read operation.
+ @param BufferSize On input, the requested number of bytes of data to read. On output, the
+ number of bytes of data actually number of bytes
+ of data read and returned in Buffer.
+ @param Buffer A pointer to a buffer into which the data read will be saved.
+
+ @retval EFI_SUCCESS The data was read.
+ @retval EFI_DEVICE_ERROR The device reported an error.
+ @retval EFI_TIMEOUT The operation was stopped due to a timeout or overrun.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_DEBUGPORT_READ)(
+ IN EFI_DEBUGPORT_PROTOCOL *This,
+ IN UINT32 Timeout,
+ IN OUT UINTN *BufferSize,
+ OUT VOID *Buffer
+ );
+
+/**
+ Checks to see if any data is available to be read from the debugport device.
+
+ @param This A pointer to the EFI_DEBUGPORT_PROTOCOL instance.
+
+ @retval EFI_SUCCESS At least one byte of data is available to be read.
+ @retval EFI_DEVICE_ERROR The debugport device is not functioning correctly.
+ @retval EFI_NOT_READY No data is available to be read.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_DEBUGPORT_POLL)(
+ IN EFI_DEBUGPORT_PROTOCOL *This
+ );
+
+///
+/// This protocol provides the communication link between the debug agent and the remote host.
+///
+struct _EFI_DEBUGPORT_PROTOCOL {
+ EFI_DEBUGPORT_RESET Reset;
+ EFI_DEBUGPORT_WRITE Write;
+ EFI_DEBUGPORT_READ Read;
+ EFI_DEBUGPORT_POLL Poll;
+};
+
+//
+// DEBUGPORT variable definitions...
+//
+#define EFI_DEBUGPORT_VARIABLE_NAME L"DEBUGPORT"
+#define EFI_DEBUGPORT_VARIABLE_GUID EFI_DEBUGPORT_PROTOCOL_GUID
+
+extern EFI_GUID gEfiDebugPortVariableGuid;
+
+//
+// DebugPort device path definitions...
+//
+#define DEVICE_PATH_MESSAGING_DEBUGPORT EFI_DEBUGPORT_PROTOCOL_GUID
+
+extern EFI_GUID gEfiDebugPortDevicePathGuid;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ EFI_GUID Guid;
+} DEBUGPORT_DEVICE_PATH;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/DevicePath.h b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePath.h
index 5914cde..d826208 100644
--- a/efi_memtest/memtest86+/efi/Include/Protocol/DevicePath.h
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePath.h
@@ -13,7 +13,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#ifndef __EFI_DEVICE_PATH_PROTOCOL_H__
#define __EFI_DEVICE_PATH_PROTOCOL_H__
-#include <Guid/PcAnsi.h>
#include <IndustryStandard/Bluetooth.h>
#include <IndustryStandard/Acpi60.h>
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathFromText.h b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathFromText.h
new file mode 100644
index 0000000..5698020
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathFromText.h
@@ -0,0 +1,66 @@
+/** @file
+ EFI_DEVICE_PATH_FROM_TEXT_PROTOCOL as defined in UEFI 2.0.
+ This protocol provides service to convert text to device paths and device nodes.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __DEVICE_PATH_FROM_TEXT_PROTOCOL_H__
+#define __DEVICE_PATH_FROM_TEXT_PROTOCOL_H__
+
+///
+/// Device Path From Text protocol
+///
+#define EFI_DEVICE_PATH_FROM_TEXT_PROTOCOL_GUID \
+ { \
+ 0x5c99a21, 0xc70f, 0x4ad2, {0x8a, 0x5f, 0x35, 0xdf, 0x33, 0x43, 0xf5, 0x1e } \
+ }
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @retval a_pointer Pointer to the EFI device node.
+ @retval NULL if TextDeviceNode is NULL or there was insufficient memory.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_FROM_TEXT_NODE)(
+ IN CONST CHAR16 *TextDeviceNode
+ );
+
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device path character.
+
+ @retval a_pointer Pointer to the allocated device path.
+ @retval NULL if TextDeviceNode is NULL or there was insufficient memory.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_FROM_TEXT_PATH)(
+ IN CONST CHAR16 *TextDevicePath
+ );
+
+///
+/// This protocol converts text to device paths and device nodes.
+///
+typedef struct {
+ EFI_DEVICE_PATH_FROM_TEXT_NODE ConvertTextToDeviceNode;
+ EFI_DEVICE_PATH_FROM_TEXT_PATH ConvertTextToDevicePath;
+} EFI_DEVICE_PATH_FROM_TEXT_PROTOCOL;
+
+extern EFI_GUID gEfiDevicePathFromTextProtocolGuid;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathToText.h b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathToText.h
new file mode 100644
index 0000000..245dae4
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathToText.h
@@ -0,0 +1,79 @@
+/** @file
+ EFI_DEVICE_PATH_TO_TEXT_PROTOCOL as defined in UEFI 2.0.
+ This protocol provides service to convert device nodes and paths to text.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __DEVICE_PATH_TO_TEXT_PROTOCOL_H__
+#define __DEVICE_PATH_TO_TEXT_PROTOCOL_H__
+
+///
+/// Device Path To Text protocol
+///
+#define EFI_DEVICE_PATH_TO_TEXT_PROTOCOL_GUID \
+ { \
+ 0x8b843e20, 0x8132, 0x4852, {0x90, 0xcc, 0x55, 0x1a, 0x4e, 0x4a, 0x7f, 0x1c } \
+ }
+
+/**
+ Convert a device node to its text representation.
+
+ @param DeviceNode Points to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @retval a_pointer a pointer to the allocated text representation of the device node data
+ @retval NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+typedef
+CHAR16*
+(EFIAPI *EFI_DEVICE_PATH_TO_TEXT_NODE)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+/**
+ Convert a device path to its text representation.
+
+ @param DevicePath Points to the device path to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts The AllowShortcuts is FALSE, then the shortcut forms of
+ text representation for a device node cannot be used.
+
+ @retval a_pointer a pointer to the allocated text representation of the device node.
+ @retval NULL if DevicePath is NULL or there was insufficient memory.
+
+**/
+typedef
+CHAR16*
+(EFIAPI *EFI_DEVICE_PATH_TO_TEXT_PATH)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+///
+/// This protocol converts device paths and device nodes to text.
+///
+typedef struct {
+ EFI_DEVICE_PATH_TO_TEXT_NODE ConvertDeviceNodeToText;
+ EFI_DEVICE_PATH_TO_TEXT_PATH ConvertDevicePathToText;
+} EFI_DEVICE_PATH_TO_TEXT_PROTOCOL;
+
+extern EFI_GUID gEfiDevicePathToTextProtocolGuid;
+
+#endif
+
+
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathUtilities.h b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathUtilities.h
new file mode 100644
index 0000000..be12f2b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/DevicePathUtilities.h
@@ -0,0 +1,186 @@
+/** @file
+ EFI_DEVICE_PATH_UTILITIES_PROTOCOL as defined in UEFI 2.0.
+ Use to create and manipulate device paths and device nodes.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __DEVICE_PATH_UTILITIES_PROTOCOL_H__
+#define __DEVICE_PATH_UTILITIES_PROTOCOL_H__
+
+///
+/// Device Path Utilities protocol
+///
+#define EFI_DEVICE_PATH_UTILITIES_PROTOCOL_GUID \
+ { \
+ 0x379be4e, 0xd706, 0x437d, {0xb0, 0x37, 0xed, 0xb8, 0x2f, 0xb7, 0x72, 0xa4 } \
+ }
+
+/**
+ Returns the size of the device path, in bytes.
+
+ @param DevicePath Points to the start of the EFI device path.
+
+ @return Size Size of the specified device path, in bytes, including the end-of-path tag.
+ @retval 0 DevicePath is NULL
+
+**/
+typedef
+UINTN
+(EFIAPI *EFI_DEVICE_PATH_UTILS_GET_DEVICE_PATH_SIZE)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+
+/**
+ Create a duplicate of the specified path.
+
+ @param DevicePath Points to the source EFI device path.
+
+ @retval Pointer A pointer to the duplicate device path.
+ @retval NULL insufficient memory or DevicePath is NULL
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_DUP_DEVICE_PATH)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Create a new path by appending the second device path to the first.
+ If Src1 is NULL and Src2 is non-NULL, then a duplicate of Src2 is returned.
+ If Src1 is non-NULL and Src2 is NULL, then a duplicate of Src1 is returned.
+ If Src1 and Src2 are both NULL, then a copy of an end-of-device-path is returned.
+
+ @param Src1 Points to the first device path.
+ @param Src2 Points to the second device path.
+
+ @retval Pointer A pointer to the newly created device path.
+ @retval NULL Memory could not be allocated
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_APPEND_PATH)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *Src1,
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *Src2
+ );
+
+/**
+ Creates a new path by appending the device node to the device path.
+ If DeviceNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DeviceNode, followed by an end-of-device path device node is returned.
+ If both DeviceNode and DevicePath are NULL then a copy of an end-of-device-path device node is returned.
+
+ @param DevicePath Points to the device path.
+ @param DeviceNode Points to the device node.
+
+ @retval Pointer A pointer to the allocated device node.
+ @retval NULL There was insufficient memory.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_APPEND_NODE)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode
+ );
+
+/**
+ Creates a new path by appending the specified device path instance to the specified device path.
+
+ @param DevicePath Points to the device path. If NULL, then ignored.
+ @param DevicePathInstance Points to the device path instance.
+
+ @retval Pointer A pointer to the newly created device path
+ @retval NULL Memory could not be allocated or DevicePathInstance is NULL.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_APPEND_INSTANCE)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance
+ );
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ @param DevicePathInstance On input, this holds the pointer to the current device path
+ instance. On output, this holds the pointer to the next
+ device path instance or NULL if there are no more device
+ path instances in the device path.
+ @param DevicePathInstanceSize On output, this holds the size of the device path instance,
+ in bytes or zero, if DevicePathInstance is NULL.
+ If NULL, then the instance size is not output.
+
+ @retval Pointer A pointer to the copy of the current device path instance.
+ @retval NULL DevicePathInstace was NULL on entry or there was insufficient memory.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_GET_NEXT_INSTANCE)(
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePathInstance,
+ OUT UINTN *DevicePathInstanceSize
+ );
+
+/**
+ Creates a device node
+
+ @param NodeType NodeType is the device node type (EFI_DEVICE_PATH.Type) for
+ the new device node.
+ @param NodeSubType NodeSubType is the device node sub-type
+ EFI_DEVICE_PATH.SubType) for the new device node.
+ @param NodeLength NodeLength is the length of the device node
+ (EFI_DEVICE_PATH.Length) for the new device node.
+
+ @retval Pointer A pointer to the newly created device node.
+ @retval NULL NodeLength is less than
+ the size of the header or there was insufficient memory.
+
+**/
+typedef
+EFI_DEVICE_PATH_PROTOCOL*
+(EFIAPI *EFI_DEVICE_PATH_UTILS_CREATE_NODE)(
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+);
+
+/**
+ Returns whether a device path is multi-instance.
+
+ @param DevicePath Points to the device path. If NULL, then ignored.
+
+ @retval TRUE The device path has more than one instance
+ @retval FALSE The device path is empty or contains only a single instance.
+
+**/
+typedef
+BOOLEAN
+(EFIAPI *EFI_DEVICE_PATH_UTILS_IS_MULTI_INSTANCE)(
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+///
+/// This protocol is used to creates and manipulates device paths and device nodes.
+///
+typedef struct {
+ EFI_DEVICE_PATH_UTILS_GET_DEVICE_PATH_SIZE GetDevicePathSize;
+ EFI_DEVICE_PATH_UTILS_DUP_DEVICE_PATH DuplicateDevicePath;
+ EFI_DEVICE_PATH_UTILS_APPEND_PATH AppendDevicePath;
+ EFI_DEVICE_PATH_UTILS_APPEND_NODE AppendDeviceNode;
+ EFI_DEVICE_PATH_UTILS_APPEND_INSTANCE AppendDevicePathInstance;
+ EFI_DEVICE_PATH_UTILS_GET_NEXT_INSTANCE GetNextDevicePathInstance;
+ EFI_DEVICE_PATH_UTILS_IS_MULTI_INSTANCE IsDevicePathMultiInstance;
+ EFI_DEVICE_PATH_UTILS_CREATE_NODE CreateDeviceNode;
+} EFI_DEVICE_PATH_UTILITIES_PROTOCOL;
+
+extern EFI_GUID gEfiDevicePathUtilitiesProtocolGuid;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/GraphicsOutput.h b/efi_memtest/memtest86+/efi/Include/Protocol/GraphicsOutput.h
index 935f2f0..1115646 100644
--- a/efi_memtest/memtest86+/efi/Include/Protocol/GraphicsOutput.h
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/GraphicsOutput.h
@@ -11,11 +11,6 @@
#ifndef __GRAPHICS_OUTPUT_H__
#define __GRAPHICS_OUTPUT_H__
-#define EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID \
- { \
- 0x9042a9de, 0x23dc, 0x4a38, {0x96, 0xfb, 0x7a, 0xde, 0xd0, 0x80, 0x51, 0x6a } \
- }
-
typedef struct _EFI_GRAPHICS_OUTPUT_PROTOCOL EFI_GRAPHICS_OUTPUT_PROTOCOL;
typedef struct {
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/HiiFont.h b/efi_memtest/memtest86+/efi/Include/Protocol/HiiFont.h
new file mode 100644
index 0000000..1f2e321
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/HiiFont.h
@@ -0,0 +1,469 @@
+/** @file
+ The file provides services to retrieve font information.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+ @par Revision Reference:
+ This Protocol was introduced in UEFI Specification 2.1.
+
+**/
+
+#ifndef __HII_FONT_H__
+#define __HII_FONT_H__
+
+#include <Protocol/GraphicsOutput.h>
+#include <Protocol/HiiImage.h>
+
+#define EFI_HII_FONT_PROTOCOL_GUID \
+{ 0xe9ca4775, 0x8657, 0x47fc, { 0x97, 0xe7, 0x7e, 0xd6, 0x5a, 0x8, 0x43, 0x24 } }
+
+typedef struct _EFI_HII_FONT_PROTOCOL EFI_HII_FONT_PROTOCOL;
+
+typedef VOID *EFI_FONT_HANDLE;
+
+///
+/// EFI_HII_OUT_FLAGS.
+///
+typedef UINT32 EFI_HII_OUT_FLAGS;
+
+#define EFI_HII_OUT_FLAG_CLIP 0x00000001
+#define EFI_HII_OUT_FLAG_WRAP 0x00000002
+#define EFI_HII_OUT_FLAG_CLIP_CLEAN_Y 0x00000004
+#define EFI_HII_OUT_FLAG_CLIP_CLEAN_X 0x00000008
+#define EFI_HII_OUT_FLAG_TRANSPARENT 0x00000010
+#define EFI_HII_IGNORE_IF_NO_GLYPH 0x00000020
+#define EFI_HII_IGNORE_LINE_BREAK 0x00000040
+#define EFI_HII_DIRECT_TO_SCREEN 0x00000080
+
+/**
+ Definition of EFI_HII_ROW_INFO.
+**/
+typedef struct _EFI_HII_ROW_INFO {
+ ///
+ /// The index of the first character in the string which is displayed on the line.
+ ///
+ UINTN StartIndex;
+ ///
+ /// The index of the last character in the string which is displayed on the line.
+ /// If this is the same as StartIndex, then no characters are displayed.
+ ///
+ UINTN EndIndex;
+ UINTN LineHeight; ///< The height of the line, in pixels.
+ UINTN LineWidth; ///< The width of the text on the line, in pixels.
+
+ ///
+ /// The font baseline offset in pixels from the bottom of the row, or 0 if none.
+ ///
+ UINTN BaselineOffset;
+} EFI_HII_ROW_INFO;
+
+///
+/// Font info flag. All flags (FONT, SIZE, STYLE, and COLOR) are defined.
+/// They are defined as EFI_FONT_INFO_***
+///
+typedef UINT32 EFI_FONT_INFO_MASK;
+
+#define EFI_FONT_INFO_SYS_FONT 0x00000001
+#define EFI_FONT_INFO_SYS_SIZE 0x00000002
+#define EFI_FONT_INFO_SYS_STYLE 0x00000004
+#define EFI_FONT_INFO_SYS_FORE_COLOR 0x00000010
+#define EFI_FONT_INFO_SYS_BACK_COLOR 0x00000020
+#define EFI_FONT_INFO_RESIZE 0x00001000
+#define EFI_FONT_INFO_RESTYLE 0x00002000
+#define EFI_FONT_INFO_ANY_FONT 0x00010000
+#define EFI_FONT_INFO_ANY_SIZE 0x00020000
+#define EFI_FONT_INFO_ANY_STYLE 0x00040000
+
+//
+// EFI_FONT_INFO
+//
+typedef struct {
+ EFI_HII_FONT_STYLE FontStyle;
+ UINT16 FontSize; ///< character cell height in pixels
+ CHAR16 FontName[1];
+} EFI_FONT_INFO;
+
+/**
+ Describes font output-related information.
+
+ This structure is used for describing the way in which a string
+ should be rendered in a particular font. FontInfo specifies the
+ basic font information and ForegroundColor and BackgroundColor
+ specify the color in which they should be displayed. The flags
+ in FontInfoMask describe where the system default should be
+ supplied instead of the specified information. The flags also
+ describe what options can be used to make a match between the
+ font requested and the font available.
+**/
+typedef struct _EFI_FONT_DISPLAY_INFO {
+ EFI_GRAPHICS_OUTPUT_BLT_PIXEL ForegroundColor;
+ EFI_GRAPHICS_OUTPUT_BLT_PIXEL BackgroundColor;
+ EFI_FONT_INFO_MASK FontInfoMask;
+ EFI_FONT_INFO FontInfo;
+} EFI_FONT_DISPLAY_INFO;
+
+/**
+
+ This function renders a string to a bitmap or the screen using
+ the specified font, color and options. It either draws the
+ string and glyphs on an existing bitmap, allocates a new bitmap,
+ or uses the screen. The strings can be clipped or wrapped.
+ Optionally, the function also returns the information about each
+ row and the character position on that row. If
+ EFI_HII_OUT_FLAG_CLIP is set, then text will be formatted only
+ based on explicit line breaks and all pixels which would lie
+ outside the bounding box specified by Width and Height are
+ ignored. The information in the RowInfoArray only describes
+ characters which are at least partially displayed. For the final
+ row, the LineHeight and BaseLine may describe pixels that are
+ outside the limit specified by Height (unless
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_Y is specified) even though those
+ pixels were not drawn. The LineWidth may describe pixels which
+ are outside the limit specified by Width (unless
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_X is specified) even though those
+ pixels were not drawn. If EFI_HII_OUT_FLAG_CLIP_CLEAN_X is set,
+ then it modifies the behavior of EFI_HII_OUT_FLAG_CLIP so that
+ if a character's right-most on pixel cannot fit, then it will
+ not be drawn at all. This flag requires that
+ EFI_HII_OUT_FLAG_CLIP be set. If EFI_HII_OUT_FLAG_CLIP_CLEAN_Y
+ is set, then it modifies the behavior of EFI_HII_OUT_FLAG_CLIP
+ so that if a row's bottom-most pixel cannot fit, then it will
+ not be drawn at all. This flag requires that
+ EFI_HII_OUT_FLAG_CLIP be set. If EFI_HII_OUT_FLAG_WRAP is set,
+ then text will be wrapped at the right-most line-break
+ opportunity prior to a character whose right-most extent would
+ exceed Width. If no line-break opportunity can be found, then
+ the text will behave as if EFI_HII_OUT_FLAG_CLIP_CLEAN_X is set.
+ This flag cannot be used with EFI_HII_OUT_FLAG_CLIP_CLEAN_X. If
+ EFI_HII_OUT_FLAG_TRANSPARENT is set, then BackgroundColor is
+ ignored and all 'off' pixels in the character's drawn
+ will use the pixel value from Blt. This flag cannot be used if
+ Blt is NULL upon entry. If EFI_HII_IGNORE_IF_NO_GLYPH is set,
+ then characters which have no glyphs are not drawn. Otherwise,
+ they are replaced with Unicode character code 0xFFFD (REPLACEMENT
+ CHARACTER). If EFI_HII_IGNORE_LINE_BREAK is set, then explicit
+ line break characters will be ignored. If
+ EFI_HII_DIRECT_TO_SCREEN is set, then the string will be written
+ directly to the output device specified by Screen. Otherwise the
+ string will be rendered to the bitmap specified by Bitmap.
+
+ @param This A pointer to the EFI_HII_FONT_PROTOCOL instance.
+
+ @param Flags Describes how the string is to be drawn.
+
+ @param String Points to the null-terminated string to be
+
+ @param StringInfo Points to the string output information,
+ including the color and font. If NULL, then
+ the string will be output in the default
+ system font and color.
+
+ @param Blt If this points to a non-NULL on entry, this points
+ to the image, which is Width pixels wide and
+ Height pixels high. The string will be drawn onto
+ this image and EFI_HII_OUT_FLAG_CLIP is implied.
+ If this points to a NULL on entry, then a buffer
+ will be allocated to hold the generated image and
+ the pointer updated on exit. It is the caller's
+ responsibility to free this buffer.
+
+ @param BltX, BltY Specifies the offset from the left and top
+ edge of the image of the first character
+ cell in the image.
+
+ @param RowInfoArray If this is non-NULL on entry, then on
+ exit, this will point to an allocated buffer
+ containing row information and
+ RowInfoArraySize will be updated to contain
+ the number of elements. This array describes
+ the characters that were at least partially
+ drawn and the heights of the rows. It is the
+ caller's responsibility to free this buffer.
+
+ @param RowInfoArraySize If this is non-NULL on entry, then on
+ exit it contains the number of
+ elements in RowInfoArray.
+
+ @param ColumnInfoArray If this is non-NULL, then on return it
+ will be filled with the horizontal
+ offset for each character in the
+ string on the row where it is
+ displayed. Non-printing characters
+ will have the offset ~0. The caller is
+ responsible for allocating a buffer large
+ enough so that there is one entry for
+ each character in the string, not
+ including the null-terminator. It is
+ possible when character display is
+ normalized that some character cells
+ overlap.
+
+ @retval EFI_SUCCESS The string was successfully updated.
+
+ @retval EFI_OUT_OF_RESOURCES Unable to allocate an output buffer for RowInfoArray or Blt.
+
+ @retval EFI_INVALID_PARAMETER The String or Blt was NULL.
+
+ @retval EFI_INVALID_PARAMETER Flags were invalid combination.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_STRING_TO_IMAGE)(
+ IN CONST EFI_HII_FONT_PROTOCOL *This,
+ IN EFI_HII_OUT_FLAGS Flags,
+ IN CONST EFI_STRING String,
+ IN CONST EFI_FONT_DISPLAY_INFO *StringInfo,
+ IN OUT EFI_IMAGE_OUTPUT **Blt,
+ IN UINTN BltX,
+ IN UINTN BltY,
+ OUT EFI_HII_ROW_INFO **RowInfoArray OPTIONAL,
+ OUT UINTN *RowInfoArraySize OPTIONAL,
+ OUT UINTN *ColumnInfoArray OPTIONAL
+);
+
+
+
+/**
+
+ This function renders a string as a bitmap or to the screen
+ and can clip or wrap the string. The bitmap is either supplied
+ by the caller or allocated by the function. The
+ strings are drawn with the font, size and style specified and
+ can be drawn transparently or opaquely. The function can also
+ return information about each row and each character's
+ position on the row. If EFI_HII_OUT_FLAG_CLIP is set, then
+ text will be formatted based only on explicit line breaks, and
+ all pixels that would lie outside the bounding box specified
+ by Width and Height are ignored. The information in the
+ RowInfoArray only describes characters which are at least
+ partially displayed. For the final row, the LineHeight and
+ BaseLine may describe pixels which are outside the limit
+ specified by Height (unless EFI_HII_OUT_FLAG_CLIP_CLEAN_Y is
+ specified) even though those pixels were not drawn. If
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_X is set, then it modifies the
+ behavior of EFI_HII_OUT_FLAG_CLIP so that if a character's
+ right-most on pixel cannot fit, then it will not be drawn at
+ all. This flag requires that EFI_HII_OUT_FLAG_CLIP be set. If
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_Y is set, then it modifies the
+ behavior of EFI_HII_OUT_FLAG_CLIP so that if a row's bottom
+ most pixel cannot fit, then it will not be drawn at all. This
+ flag requires that EFI_HII_OUT_FLAG_CLIP be set. If
+ EFI_HII_OUT_FLAG_WRAP is set, then text will be wrapped at the
+ right-most line-break opportunity prior to a character whose
+ right-most extent would exceed Width. If no line-break
+ opportunity can be found, then the text will behave as if
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_X is set. This flag cannot be used
+ with EFI_HII_OUT_FLAG_CLIP_CLEAN_X. If
+ EFI_HII_OUT_FLAG_TRANSPARENT is set, then BackgroundColor is
+ ignored and all off" pixels in the character's glyph will
+ use the pixel value from Blt. This flag cannot be used if Blt
+ is NULL upon entry. If EFI_HII_IGNORE_IF_NO_GLYPH is set, then
+ characters which have no glyphs are not drawn. Otherwise, they
+ are replaced with Unicode character code 0xFFFD (REPLACEMENT
+ CHARACTER). If EFI_HII_IGNORE_LINE_BREAK is set, then explicit
+ line break characters will be ignored. If
+ EFI_HII_DIRECT_TO_SCREEN is set, then the string will be
+ written directly to the output device specified by Screen.
+ Otherwise the string will be rendered to the bitmap specified
+ by Bitmap.
+
+
+ @param This A pointer to the EFI_HII_FONT_PROTOCOL instance.
+
+ @param Flags Describes how the string is to be drawn.
+
+ @param PackageList
+ The package list in the HII database to
+ search for the specified string.
+
+ @param StringId The string's id, which is unique within
+ PackageList.
+
+ @param Language Points to the language for the retrieved
+ string. If NULL, then the current system
+ language is used.
+
+ @param StringInfo Points to the string output information,
+ including the color and font. If NULL, then
+ the string will be output in the default
+ system font and color.
+
+ @param Blt If this points to a non-NULL on entry, this points
+ to the image, which is Width pixels wide and
+ Height pixels high. The string will be drawn onto
+ this image and EFI_HII_OUT_FLAG_CLIP is implied.
+ If this points to a NULL on entry, then a buffer
+ will be allocated to hold the generated image and
+ the pointer updated on exit. It is the caller's
+ responsibility to free this buffer.
+
+ @param BltX, BltY Specifies the offset from the left and top
+ edge of the output image of the first
+ character cell in the image.
+
+ @param RowInfoArray If this is non-NULL on entry, then on
+ exit, this will point to an allocated
+ buffer containing row information and
+ RowInfoArraySize will be updated to
+ contain the number of elements. This array
+ describes the characters which were at
+ least partially drawn and the heights of
+ the rows. It is the caller's
+ responsibility to free this buffer.
+
+ @param RowInfoArraySize If this is non-NULL on entry, then on
+ exit it contains the number of
+ elements in RowInfoArray.
+
+ @param ColumnInfoArray If non-NULL, on return it is filled
+ with the horizontal offset for each
+ character in the string on the row
+ where it is displayed. Non-printing
+ characters will have the offset ~0.
+ The caller is responsible to allocate
+ a buffer large enough so that there is
+ one entry for each character in the
+ string, not including the
+ null-terminator. It is possible when
+ character display is normalized that
+ some character cells overlap.
+
+
+ @retval EFI_SUCCESS The string was successfully updated.
+
+ @retval EFI_OUT_OF_RESOURCES Unable to allocate an output
+ buffer for RowInfoArray or Blt.
+
+ @retval EFI_INVALID_PARAMETER The String, or Blt, or Height, or
+ Width was NULL.
+ @retval EFI_INVALID_PARAMETER The Blt or PackageList was NULL.
+ @retval EFI_INVALID_PARAMETER Flags were invalid combination.
+ @retval EFI_NOT_FOUND The specified PackageList is not in the Database,
+ or the stringid is not in the specified PackageList.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_STRING_ID_TO_IMAGE)(
+ IN CONST EFI_HII_FONT_PROTOCOL *This,
+ IN EFI_HII_OUT_FLAGS Flags,
+ IN EFI_HII_HANDLE PackageList,
+ IN EFI_STRING_ID StringId,
+ IN CONST CHAR8 *Language,
+ IN CONST EFI_FONT_DISPLAY_INFO *StringInfo OPTIONAL,
+ IN OUT EFI_IMAGE_OUTPUT **Blt,
+ IN UINTN BltX,
+ IN UINTN BltY,
+ OUT EFI_HII_ROW_INFO **RowInfoArray OPTIONAL,
+ OUT UINTN *RowInfoArraySize OPTIONAL,
+ OUT UINTN *ColumnInfoArray OPTIONAL
+);
+
+
+/**
+
+ Convert the glyph for a single character into a bitmap.
+
+ @param This A pointer to the EFI_HII_FONT_PROTOCOL instance.
+
+ @param Char The character to retrieve.
+
+ @param StringInfo Points to the string font and color
+ information or NULL if the string should use
+ the default system font and color.
+
+ @param Blt This must point to a NULL on entry. A buffer will
+ be allocated to hold the output and the pointer
+ updated on exit. It is the caller's responsibility
+ to free this buffer.
+
+ @param Baseline The number of pixels from the bottom of the bitmap
+ to the baseline.
+
+
+ @retval EFI_SUCCESS The glyph bitmap created.
+
+ @retval EFI_OUT_OF_RESOURCES Unable to allocate the output buffer Blt.
+
+ @retval EFI_WARN_UNKNOWN_GLYPH The glyph was unknown and was
+ replaced with the glyph for
+ Unicode character code 0xFFFD.
+
+ @retval EFI_INVALID_PARAMETER Blt is NULL, or Width is NULL, or
+ Height is NULL
+
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_GET_GLYPH)(
+ IN CONST EFI_HII_FONT_PROTOCOL *This,
+ IN CONST CHAR16 Char,
+ IN CONST EFI_FONT_DISPLAY_INFO *StringInfo,
+ OUT EFI_IMAGE_OUTPUT **Blt,
+ OUT UINTN *Baseline OPTIONAL
+);
+
+/**
+
+ This function iterates through fonts which match the specified
+ font, using the specified criteria. If String is non-NULL, then
+ all of the characters in the string must exist in order for a
+ candidate font to be returned.
+
+ @param This A pointer to the EFI_HII_FONT_PROTOCOL instance.
+
+ @param FontHandle On entry, points to the font handle returned
+ by a previous call to GetFontInfo() or NULL
+ to start with the first font. On return,
+ points to the returned font handle or points
+ to NULL if there are no more matching fonts.
+
+ @param StringInfoIn Upon entry, points to the font to return
+ information about. If NULL, then the information
+ about the system default font will be returned.
+
+ @param StringInfoOut Upon return, contains the matching font's information.
+ If NULL, then no information is returned. This buffer
+ is allocated with a call to the Boot Service AllocatePool().
+ It is the caller's responsibility to call the Boot
+ Service FreePool() when the caller no longer requires
+ the contents of StringInfoOut.
+
+ @param String Points to the string which will be tested to
+ determine if all characters are available. If
+ NULL, then any font is acceptable.
+
+ @retval EFI_SUCCESS Matching font returned successfully.
+
+ @retval EFI_NOT_FOUND No matching font was found.
+
+ @retval EFI_OUT_OF_RESOURCES There were insufficient resources to complete the request.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_GET_FONT_INFO)(
+ IN CONST EFI_HII_FONT_PROTOCOL *This,
+ IN OUT EFI_FONT_HANDLE *FontHandle,
+ IN CONST EFI_FONT_DISPLAY_INFO *StringInfoIn, OPTIONAL
+ OUT EFI_FONT_DISPLAY_INFO **StringInfoOut,
+ IN CONST EFI_STRING String OPTIONAL
+);
+
+///
+/// The protocol provides the service to retrieve the font informations.
+///
+struct _EFI_HII_FONT_PROTOCOL {
+ EFI_HII_STRING_TO_IMAGE StringToImage;
+ EFI_HII_STRING_ID_TO_IMAGE StringIdToImage;
+ EFI_HII_GET_GLYPH GetGlyph;
+ EFI_HII_GET_FONT_INFO GetFontInfo;
+};
+
+extern EFI_GUID gEfiHiiFontProtocolGuid;
+
+
+#endif
+
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/HiiImage.h b/efi_memtest/memtest86+/efi/Include/Protocol/HiiImage.h
new file mode 100644
index 0000000..d72ac76
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/HiiImage.h
@@ -0,0 +1,353 @@
+/** @file
+ The file provides services to access to images in the images database.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+ @par Revision Reference:
+ This Protocol was introduced in UEFI Specification 2.1.
+
+**/
+
+#ifndef __HII_IMAGE_H__
+#define __HII_IMAGE_H__
+
+#include <Protocol/GraphicsOutput.h>
+
+#define EFI_HII_IMAGE_PROTOCOL_GUID \
+ { 0x31a6406a, 0x6bdf, 0x4e46, { 0xb2, 0xa2, 0xeb, 0xaa, 0x89, 0xc4, 0x9, 0x20 } }
+
+typedef struct _EFI_HII_IMAGE_PROTOCOL EFI_HII_IMAGE_PROTOCOL;
+
+
+///
+/// Flags in EFI_IMAGE_INPUT
+///
+#define EFI_IMAGE_TRANSPARENT 0x00000001
+
+/**
+
+ Definition of EFI_IMAGE_INPUT.
+
+ @param Flags Describe image characteristics. If
+ EFI_IMAGE_TRANSPARENT is set, then the image was
+ designed for transparent display.
+
+ @param Width Image width, in pixels.
+
+ @param Height Image height, in pixels.
+
+ @param Bitmap A pointer to the actual bitmap, organized left-to-right,
+ top-to-bottom. The size of the bitmap is
+ Width*Height*sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL).
+
+
+**/
+typedef struct _EFI_IMAGE_INPUT {
+ UINT32 Flags;
+ UINT16 Width;
+ UINT16 Height;
+ EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Bitmap;
+} EFI_IMAGE_INPUT;
+
+
+/**
+
+ This function adds the image Image to the group of images
+ owned by PackageList, and returns a new image identifier
+ (ImageId).
+
+ @param This A pointer to the EFI_HII_IMAGE_PROTOCOL instance.
+
+ @param PackageList Handle of the package list where this image will be added.
+
+ @param ImageId On return, contains the new image id, which is
+ unique within PackageList.
+
+ @param Image Points to the image.
+
+ @retval EFI_SUCCESS The new image was added
+ successfully
+
+ @retval EFI_OUT_OF_RESOURCES Could not add the image.
+
+ @retval EFI_INVALID_PARAMETER Image is NULL or ImageId is
+ NULL.
+
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_NEW_IMAGE)(
+ IN CONST EFI_HII_IMAGE_PROTOCOL *This,
+ IN EFI_HII_HANDLE PackageList,
+ OUT EFI_IMAGE_ID *ImageId,
+ IN CONST EFI_IMAGE_INPUT *Image
+);
+
+/**
+
+ This function retrieves the image specified by ImageId which
+ is associated with the specified PackageList and copies it
+ into the buffer specified by Image. If the image specified by
+ ImageId is not present in the specified PackageList, then
+ EFI_NOT_FOUND is returned. If the buffer specified by
+ ImageSize is too small to hold the image, then
+ EFI_BUFFER_TOO_SMALL will be returned. ImageSize will be
+ updated to the size of buffer actually required to hold the
+ image.
+
+ @param This A pointer to the EFI_HII_IMAGE_PROTOCOL instance.
+
+ @param PackageList The package list in the HII database to
+ search for the specified image.
+
+ @param ImageId The image's id, which is unique within
+ PackageList.
+
+ @param Image Points to the new image.
+
+ @retval EFI_SUCCESS The image was returned successfully.
+
+ @retval EFI_NOT_FOUND The image specified by ImageId is not
+ available. Or The specified PackageList is not in the database.
+
+ @retval EFI_INVALID_PARAMETER The Image or Langugae was NULL.
+ @retval EFI_OUT_OF_RESOURCES The bitmap could not be retrieved because there was not
+ enough memory.
+
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_GET_IMAGE)(
+ IN CONST EFI_HII_IMAGE_PROTOCOL *This,
+ IN EFI_HII_HANDLE PackageList,
+ IN EFI_IMAGE_ID ImageId,
+ OUT EFI_IMAGE_INPUT *Image
+);
+
+/**
+
+ This function updates the image specified by ImageId in the
+ specified PackageListHandle to the image specified by Image.
+
+
+ @param This A pointer to the EFI_HII_IMAGE_PROTOCOL instance.
+
+ @param PackageList The package list containing the images.
+
+ @param ImageId The image id, which is unique within PackageList.
+
+ @param Image Points to the image.
+
+ @retval EFI_SUCCESS The image was successfully updated.
+
+ @retval EFI_NOT_FOUND The image specified by ImageId is not in the database.
+ The specified PackageList is not in the database.
+
+ @retval EFI_INVALID_PARAMETER The Image or Language was NULL.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_SET_IMAGE)(
+ IN CONST EFI_HII_IMAGE_PROTOCOL *This,
+ IN EFI_HII_HANDLE PackageList,
+ IN EFI_IMAGE_ID ImageId,
+ IN CONST EFI_IMAGE_INPUT *Image
+);
+
+
+///
+/// EFI_HII_DRAW_FLAGS describes how the image is to be drawn.
+/// These flags are defined as EFI_HII_DRAW_FLAG_***
+///
+typedef UINT32 EFI_HII_DRAW_FLAGS;
+
+#define EFI_HII_DRAW_FLAG_CLIP 0x00000001
+#define EFI_HII_DRAW_FLAG_TRANSPARENT 0x00000030
+#define EFI_HII_DRAW_FLAG_DEFAULT 0x00000000
+#define EFI_HII_DRAW_FLAG_FORCE_TRANS 0x00000010
+#define EFI_HII_DRAW_FLAG_FORCE_OPAQUE 0x00000020
+#define EFI_HII_DIRECT_TO_SCREEN 0x00000080
+
+/**
+
+ Definition of EFI_IMAGE_OUTPUT.
+
+ @param Width Width of the output image.
+
+ @param Height Height of the output image.
+
+ @param Bitmap Points to the output bitmap.
+
+ @param Screen Points to the EFI_GRAPHICS_OUTPUT_PROTOCOL which
+ describes the screen on which to draw the
+ specified image.
+
+**/
+typedef struct _EFI_IMAGE_OUTPUT {
+ UINT16 Width;
+ UINT16 Height;
+ union {
+ EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Bitmap;
+ EFI_GRAPHICS_OUTPUT_PROTOCOL *Screen;
+ } Image;
+} EFI_IMAGE_OUTPUT;
+
+
+/**
+
+ This function renders an image to a bitmap or the screen using
+ the specified color and options. It draws the image on an
+ existing bitmap, allocates a new bitmap or uses the screen. The
+ images can be clipped. If EFI_HII_DRAW_FLAG_CLIP is set, then
+ all pixels drawn outside the bounding box specified by Width and
+ Height are ignored. If EFI_HII_DRAW_FLAG_TRANSPARENT is set,
+ then all 'off' pixels in the images drawn will use the
+ pixel value from Blt. This flag cannot be used if Blt is NULL
+ upon entry. If EFI_HII_DIRECT_TO_SCREEN is set, then the image
+ will be written directly to the output device specified by
+ Screen. Otherwise the image will be rendered to the bitmap
+ specified by Bitmap.
+
+
+ @param This A pointer to the EFI_HII_IMAGE_PROTOCOL instance.
+
+ @param Flags Describes how the image is to be drawn.
+ EFI_HII_DRAW_FLAGS is defined in Related
+ Definitions, below.
+
+ @param Image Points to the image to be displayed.
+
+ @param Blt If this points to a non-NULL on entry, this points
+ to the image, which is Width pixels wide and
+ Height pixels high. The image will be drawn onto
+ this image and EFI_HII_DRAW_FLAG_CLIP is implied.
+ If this points to a NULL on entry, then a buffer
+ will be allocated to hold the generated image and
+ the pointer updated on exit. It is the caller's
+ responsibility to free this buffer.
+
+ @param BltX, BltY Specifies the offset from the left and top
+ edge of the image of the first pixel in
+ the image.
+
+ @retval EFI_SUCCESS The image was successfully updated.
+
+ @retval EFI_OUT_OF_RESOURCES Unable to allocate an output
+ buffer for RowInfoArray or Blt.
+
+ @retval EFI_INVALID_PARAMETER The Image or Blt or Height or
+ Width was NULL.
+
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_DRAW_IMAGE)(
+ IN CONST EFI_HII_IMAGE_PROTOCOL *This,
+ IN EFI_HII_DRAW_FLAGS Flags,
+ IN CONST EFI_IMAGE_INPUT *Image,
+ IN OUT EFI_IMAGE_OUTPUT **Blt,
+ IN UINTN BltX,
+ IN UINTN BltY
+);
+
+/**
+
+ This function renders an image as a bitmap or to the screen and
+ can clip the image. The bitmap is either supplied by the caller
+ or else is allocated by the function. The images can be drawn
+ transparently or opaquely. If EFI_HII_DRAW_FLAG_CLIP is set,
+ then all pixels drawn outside the bounding box specified by
+ Width and Height are ignored. If EFI_HII_DRAW_FLAG_TRANSPARENT
+ is set, then all "off" pixels in the character's glyph will
+ use the pixel value from Blt. This flag cannot be used if Blt
+ is NULL upon entry. If EFI_HII_DIRECT_TO_SCREEN is set, then
+ the image will be written directly to the output device
+ specified by Screen. Otherwise the image will be rendered to
+ the bitmap specified by Bitmap.
+ This function renders an image to a bitmap or the screen using
+ the specified color and options. It draws the image on an
+ existing bitmap, allocates a new bitmap or uses the screen. The
+ images can be clipped. If EFI_HII_DRAW_FLAG_CLIP is set, then
+ all pixels drawn outside the bounding box specified by Width and
+ Height are ignored. The EFI_HII_DRAW_FLAG_TRANSPARENT flag
+ determines whether the image will be drawn transparent or
+ opaque. If EFI_HII_DRAW_FLAG_FORCE_TRANS is set, then the image
+ will be drawn so that all 'off' pixels in the image will
+ be drawn using the pixel value from Blt and all other pixels
+ will be copied. If EFI_HII_DRAW_FLAG_FORCE_OPAQUE is set, then
+ the image's pixels will be copied directly to the
+ destination. If EFI_HII_DRAW_FLAG_DEFAULT is set, then the image
+ will be drawn transparently or opaque, depending on the
+ image's transparency setting (see EFI_IMAGE_TRANSPARENT).
+ Images cannot be drawn transparently if Blt is NULL. If
+ EFI_HII_DIRECT_TO_SCREEN is set, then the image will be written
+ directly to the output device specified by Screen. Otherwise the
+ image will be rendered to the bitmap specified by Bitmap.
+
+ @param This A pointer to the EFI_HII_IMAGE_PROTOCOL instance.
+
+ @param Flags Describes how the image is to be drawn.
+
+ @param PackageList The package list in the HII database to
+ search for the specified image.
+
+ @param ImageId The image's id, which is unique within PackageList.
+
+ @param Blt If this points to a non-NULL on entry, this points
+ to the image, which is Width pixels wide and
+ Height pixels high. The image will be drawn onto
+ this image and EFI_HII_DRAW_FLAG_CLIP is implied.
+ If this points to a NULL on entry, then a buffer
+ will be allocated to hold the generated image and
+ the pointer updated on exit. It is the caller's
+ responsibility to free this buffer.
+
+ @param BltX, BltY Specifies the offset from the left and top
+ edge of the output image of the first
+ pixel in the image.
+
+ @retval EFI_SUCCESS The image was successfully updated.
+
+ @retval EFI_OUT_OF_RESOURCES Unable to allocate an output
+ buffer for RowInfoArray or Blt.
+
+ @retval EFI_NOT_FOUND The image specified by ImageId is not in the database.
+ Or The specified PackageList is not in the database.
+
+ @retval EFI_INVALID_PARAMETER The Blt was NULL.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_HII_DRAW_IMAGE_ID)(
+IN CONST EFI_HII_IMAGE_PROTOCOL *This,
+IN EFI_HII_DRAW_FLAGS Flags,
+IN EFI_HII_HANDLE PackageList,
+IN EFI_IMAGE_ID ImageId,
+IN OUT EFI_IMAGE_OUTPUT **Blt,
+IN UINTN BltX,
+IN UINTN BltY
+);
+
+
+///
+/// Services to access to images in the images database.
+///
+struct _EFI_HII_IMAGE_PROTOCOL {
+ EFI_HII_NEW_IMAGE NewImage;
+ EFI_HII_GET_IMAGE GetImage;
+ EFI_HII_SET_IMAGE SetImage;
+ EFI_HII_DRAW_IMAGE DrawImage;
+ EFI_HII_DRAW_IMAGE_ID DrawImageId;
+};
+
+extern EFI_GUID gEfiHiiImageProtocolGuid;
+
+#endif
+
+
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/LoadedImage.h b/efi_memtest/memtest86+/efi/Include/Protocol/LoadedImage.h
new file mode 100644
index 0000000..9195785
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/LoadedImage.h
@@ -0,0 +1,79 @@
+/** @file
+ UEFI 2.0 Loaded image protocol definition.
+
+ Every EFI driver and application is passed an image handle when it is loaded.
+ This image handle will contain a Loaded Image Protocol.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "Efi_Defs_GUID.h"
+
+#ifndef __LOADED_IMAGE_PROTOCOL_H__
+#define __LOADED_IMAGE_PROTOCOL_H__
+
+#define EFI_LOADED_IMAGE_DEVICE_PATH_PROTOCOL_GUID \
+ { \
+ 0xbc62157e, 0x3e33, 0x4fec, {0x99, 0x20, 0x2d, 0x3b, 0x36, 0xd7, 0x50, 0xdf } \
+ }
+
+///
+/// Protocol GUID defined in EFI1.1.
+///
+#define LOADED_IMAGE_PROTOCOL EFI_LOADED_IMAGE_PROTOCOL_GUID
+
+///
+/// EFI_SYSTEM_TABLE & EFI_IMAGE_UNLOAD are defined in EfiApi.h
+///
+#define EFI_LOADED_IMAGE_PROTOCOL_REVISION 0x1000
+
+///
+/// Revision defined in EFI1.1.
+///
+#define EFI_LOADED_IMAGE_INFORMATION_REVISION EFI_LOADED_IMAGE_PROTOCOL_REVISION
+
+///
+/// Can be used on any image handle to obtain information about the loaded image.
+///
+typedef struct {
+ UINT32 Revision; ///< Defines the revision of the EFI_LOADED_IMAGE_PROTOCOL structure.
+ ///< All future revisions will be backward compatible to the current revision.
+ EFI_HANDLE ParentHandle; ///< Parent image's image handle. NULL if the image is loaded directly from
+ ///< the firmware's boot manager.
+ EFI_SYSTEM_TABLE *SystemTable; ///< the image's EFI system table pointer.
+
+ //
+ // Source location of image
+ //
+ EFI_HANDLE DeviceHandle; ///< The device handle that the EFI Image was loaded from.
+ EFI_DEVICE_PATH_PROTOCOL *FilePath; ///< A pointer to the file path portion specific to DeviceHandle
+ ///< that the EFI Image was loaded from.
+ VOID *Reserved; ///< Reserved. DO NOT USE.
+
+ //
+ // Images load options
+ //
+ UINT32 LoadOptionsSize;///< The size in bytes of LoadOptions.
+ VOID *LoadOptions; ///< A pointer to the image's binary load options.
+
+ //
+ // Location of where image was loaded
+ //
+ VOID *ImageBase; ///< The base address at which the image was loaded.
+ UINT64 ImageSize; ///< The size in bytes of the loaded image.
+ EFI_MEMORY_TYPE ImageCodeType; ///< The memory type that the code sections were loaded as.
+ EFI_MEMORY_TYPE ImageDataType; ///< The memory type that the data sections were loaded as.
+ EFI_IMAGE_UNLOAD Unload;
+} EFI_LOADED_IMAGE_PROTOCOL;
+
+//
+// For backward-compatible with EFI1.1.
+//
+typedef EFI_LOADED_IMAGE_PROTOCOL EFI_LOADED_IMAGE;
+
+extern EFI_GUID gEfiLoadedImageProtocolGuid;
+extern EFI_GUID gEfiLoadedImageDevicePathProtocolGuid;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/SimpleFileSystem.h b/efi_memtest/memtest86+/efi/Include/Protocol/SimpleFileSystem.h
index 38d54db..73aa92e 100644
--- a/efi_memtest/memtest86+/efi/Include/Protocol/SimpleFileSystem.h
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/SimpleFileSystem.h
@@ -15,11 +15,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#ifndef __SIMPLE_FILE_SYSTEM_H__
#define __SIMPLE_FILE_SYSTEM_H__
-#define EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_GUID \
- { \
- 0x964e5b22, 0x6459, 0x11d2, {0x8e, 0x39, 0x0, 0xa0, 0xc9, 0x69, 0x72, 0x3b } \
- }
-
typedef struct _EFI_SIMPLE_FILE_SYSTEM_PROTOCOL EFI_SIMPLE_FILE_SYSTEM_PROTOCOL;
typedef struct _EFI_FILE_PROTOCOL EFI_FILE_PROTOCOL;
diff --git a/efi_memtest/memtest86+/efi/Include/Protocol/UgaDraw.h b/efi_memtest/memtest86+/efi/Include/Protocol/UgaDraw.h
new file mode 100644
index 0000000..47286bb
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/Protocol/UgaDraw.h
@@ -0,0 +1,160 @@
+/** @file
+ UGA Draw protocol from the EFI 1.10 specification.
+
+ Abstraction of a very simple graphics device.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __UGA_DRAW_H__
+#define __UGA_DRAW_H__
+
+
+#define EFI_UGA_DRAW_PROTOCOL_GUID \
+ { \
+ 0x982c298b, 0xf4fa, 0x41cb, {0xb8, 0x38, 0x77, 0xaa, 0x68, 0x8f, 0xb8, 0x39 } \
+ }
+
+typedef struct _EFI_UGA_DRAW_PROTOCOL EFI_UGA_DRAW_PROTOCOL;
+
+/**
+ Return the current video mode information.
+
+ @param This The EFI_UGA_DRAW_PROTOCOL instance.
+ @param HorizontalResolution The size of video screen in pixels in the X dimension.
+ @param VerticalResolution The size of video screen in pixels in the Y dimension.
+ @param ColorDepth Number of bits per pixel, currently defined to be 32.
+ @param RefreshRate The refresh rate of the monitor in Hertz.
+
+ @retval EFI_SUCCESS Mode information returned.
+ @retval EFI_NOT_STARTED Video display is not initialized. Call SetMode ()
+ @retval EFI_INVALID_PARAMETER One of the input args was NULL.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_UGA_DRAW_PROTOCOL_GET_MODE)(
+ IN EFI_UGA_DRAW_PROTOCOL *This,
+ OUT UINT32 *HorizontalResolution,
+ OUT UINT32 *VerticalResolution,
+ OUT UINT32 *ColorDepth,
+ OUT UINT32 *RefreshRate
+ );
+
+/**
+ Set the current video mode information.
+
+ @param This The EFI_UGA_DRAW_PROTOCOL instance.
+ @param HorizontalResolution The size of video screen in pixels in the X dimension.
+ @param VerticalResolution The size of video screen in pixels in the Y dimension.
+ @param ColorDepth Number of bits per pixel, currently defined to be 32.
+ @param RefreshRate The refresh rate of the monitor in Hertz.
+
+ @retval EFI_SUCCESS Mode information returned.
+ @retval EFI_NOT_STARTED Video display is not initialized. Call SetMode ()
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_UGA_DRAW_PROTOCOL_SET_MODE)(
+ IN EFI_UGA_DRAW_PROTOCOL *This,
+ IN UINT32 HorizontalResolution,
+ IN UINT32 VerticalResolution,
+ IN UINT32 ColorDepth,
+ IN UINT32 RefreshRate
+ );
+
+typedef struct {
+ UINT8 Blue;
+ UINT8 Green;
+ UINT8 Red;
+ UINT8 Reserved;
+} EFI_UGA_PIXEL;
+
+typedef union {
+ EFI_UGA_PIXEL Pixel;
+ UINT32 Raw;
+} EFI_UGA_PIXEL_UNION;
+
+///
+/// Enumration value for actions of Blt operations.
+///
+typedef enum {
+ EfiUgaVideoFill, ///< Write data from the BltBuffer pixel (SourceX, SourceY)
+ ///< directly to every pixel of the video display rectangle
+ ///< (DestinationX, DestinationY) (DestinationX + Width, DestinationY + Height).
+ ///< Only one pixel will be used from the BltBuffer. Delta is NOT used.
+
+ EfiUgaVideoToBltBuffer, ///< Read data from the video display rectangle
+ ///< (SourceX, SourceY) (SourceX + Width, SourceY + Height) and place it in
+ ///< the BltBuffer rectangle (DestinationX, DestinationY )
+ ///< (DestinationX + Width, DestinationY + Height). If DestinationX or
+ ///< DestinationY is not zero then Delta must be set to the length in bytes
+ ///< of a row in the BltBuffer.
+
+ EfiUgaBltBufferToVideo, ///< Write data from the BltBuffer rectangle
+ ///< (SourceX, SourceY) (SourceX + Width, SourceY + Height) directly to the
+ ///< video display rectangle (DestinationX, DestinationY)
+ ///< (DestinationX + Width, DestinationY + Height). If SourceX or SourceY is
+ ///< not zero then Delta must be set to the length in bytes of a row in the
+ ///< BltBuffer.
+
+ EfiUgaVideoToVideo, ///< Copy from the video display rectangle (SourceX, SourceY)
+ ///< (SourceX + Width, SourceY + Height) .to the video display rectangle
+ ///< (DestinationX, DestinationY) (DestinationX + Width, DestinationY + Height).
+ ///< The BltBuffer and Delta are not used in this mode.
+
+ EfiUgaBltMax ///< Maxmimum value for enumration value of Blt operation. If a Blt operation
+ ///< larger or equal to this enumration value, it is invalid.
+} EFI_UGA_BLT_OPERATION;
+
+/**
+ Blt a rectangle of pixels on the graphics screen.
+
+ @param[in] This - Protocol instance pointer.
+ @param[in] BltBuffer - Buffer containing data to blit into video buffer. This
+ buffer has a size of Width*Height*sizeof(EFI_UGA_PIXEL)
+ @param[in] BltOperation - Operation to perform on BlitBuffer and video memory
+ @param[in] SourceX - X coordinate of source for the BltBuffer.
+ @param[in] SourceY - Y coordinate of source for the BltBuffer.
+ @param[in] DestinationX - X coordinate of destination for the BltBuffer.
+ @param[in] DestinationY - Y coordinate of destination for the BltBuffer.
+ @param[in] Width - Width of rectangle in BltBuffer in pixels.
+ @param[in] Height - Hight of rectangle in BltBuffer in pixels.
+ @param[in] Delta - OPTIONAL
+
+ @retval EFI_SUCCESS - The Blt operation completed.
+ @retval EFI_INVALID_PARAMETER - BltOperation is not valid.
+ @retval EFI_DEVICE_ERROR - A hardware error occurred writting to the video buffer.
+
+**/
+typedef
+EFI_STATUS
+(EFIAPI *EFI_UGA_DRAW_PROTOCOL_BLT)(
+ IN EFI_UGA_DRAW_PROTOCOL * This,
+ IN EFI_UGA_PIXEL * BltBuffer, OPTIONAL
+ IN EFI_UGA_BLT_OPERATION BltOperation,
+ IN UINTN SourceX,
+ IN UINTN SourceY,
+ IN UINTN DestinationX,
+ IN UINTN DestinationY,
+ IN UINTN Width,
+ IN UINTN Height,
+ IN UINTN Delta OPTIONAL
+ );
+
+///
+/// This protocol provides a basic abstraction to set video modes and
+/// copy pixels to and from the graphics controller's frame buffer.
+///
+struct _EFI_UGA_DRAW_PROTOCOL {
+ EFI_UGA_DRAW_PROTOCOL_GET_MODE GetMode;
+ EFI_UGA_DRAW_PROTOCOL_SET_MODE SetMode;
+ EFI_UGA_DRAW_PROTOCOL_BLT Blt;
+};
+
+extern EFI_GUID gEfiUgaDrawProtocolGuid;
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/Uefi/UefiInternalFormRepresentation.h b/efi_memtest/memtest86+/efi/Include/Uefi/UefiInternalFormRepresentation.h
index 40fcdb7..1535ca6 100644
--- a/efi_memtest/memtest86+/efi/Include/Uefi/UefiInternalFormRepresentation.h
+++ b/efi_memtest/memtest86+/efi/Include/Uefi/UefiInternalFormRepresentation.h
@@ -15,8 +15,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#ifndef __UEFI_INTERNAL_FORMREPRESENTATION_H__
#define __UEFI_INTERNAL_FORMREPRESENTATION_H__
-#include <Guid/HiiFormMapMethodGuid.h>
-
///
/// The following types are currently defined:
///
diff --git a/efi_memtest/memtest86+/efi/Include/libs/BaseDebugPrintErrorLevelLib.lib b/efi_memtest/memtest86+/efi/Include/libs/BaseDebugPrintErrorLevelLib.lib
deleted file mode 100644
index 435f4e2..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/BaseDebugPrintErrorLevelLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/BaseLib.lib b/efi_memtest/memtest86+/efi/Include/libs/BaseLib.lib
deleted file mode 100644
index 676c5a9..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/BaseLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/BaseMemoryLib.lib b/efi_memtest/memtest86+/efi/Include/libs/BaseMemoryLib.lib
deleted file mode 100644
index 15f74d2..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/BaseMemoryLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/BasePcdLibNull.lib b/efi_memtest/memtest86+/efi/Include/libs/BasePcdLibNull.lib
deleted file mode 100644
index 4b10117..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/BasePcdLibNull.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/BasePrintLib.lib b/efi_memtest/memtest86+/efi/Include/libs/BasePrintLib.lib
deleted file mode 100644
index 10650b0..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/BasePrintLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiApplicationEntryPoint.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiApplicationEntryPoint.lib
deleted file mode 100644
index de9d990..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiApplicationEntryPoint.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiBootServicesTableLib.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiBootServicesTableLib.lib
deleted file mode 100644
index 8e880f0..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiBootServicesTableLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiDebugLibStdErr.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiDebugLibStdErr.lib
deleted file mode 100644
index 1864609..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiDebugLibStdErr.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiDevicePathLib.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiDevicePathLib.lib
deleted file mode 100644
index 99bef02..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiDevicePathLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiLib.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiLib.lib
deleted file mode 100644
index d8170ed..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiMemoryAllocationLib.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiMemoryAllocationLib.lib
deleted file mode 100644
index 0e2ce9d..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiMemoryAllocationLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/libs/UefiRuntimeServicesTableLib.lib b/efi_memtest/memtest86+/efi/Include/libs/UefiRuntimeServicesTableLib.lib
deleted file mode 100644
index e31760f..0000000
--- a/efi_memtest/memtest86+/efi/Include/libs/UefiRuntimeServicesTableLib.lib
+++ /dev/null
Binary files differ
diff --git a/efi_memtest/memtest86+/efi/Include/src/ApplicationEntryPoint.c b/efi_memtest/memtest86+/efi/Include/src/ApplicationEntryPoint.c
new file mode 100644
index 0000000..324e88c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/ApplicationEntryPoint.c
@@ -0,0 +1,115 @@
+/** @file
+ Entry point library instance to a UEFI application.
+
+Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Uefi.h>
+#include <Library/UefiApplicationEntryPoint.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+
+
+/**
+ Entry point to UEFI Application.
+
+ This function is the entry point for a UEFI Application. This function must call
+ ProcessLibraryConstructorList(), ProcessModuleEntryPointList(), and ProcessLibraryDestructorList().
+ The return value from ProcessModuleEntryPointList() is returned.
+ If _gUefiDriverRevision is not zero and SystemTable->Hdr.Revision is less than _gUefiDriverRevison,
+ then return EFI_INCOMPATIBLE_VERSION.
+
+ @param ImageHandle The image handle of the UEFI Application.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The UEFI Application exited normally.
+ @retval EFI_INCOMPATIBLE_VERSION _gUefiDriverRevision is greater than SystemTable->Hdr.Revision.
+ @retval Other Return value from ProcessModuleEntryPointList().
+
+**/
+EFI_STATUS
+EFIAPI
+_ModuleEntryPoint (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ if (_gUefiDriverRevision != 0) {
+ //
+ // Make sure that the EFI/UEFI spec revision of the platform is >= EFI/UEFI spec revision of the application.
+ //
+ if (SystemTable->Hdr.Revision < _gUefiDriverRevision) {
+ return EFI_INCOMPATIBLE_VERSION;
+ }
+ }
+
+ //
+ // Call constructor for all libraries.
+ //
+ ProcessLibraryConstructorList (ImageHandle, SystemTable);
+
+ //
+ // Call the module's entry point
+ //
+ Status = ProcessModuleEntryPointList (ImageHandle, SystemTable);
+
+ //
+ // Process destructor for all libraries.
+ //
+ ProcessLibraryDestructorList (ImageHandle, SystemTable);
+
+ //
+ // Return the return status code from the driver entry point
+ //
+ return Status;
+}
+
+
+/**
+ Invokes the library destructors for all dependent libraries and terminates
+ the UEFI Application.
+
+ This function calls ProcessLibraryDestructorList() and the EFI Boot Service Exit()
+ with a status specified by Status.
+
+ @param Status Status returned by the application that is exiting.
+
+**/
+VOID
+EFIAPI
+Exit (
+ IN EFI_STATUS Status
+ )
+
+{
+ ProcessLibraryDestructorList (gImageHandle, gST);
+
+ gBS->Exit (gImageHandle, Status, 0, NULL);
+}
+
+
+/**
+ Required by the EBC compiler and identical in functionality to _ModuleEntryPoint().
+
+ @param ImageHandle The image handle of the UEFI Application.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The UEFI Application exited normally.
+ @retval EFI_INCOMPATIBLE_VERSION _gUefiDriverRevision is greater than SystemTable->Hdr.Revision.
+ @retval Other Return value from ProcessModuleEntryPointList().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiMain (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ return _ModuleEntryPoint (ImageHandle, SystemTable);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseDebugPrintErrorLevelLib.c b/efi_memtest/memtest86+/efi/Include/src/BaseDebugPrintErrorLevelLib.c
new file mode 100644
index 0000000..265d6a0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseDebugPrintErrorLevelLib.c
@@ -0,0 +1,55 @@
+/** @file
+ Debug Print Error Level library instance that retrieves the current error
+ level from PcdDebugPrintErrorLevel. This generic library instance does not
+ support the setting of the global debug print error level mask for the platform.
+
+ Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Base.h>
+#include <Library/DebugPrintErrorLevelLib.h>
+#include <Library/PcdLib.h>
+
+#include "Efi_Defs.h"
+
+/**
+ Returns the debug print error level mask for the current module.
+
+ @return Debug print error level mask for the current module.
+
+**/
+UINT32
+EFIAPI
+GetDebugPrintErrorLevel (
+ VOID
+ )
+{
+ //
+ // Retrieve the current debug print error level mask from PcdDebugPrintErrorLevel.
+ //
+ return PcdGet32 (PcdDebugPrintErrorLevel);
+}
+
+/**
+ Sets the global debug print error level mask fpr the entire platform.
+
+ @param ErrorLevel Global debug print error level.
+
+ @retval TRUE The debug print error level mask was sucessfully set.
+ @retval FALSE The debug print error level mask could not be set.
+
+**/
+BOOLEAN
+EFIAPI
+SetDebugPrintErrorLevel (
+ UINT32 ErrorLevel
+ )
+{
+ //
+ // This library uinstance does not support setting the global debug print error
+ // level mask.
+ //
+ return FALSE;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/ARShiftU64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ARShiftU64.c
new file mode 100644
index 0000000..9928854
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ARShiftU64.c
@@ -0,0 +1,35 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. The high bits are filled
+ with the original integer's bit 63. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to bit 63 of Operand. The shifted value is returned.
+
+ If Count is greater than 63, then ASSERT().
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand >> Count
+
+**/
+UINT64
+EFIAPI
+ARShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 64);
+ return InternalMathARShiftU64 (Operand, Count);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/BaseLibInternals.h b/efi_memtest/memtest86+/efi/Include/src/BaseLib/BaseLibInternals.h
new file mode 100644
index 0000000..6837d67
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/BaseLibInternals.h
@@ -0,0 +1,869 @@
+/** @file
+ Declaration of internal functions in BaseLib.
+
+ Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __BASE_LIB_INTERNALS__
+#define __BASE_LIB_INTERNALS__
+
+#include <Base.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+
+//
+// Math functions
+//
+
+/**
+ Shifts a 64-bit integer left between 0 and 63 bits. The low bits
+ are filled with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the left by Count bits. The
+ low Count bits are set to zero. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift left.
+ @param Count The number of bits to shift left.
+
+ @return Operand << Count
+
+**/
+UINT64
+EFIAPI
+InternalMathLShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ );
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. The high bits
+ are filled with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to zero. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand >> Count
+
+**/
+UINT64
+EFIAPI
+InternalMathRShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ );
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. The high bits
+ are filled with original integer's bit 63. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to bit 63 of Operand. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand arithmetically shifted right by Count
+
+**/
+UINT64
+EFIAPI
+InternalMathARShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ );
+
+/**
+ Rotates a 64-bit integer left between 0 and 63 bits, filling
+ the low bits with the high bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the left by Count bits. The
+ low Count bits are filled with the high Count bits of Operand. The rotated
+ value is returned.
+
+ @param Operand The 64-bit operand to rotate left.
+ @param Count The number of bits to rotate left.
+
+ @return Operand <<< Count
+
+**/
+UINT64
+EFIAPI
+InternalMathLRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ );
+
+/**
+ Rotates a 64-bit integer right between 0 and 63 bits, filling
+ the high bits with the high low bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the right by Count bits.
+ The high Count bits are filled with the low Count bits of Operand. The rotated
+ value is returned.
+
+ @param Operand The 64-bit operand to rotate right.
+ @param Count The number of bits to rotate right.
+
+ @return Operand >>> Count
+
+**/
+UINT64
+EFIAPI
+InternalMathRRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ );
+
+/**
+ Switches the endianess of a 64-bit integer.
+
+ This function swaps the bytes in a 64-bit unsigned value to switch the value
+ from little endian to big endian or vice versa. The byte swapped value is
+ returned.
+
+ @param Operand A 64-bit unsigned value.
+
+ @return The byte swapped Operand.
+
+**/
+UINT64
+EFIAPI
+InternalMathSwapBytes64 (
+ IN UINT64 Operand
+ );
+
+/**
+ Multiplies a 64-bit unsigned integer by a 32-bit unsigned integer
+ and generates a 64-bit unsigned result.
+
+ This function multiplies the 64-bit unsigned value Multiplicand by the 32-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 32-bit unsigned value.
+
+ @return Multiplicand * Multiplier
+
+**/
+UINT64
+EFIAPI
+InternalMathMultU64x32 (
+ IN UINT64 Multiplicand,
+ IN UINT32 Multiplier
+ );
+
+/**
+ Multiplies a 64-bit unsigned integer by a 64-bit unsigned integer
+ and generates a 64-bit unsigned result.
+
+ This function multiples the 64-bit unsigned value Multiplicand by the 64-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 64-bit unsigned value.
+
+ @return Multiplicand * Multiplier
+
+**/
+UINT64
+EFIAPI
+InternalMathMultU64x64 (
+ IN UINT64 Multiplicand,
+ IN UINT64 Multiplier
+ );
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 64-bit unsigned result.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. This
+ function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+InternalMathDivU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ );
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 32-bit remainder. This function
+ returns the 32-bit unsigned remainder.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend % Divisor
+
+**/
+UINT32
+EFIAPI
+InternalMathModU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ );
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 64-bit unsigned result and an optional 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 32-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+ @param Remainder A pointer to a 32-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+InternalMathDivRemU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor,
+ OUT UINT32 *Remainder OPTIONAL
+ );
+
+/**
+ Divides a 64-bit unsigned integer by a 64-bit unsigned integer and
+ generates a 64-bit unsigned result and an optional 64-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 64-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 64-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 64-bit unsigned value.
+ @param Remainder A pointer to a 64-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+InternalMathDivRemU64x64 (
+ IN UINT64 Dividend,
+ IN UINT64 Divisor,
+ OUT UINT64 *Remainder OPTIONAL
+ );
+
+/**
+ Divides a 64-bit signed integer by a 64-bit signed integer and
+ generates a 64-bit signed result and an optional 64-bit signed remainder.
+
+ This function divides the 64-bit signed value Dividend by the 64-bit
+ signed value Divisor and generates a 64-bit signed quotient. If Remainder
+ is not NULL, then the 64-bit signed remainder is returned in Remainder.
+ This function returns the 64-bit signed quotient.
+
+ @param Dividend A 64-bit signed value.
+ @param Divisor A 64-bit signed value.
+ @param Remainder A pointer to a 64-bit signed value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+INT64
+EFIAPI
+InternalMathDivRemS64x64 (
+ IN INT64 Dividend,
+ IN INT64 Divisor,
+ OUT INT64 *Remainder OPTIONAL
+ );
+
+/**
+ Transfers control to a function starting with a new stack.
+
+ Transfers control to the function specified by EntryPoint using the
+ new stack specified by NewStack and passing in the parameters specified
+ by Context1 and Context2. Context1 and Context2 are optional and may
+ be NULL. The function EntryPoint must never return.
+ Marker will be ignored on IA-32, x64, and EBC.
+ IPF CPUs expect one additional parameter of type VOID * that specifies
+ the new backing store pointer.
+
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ @param EntryPoint A pointer to function to call with the new stack.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function.
+ @param Marker VA_LIST marker for the variable argument list.
+
+**/
+VOID
+EFIAPI
+InternalSwitchStack (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack,
+ IN VA_LIST Marker
+ );
+
+
+/**
+ Worker function that returns a bit field from Operand.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+
+ @return The bit field read.
+
+**/
+UINTN
+EFIAPI
+BitFieldReadUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ );
+
+
+/**
+ Worker function that reads a bit field from Operand, performs a bitwise OR,
+ and returns the result.
+
+ Performs a bitwise OR between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new value is returned.
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ @param OrData The value to OR with the read value from the value
+
+ @return The new value.
+
+**/
+UINTN
+EFIAPI
+BitFieldOrUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINTN OrData
+ );
+
+
+/**
+ Worker function that reads a bit field from Operand, performs a bitwise AND,
+ and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new value is returned.
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ @param AndData The value to And with the read value from the value
+
+ @return The new value.
+
+**/
+UINTN
+EFIAPI
+BitFieldAndUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINTN AndData
+ );
+
+
+/**
+ Worker function that checks ASSERT condition for JumpBuffer
+
+ Checks ASSERT condition for JumpBuffer.
+
+ If JumpBuffer is NULL, then ASSERT().
+ For IPF CPUs, if JumpBuffer is not aligned on a 16-byte boundary, then ASSERT().
+
+ @param JumpBuffer A pointer to CPU context buffer.
+
+**/
+VOID
+EFIAPI
+InternalAssertJumpBuffer (
+ IN BASE_LIBRARY_JUMP_BUFFER *JumpBuffer
+ );
+
+
+/**
+ Restores the CPU context that was saved with SetJump().
+
+ Restores the CPU context from the buffer specified by JumpBuffer.
+ This function never returns to the caller.
+ Instead is resumes execution based on the state of JumpBuffer.
+
+ @param JumpBuffer A pointer to CPU context buffer.
+ @param Value The value to return when the SetJump() context is restored.
+
+**/
+VOID
+EFIAPI
+InternalLongJump (
+ IN BASE_LIBRARY_JUMP_BUFFER *JumpBuffer,
+ IN UINTN Value
+ );
+
+
+/**
+ Check if a Unicode character is a decimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid decimal character is from
+ L'0' to L'9'.
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a decmial character.
+ @retval FALSE If the Char is not a decmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalIsDecimalDigitCharacter (
+ IN CHAR16 Char
+ );
+
+
+/**
+ Convert a Unicode character to numerical value.
+
+ This internal function only deal with Unicode character
+ which maps to a valid hexadecimal ASII character, i.e.
+ L'0' to L'9', L'a' to L'f' or L'A' to L'F'. For other
+ Unicode character, the value returned does not make sense.
+
+ @param Char The character to convert.
+
+ @return The numerical value converted.
+
+**/
+UINTN
+EFIAPI
+InternalHexCharToUintn (
+ IN CHAR16 Char
+ );
+
+
+/**
+ Check if a Unicode character is a hexadecimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid hexadecimal character is
+ L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
+
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a hexadecmial character.
+ @retval FALSE If the Char is not a hexadecmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalIsHexaDecimalDigitCharacter (
+ IN CHAR16 Char
+ );
+
+
+/**
+ Check if a ASCII character is a decimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid decimal character is from
+ '0' to '9'.
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a decmial character.
+ @retval FALSE If the Char is not a decmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalAsciiIsDecimalDigitCharacter (
+ IN CHAR8 Char
+ );
+
+
+/**
+ Check if a ASCII character is a hexadecimal character.
+
+ This internal function checks if a ASCII character is a
+ decimal character. The valid hexadecimal character is
+ L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
+
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a hexadecmial character.
+ @retval FALSE If the Char is not a hexadecmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalAsciiIsHexaDecimalDigitCharacter (
+ IN CHAR8 Char
+ );
+
+
+/**
+ Convert a ASCII character to numerical value.
+
+ This internal function only deal with Unicode character
+ which maps to a valid hexadecimal ASII character, i.e.
+ '0' to '9', 'a' to 'f' or 'A' to 'F'. For other
+ ASCII character, the value returned does not make sense.
+
+ @param Char The character to convert.
+
+ @return The numerical value converted.
+
+**/
+UINTN
+EFIAPI
+InternalAsciiHexCharToUintn (
+ IN CHAR8 Char
+ );
+
+
+//
+// Ia32 and x64 specific functions
+//
+#if defined (MDE_CPU_IA32) || defined (MDE_CPU_X64)
+
+/**
+ Reads the current Global Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current GDTR descriptor and returns it in Gdtr. This
+ function is only available on IA-32 and x64.
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86ReadGdtr (
+ OUT IA32_DESCRIPTOR *Gdtr
+ );
+
+/**
+ Writes the current Global Descriptor Table Register (GDTR) descriptor.
+
+ Writes and the current GDTR descriptor specified by Gdtr. This function is
+ only available on IA-32 and x64.
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86WriteGdtr (
+ IN CONST IA32_DESCRIPTOR *Gdtr
+ );
+
+/**
+ Reads the current Interrupt Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current IDTR descriptor and returns it in Idtr. This
+ function is only available on IA-32 and x64.
+
+ @param Idtr The pointer to an IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86ReadIdtr (
+ OUT IA32_DESCRIPTOR *Idtr
+ );
+
+/**
+ Writes the current Interrupt Descriptor Table Register(GDTR) descriptor.
+
+ Writes the current IDTR descriptor and returns it in Idtr. This function is
+ only available on IA-32 and x64.
+
+ @param Idtr The pointer to an IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86WriteIdtr (
+ IN CONST IA32_DESCRIPTOR *Idtr
+ );
+
+/**
+ Save the current floating point/SSE/SSE2 context to a buffer.
+
+ Saves the current floating point/SSE/SSE2 state to the buffer specified by
+ Buffer. Buffer must be aligned on a 16-byte boundary. This function is only
+ available on IA-32 and x64.
+
+ @param Buffer The pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+InternalX86FxSave (
+ OUT IA32_FX_BUFFER *Buffer
+ );
+
+/**
+ Restores the current floating point/SSE/SSE2 context from a buffer.
+
+ Restores the current floating point/SSE/SSE2 state from the buffer specified
+ by Buffer. Buffer must be aligned on a 16-byte boundary. This function is
+ only available on IA-32 and x64.
+
+ @param Buffer The pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+InternalX86FxRestore (
+ IN CONST IA32_FX_BUFFER *Buffer
+ );
+
+/**
+ Enables the 32-bit paging mode on the CPU.
+
+ Enables the 32-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode. This function is
+ only available on IA-32. After the 32-bit paging mode is enabled, control is
+ transferred to the function specified by EntryPoint using the new stack
+ specified by NewStack and passing in the parameters specified by Context1 and
+ Context2. Context1 and Context2 are optional and may be NULL. The function
+ EntryPoint must never return.
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit protected mode with flat descriptors. This
+ means all descriptors must have a base of 0 and a limit of 4GB.
+ 3) CR0 and CR4 must be compatible with 32-bit protected mode with flat
+ descriptors.
+ 4) CR3 must point to valid page tables that will be used once the transition
+ is complete, and those page tables must guarantee that the pages for this
+ function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is enabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is enabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is enabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+InternalX86EnablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ );
+
+/**
+ Disables the 32-bit paging mode on the CPU.
+
+ Disables the 32-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 32-paged protected
+ mode. This function is only available on IA-32. After the 32-bit paging mode
+ is disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be NULL. The function EntryPoint must never return.
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit paged mode.
+ 3) CR0, CR3, and CR4 must be compatible with 32-bit paged mode.
+ 4) CR3 must point to valid page tables that guarantee that the pages for
+ this function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is disabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is disabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is
+ disabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+InternalX86DisablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ );
+
+/**
+ Enables the 64-bit paging mode on the CPU.
+
+ Enables the 64-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode with flat
+ descriptors. This function is only available on IA-32. After the 64-bit
+ paging mode is enabled, control is transferred to the function specified by
+ EntryPoint using the new stack specified by NewStack and passing in the
+ parameters specified by Context1 and Context2. Context1 and Context2 are
+ optional and may be 0. The function EntryPoint must never return.
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for long mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is enabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is enabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is enabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+InternalX86EnablePaging64 (
+ IN UINT16 Cs,
+ IN UINT64 EntryPoint,
+ IN UINT64 Context1, OPTIONAL
+ IN UINT64 Context2, OPTIONAL
+ IN UINT64 NewStack
+ );
+
+/**
+ Disables the 64-bit paging mode on the CPU.
+
+ Disables the 64-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 64-paging mode.
+ This function is only available on x64. After the 64-bit paging mode is
+ disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be 0. The function EntryPoint must never return.
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for 32-bit protected mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is disabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is disabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is disabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+InternalX86DisablePaging64 (
+ IN UINT16 Cs,
+ IN UINT32 EntryPoint,
+ IN UINT32 Context1, OPTIONAL
+ IN UINT32 Context2, OPTIONAL
+ IN UINT32 NewStack
+ );
+
+/**
+ Generates a 16-bit random number through RDRAND instruction.
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+ **/
+BOOLEAN
+EFIAPI
+InternalX86RdRand16 (
+ OUT UINT16 *Rand
+ );
+
+/**
+ Generates a 32-bit random number through RDRAND instruction.
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+**/
+BOOLEAN
+EFIAPI
+InternalX86RdRand32 (
+ OUT UINT32 *Rand
+ );
+
+/**
+ Generates a 64-bit random number through RDRAND instruction.
+
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+**/
+BOOLEAN
+EFIAPI
+InternalX86RdRand64 (
+ OUT UINT64 *Rand
+ );
+
+#else
+
+#endif
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/BitField.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/BitField.c
new file mode 100644
index 0000000..0f48a03
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/BitField.c
@@ -0,0 +1,1002 @@
+/** @file
+ Bit field functions of BaseLib.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Worker function that returns a bit field from Operand.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+
+ @return The bit field read.
+
+**/
+UINTN
+EFIAPI
+InternalBaseLibBitFieldReadUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ //
+ // ~((UINTN)-2 << EndBit) is a mask in which bit[0] thru bit[EndBit]
+ // are 1's while bit[EndBit + 1] thru the most significant bit are 0's.
+ //
+ return (Operand & ~((UINTN)-2 << EndBit)) >> StartBit;
+}
+
+/**
+ Worker function that reads a bit field from Operand, performs a bitwise OR,
+ and returns the result.
+
+ Performs a bitwise OR between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new value is returned.
+
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ @param OrData The value to OR with the read value from the value.
+
+ @return The new value.
+
+**/
+UINTN
+EFIAPI
+InternalBaseLibBitFieldOrUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINTN OrData
+ )
+{
+ //
+ // Higher bits in OrData those are not used must be zero.
+ //
+ // EndBit - StartBit + 1 might be 32 while the result right shifting 32 on a 32bit integer is undefined,
+ // So the logic is updated to right shift (EndBit - StartBit) bits and compare the last bit directly.
+ //
+ ASSERT ((OrData >> (EndBit - StartBit)) == ((OrData >> (EndBit - StartBit)) & 1));
+
+ //
+ // ~((UINTN)-2 << EndBit) is a mask in which bit[0] thru bit[EndBit]
+ // are 1's while bit[EndBit + 1] thru the most significant bit are 0's.
+ //
+ return Operand | ((OrData << StartBit) & ~((UINTN) -2 << EndBit));
+}
+
+/**
+ Worker function that reads a bit field from Operand, performs a bitwise AND,
+ and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new value is returned.
+
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ @param AndData The value to And with the read value from the value.
+
+ @return The new value.
+
+**/
+UINTN
+EFIAPI
+InternalBaseLibBitFieldAndUint (
+ IN UINTN Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINTN AndData
+ )
+{
+ //
+ // Higher bits in AndData those are not used must be zero.
+ //
+ // EndBit - StartBit + 1 might be 32 while the result right shifting 32 on a 32bit integer is undefined,
+ // So the logic is updated to right shift (EndBit - StartBit) bits and compare the last bit directly.
+ //
+ ASSERT ((AndData >> (EndBit - StartBit)) == ((AndData >> (EndBit - StartBit)) & 1));
+
+ //
+ // ~((UINTN)-2 << EndBit) is a mask in which bit[0] thru bit[EndBit]
+ // are 1's while bit[EndBit + 1] thru the most significant bit are 0's.
+ //
+ return Operand & ~((~AndData << StartBit) & ~((UINTN)-2 << EndBit));
+}
+
+/**
+ Returns a bit field from an 8-bit value.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ If 8-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 7, then ASSERT().
+ If EndBit is greater than 7, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..7.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..7.
+
+ @return The bit field read.
+
+**/
+UINT8
+EFIAPI
+BitFieldRead8 (
+ IN UINT8 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ ASSERT (EndBit < 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT8)InternalBaseLibBitFieldReadUint (Operand, StartBit, EndBit);
+}
+
+/**
+ Writes a bit field to an 8-bit value, and returns the result.
+
+ Writes Value to the bit field specified by the StartBit and the EndBit in
+ Operand. All other bits in Operand are preserved. The new 8-bit value is
+ returned.
+
+ If 8-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 7, then ASSERT().
+ If EndBit is greater than 7, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..7.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..7.
+ @param Value The new value of the bit field.
+
+ @return The new 8-bit value.
+
+**/
+UINT8
+EFIAPI
+BitFieldWrite8 (
+ IN UINT8 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT8 Value
+ )
+{
+ ASSERT (EndBit < 8);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldAndThenOr8 (Operand, StartBit, EndBit, 0, Value);
+}
+
+/**
+ Reads a bit field from an 8-bit value, performs a bitwise OR, and returns the
+ result.
+
+ Performs a bitwise OR between the bit field specified by StartBit
+ and EndBit in Operand and the value specified by OrData. All other bits in
+ Operand are preserved. The new 8-bit value is returned.
+
+ If 8-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 7, then ASSERT().
+ If EndBit is greater than 7, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..7.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..7.
+ @param OrData The value to OR with the read value from the value.
+
+ @return The new 8-bit value.
+
+**/
+UINT8
+EFIAPI
+BitFieldOr8 (
+ IN UINT8 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT8 OrData
+ )
+{
+ ASSERT (EndBit < 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT8)InternalBaseLibBitFieldOrUint (Operand, StartBit, EndBit, OrData);
+}
+
+/**
+ Reads a bit field from an 8-bit value, performs a bitwise AND, and returns
+ the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new 8-bit value is returned.
+
+ If 8-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 7, then ASSERT().
+ If EndBit is greater than 7, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..7.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..7.
+ @param AndData The value to AND with the read value from the value.
+
+ @return The new 8-bit value.
+
+**/
+UINT8
+EFIAPI
+BitFieldAnd8 (
+ IN UINT8 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT8 AndData
+ )
+{
+ ASSERT (EndBit < 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT8)InternalBaseLibBitFieldAndUint (Operand, StartBit, EndBit, AndData);
+}
+
+/**
+ Reads a bit field from an 8-bit value, performs a bitwise AND followed by a
+ bitwise OR, and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData, followed by a bitwise
+ OR with value specified by OrData. All other bits in Operand are
+ preserved. The new 8-bit value is returned.
+
+ If 8-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 7, then ASSERT().
+ If EndBit is greater than 7, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..7.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..7.
+ @param AndData The value to AND with the read value from the value.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The new 8-bit value.
+
+**/
+UINT8
+EFIAPI
+BitFieldAndThenOr8 (
+ IN UINT8 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT8 AndData,
+ IN UINT8 OrData
+ )
+{
+ ASSERT (EndBit < 8);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldOr8 (
+ BitFieldAnd8 (Operand, StartBit, EndBit, AndData),
+ StartBit,
+ EndBit,
+ OrData
+ );
+}
+
+/**
+ Returns a bit field from a 16-bit value.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ If 16-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 15, then ASSERT().
+ If EndBit is greater than 15, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..15.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..15.
+
+ @return The bit field read.
+
+**/
+UINT16
+EFIAPI
+BitFieldRead16 (
+ IN UINT16 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ ASSERT (EndBit < 16);
+ ASSERT (StartBit <= EndBit);
+ return (UINT16)InternalBaseLibBitFieldReadUint (Operand, StartBit, EndBit);
+}
+
+/**
+ Writes a bit field to a 16-bit value, and returns the result.
+
+ Writes Value to the bit field specified by the StartBit and the EndBit in
+ Operand. All other bits in Operand are preserved. The new 16-bit value is
+ returned.
+
+ If 16-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 15, then ASSERT().
+ If EndBit is greater than 15, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..15.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..15.
+ @param Value The new value of the bit field.
+
+ @return The new 16-bit value.
+
+**/
+UINT16
+EFIAPI
+BitFieldWrite16 (
+ IN UINT16 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT16 Value
+ )
+{
+ ASSERT (EndBit < 16);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldAndThenOr16 (Operand, StartBit, EndBit, 0, Value);
+}
+
+/**
+ Reads a bit field from a 16-bit value, performs a bitwise OR, and returns the
+ result.
+
+ Performs a bitwise OR between the bit field specified by StartBit
+ and EndBit in Operand and the value specified by OrData. All other bits in
+ Operand are preserved. The new 16-bit value is returned.
+
+ If 16-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 15, then ASSERT().
+ If EndBit is greater than 15, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..15.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..15.
+ @param OrData The value to OR with the read value from the value.
+
+ @return The new 16-bit value.
+
+**/
+UINT16
+EFIAPI
+BitFieldOr16 (
+ IN UINT16 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT16 OrData
+ )
+{
+ ASSERT (EndBit < 16);
+ ASSERT (StartBit <= EndBit);
+ return (UINT16)InternalBaseLibBitFieldOrUint (Operand, StartBit, EndBit, OrData);
+}
+
+/**
+ Reads a bit field from a 16-bit value, performs a bitwise AND, and returns
+ the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new 16-bit value is returned.
+
+ If 16-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 15, then ASSERT().
+ If EndBit is greater than 15, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..15.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..15.
+ @param AndData The value to AND with the read value from the value.
+
+ @return The new 16-bit value.
+
+**/
+UINT16
+EFIAPI
+BitFieldAnd16 (
+ IN UINT16 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT16 AndData
+ )
+{
+ ASSERT (EndBit < 16);
+ ASSERT (StartBit <= EndBit);
+ return (UINT16)InternalBaseLibBitFieldAndUint (Operand, StartBit, EndBit, AndData);
+}
+
+/**
+ Reads a bit field from a 16-bit value, performs a bitwise AND followed by a
+ bitwise OR, and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData, followed by a bitwise
+ OR with value specified by OrData. All other bits in Operand are
+ preserved. The new 16-bit value is returned.
+
+ If 16-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 15, then ASSERT().
+ If EndBit is greater than 15, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..15.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..15.
+ @param AndData The value to AND with the read value from the value.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The new 16-bit value.
+
+**/
+UINT16
+EFIAPI
+BitFieldAndThenOr16 (
+ IN UINT16 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT16 AndData,
+ IN UINT16 OrData
+ )
+{
+ ASSERT (EndBit < 16);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldOr16 (
+ BitFieldAnd16 (Operand, StartBit, EndBit, AndData),
+ StartBit,
+ EndBit,
+ OrData
+ );
+}
+
+/**
+ Returns a bit field from a 32-bit value.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ If 32-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+
+ @return The bit field read.
+
+**/
+UINT32
+EFIAPI
+BitFieldRead32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)InternalBaseLibBitFieldReadUint (Operand, StartBit, EndBit);
+}
+
+/**
+ Writes a bit field to a 32-bit value, and returns the result.
+
+ Writes Value to the bit field specified by the StartBit and the EndBit in
+ Operand. All other bits in Operand are preserved. The new 32-bit value is
+ returned.
+
+ If 32-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param Value The new value of the bit field.
+
+ @return The new 32-bit value.
+
+**/
+UINT32
+EFIAPI
+BitFieldWrite32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 Value
+ )
+{
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldAndThenOr32 (Operand, StartBit, EndBit, 0, Value);
+}
+
+/**
+ Reads a bit field from a 32-bit value, performs a bitwise OR, and returns the
+ result.
+
+ Performs a bitwise OR between the bit field specified by StartBit
+ and EndBit in Operand and the value specified by OrData. All other bits in
+ Operand are preserved. The new 32-bit value is returned.
+
+ If 32-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param OrData The value to OR with the read value from the value.
+
+ @return The new 32-bit value.
+
+**/
+UINT32
+EFIAPI
+BitFieldOr32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 OrData
+ )
+{
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)InternalBaseLibBitFieldOrUint (Operand, StartBit, EndBit, OrData);
+}
+
+/**
+ Reads a bit field from a 32-bit value, performs a bitwise AND, and returns
+ the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new 32-bit value is returned.
+
+ If 32-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param AndData The value to AND with the read value from the value.
+
+ @return The new 32-bit value.
+
+**/
+UINT32
+EFIAPI
+BitFieldAnd32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 AndData
+ )
+{
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)InternalBaseLibBitFieldAndUint (Operand, StartBit, EndBit, AndData);
+}
+
+/**
+ Reads a bit field from a 32-bit value, performs a bitwise AND followed by a
+ bitwise OR, and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData, followed by a bitwise
+ OR with value specified by OrData. All other bits in Operand are
+ preserved. The new 32-bit value is returned.
+
+ If 32-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param AndData The value to AND with the read value from the value.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The new 32-bit value.
+
+**/
+UINT32
+EFIAPI
+BitFieldAndThenOr32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 AndData,
+ IN UINT32 OrData
+ )
+{
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldOr32 (
+ BitFieldAnd32 (Operand, StartBit, EndBit, AndData),
+ StartBit,
+ EndBit,
+ OrData
+ );
+}
+
+/**
+ Returns a bit field from a 64-bit value.
+
+ Returns the bitfield specified by the StartBit and the EndBit from Operand.
+
+ If 64-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+
+ @return The bit field read.
+
+**/
+UINT64
+EFIAPI
+BitFieldRead64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+ return RShiftU64 (Operand & ~LShiftU64 ((UINT64)-2, EndBit), StartBit);
+}
+
+/**
+ Writes a bit field to a 64-bit value, and returns the result.
+
+ Writes Value to the bit field specified by the StartBit and the EndBit in
+ Operand. All other bits in Operand are preserved. The new 64-bit value is
+ returned.
+
+ If 64-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param Value The new value of the bit field.
+
+ @return The new 64-bit value.
+
+**/
+UINT64
+EFIAPI
+BitFieldWrite64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 Value
+ )
+{
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldAndThenOr64 (Operand, StartBit, EndBit, 0, Value);
+}
+
+/**
+ Reads a bit field from a 64-bit value, performs a bitwise OR, and returns the
+ result.
+
+ Performs a bitwise OR between the bit field specified by StartBit
+ and EndBit in Operand and the value specified by OrData. All other bits in
+ Operand are preserved. The new 64-bit value is returned.
+
+ If 64-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param OrData The value to OR with the read value from the value
+
+ @return The new 64-bit value.
+
+**/
+UINT64
+EFIAPI
+BitFieldOr64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 OrData
+ )
+{
+ UINT64 Value1;
+ UINT64 Value2;
+
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+ //
+ // Higher bits in OrData those are not used must be zero.
+ //
+ // EndBit - StartBit + 1 might be 64 while the result right shifting 64 on RShiftU64() API is invalid,
+ // So the logic is updated to right shift (EndBit - StartBit) bits and compare the last bit directly.
+ //
+ ASSERT (RShiftU64 (OrData, EndBit - StartBit) == (RShiftU64 (OrData, EndBit - StartBit) & 1));
+
+ Value1 = LShiftU64 (OrData, StartBit);
+ Value2 = LShiftU64 ((UINT64) - 2, EndBit);
+
+ return Operand | (Value1 & ~Value2);
+}
+
+/**
+ Reads a bit field from a 64-bit value, performs a bitwise AND, and returns
+ the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData. All other bits in Operand are
+ preserved. The new 64-bit value is returned.
+
+ If 64-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param AndData The value to AND with the read value from the value.
+
+ @return The new 64-bit value.
+
+**/
+UINT64
+EFIAPI
+BitFieldAnd64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 AndData
+ )
+{
+ UINT64 Value1;
+ UINT64 Value2;
+
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+ //
+ // Higher bits in AndData those are not used must be zero.
+ //
+ // EndBit - StartBit + 1 might be 64 while the right shifting 64 on RShiftU64() API is invalid,
+ // So the logic is updated to right shift (EndBit - StartBit) bits and compare the last bit directly.
+ //
+ ASSERT (RShiftU64 (AndData, EndBit - StartBit) == (RShiftU64 (AndData, EndBit - StartBit) & 1));
+
+ Value1 = LShiftU64 (~AndData, StartBit);
+ Value2 = LShiftU64 ((UINT64)-2, EndBit);
+
+ return Operand & ~(Value1 & ~Value2);
+}
+
+/**
+ Reads a bit field from a 64-bit value, performs a bitwise AND followed by a
+ bitwise OR, and returns the result.
+
+ Performs a bitwise AND between the bit field specified by StartBit and EndBit
+ in Operand and the value specified by AndData, followed by a bitwise
+ OR with value specified by OrData. All other bits in Operand are
+ preserved. The new 64-bit value is returned.
+
+ If 64-bit operations are not supported, then ASSERT().
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param AndData The value to AND with the read value from the value.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The new 64-bit value.
+
+**/
+UINT64
+EFIAPI
+BitFieldAndThenOr64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 AndData,
+ IN UINT64 OrData
+ )
+{
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+ return BitFieldOr64 (
+ BitFieldAnd64 (Operand, StartBit, EndBit, AndData),
+ StartBit,
+ EndBit,
+ OrData
+ );
+}
+
+/**
+ Reads a bit field from a 32-bit value, counts and returns
+ the number of set bits.
+
+ Counts the number of set bits in the bit field specified by
+ StartBit and EndBit in Operand. The count is returned.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+
+ @return The number of bits set between StartBit and EndBit.
+
+**/
+UINT8
+EFIAPI
+BitFieldCountOnes32 (
+ IN UINT32 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ UINT32 Count;
+
+ ASSERT (EndBit < 32);
+ ASSERT (StartBit <= EndBit);
+
+ Count = BitFieldRead32 (Operand, StartBit, EndBit);
+ Count -= ((Count >> 1) & 0x55555555);
+ Count = (Count & 0x33333333) + ((Count >> 2) & 0x33333333);
+ Count += Count >> 4;
+ Count &= 0x0F0F0F0F;
+ Count += Count >> 8;
+ Count += Count >> 16;
+
+ return (UINT8) Count & 0x3F;
+}
+
+/**
+ Reads a bit field from a 64-bit value, counts and returns
+ the number of set bits.
+
+ Counts the number of set bits in the bit field specified by
+ StartBit and EndBit in Operand. The count is returned.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Operand Operand on which to perform the bitfield operation.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+
+ @return The number of bits set between StartBit and EndBit.
+
+**/
+UINT8
+EFIAPI
+BitFieldCountOnes64 (
+ IN UINT64 Operand,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ UINT64 BitField;
+ UINT8 Count;
+
+ ASSERT (EndBit < 64);
+ ASSERT (StartBit <= EndBit);
+
+ BitField = BitFieldRead64 (Operand, StartBit, EndBit);
+ Count = BitFieldCountOnes32 ((UINT32) BitField, 0, 31);
+ Count += BitFieldCountOnes32 ((UINT32) RShiftU64(BitField, 32), 0, 31);
+
+ return Count;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/CheckSum.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/CheckSum.c
new file mode 100644
index 0000000..d91a7a0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/CheckSum.c
@@ -0,0 +1,626 @@
+/** @file
+ Utility functions to generate checksum based on 2's complement
+ algorithm.
+
+ Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the sum of all elements in a buffer in unit of UINT8.
+ During calculation, the carry bits are dropped.
+
+ This function calculates the sum of all elements in a buffer
+ in unit of UINT8. The carry bits in result of addition are dropped.
+ The result is returned as UINT8. If Length is Zero, then Zero is
+ returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the sum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Sum The sum of Buffer with carry bits dropped during additions.
+
+**/
+UINT8
+EFIAPI
+CalculateSum8 (
+ IN CONST UINT8 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT8 Sum;
+ UINTN Count;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (Length <= (MAX_ADDRESS - ((UINTN) Buffer) + 1));
+
+ for (Sum = 0, Count = 0; Count < Length; Count++) {
+ Sum = (UINT8) (Sum + *(Buffer + Count));
+ }
+
+ return Sum;
+}
+
+
+/**
+ Returns the two's complement checksum of all elements in a buffer
+ of 8-bit values.
+
+ This function first calculates the sum of the 8-bit values in the
+ buffer specified by Buffer and Length. The carry bits in the result
+ of addition are dropped. Then, the two's complement of the sum is
+ returned. If Length is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the checksum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Checksum The 2's complement checksum of Buffer.
+
+**/
+UINT8
+EFIAPI
+CalculateCheckSum8 (
+ IN CONST UINT8 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT8 CheckSum;
+
+ CheckSum = CalculateSum8 (Buffer, Length);
+
+ //
+ // Return the checksum based on 2's complement.
+ //
+ return (UINT8) (0x100 - CheckSum);
+}
+
+/**
+ Returns the sum of all elements in a buffer of 16-bit values. During
+ calculation, the carry bits are dropped.
+
+ This function calculates the sum of the 16-bit values in the buffer
+ specified by Buffer and Length. The carry bits in result of addition are dropped.
+ The 16-bit result is returned. If Length is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the sum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Sum The sum of Buffer with carry bits dropped during additions.
+
+**/
+UINT16
+EFIAPI
+CalculateSum16 (
+ IN CONST UINT16 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT16 Sum;
+ UINTN Count;
+ UINTN Total;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN) Buffer & 0x1) == 0);
+ ASSERT ((Length & 0x1) == 0);
+ ASSERT (Length <= (MAX_ADDRESS - ((UINTN) Buffer) + 1));
+
+ Total = Length / sizeof (*Buffer);
+ for (Sum = 0, Count = 0; Count < Total; Count++) {
+ Sum = (UINT16) (Sum + *(Buffer + Count));
+ }
+
+ return Sum;
+}
+
+
+/**
+ Returns the two's complement checksum of all elements in a buffer of
+ 16-bit values.
+
+ This function first calculates the sum of the 16-bit values in the buffer
+ specified by Buffer and Length. The carry bits in the result of addition
+ are dropped. Then, the two's complement of the sum is returned. If Length
+ is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the checksum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Checksum The 2's complement checksum of Buffer.
+
+**/
+UINT16
+EFIAPI
+CalculateCheckSum16 (
+ IN CONST UINT16 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT16 CheckSum;
+
+ CheckSum = CalculateSum16 (Buffer, Length);
+
+ //
+ // Return the checksum based on 2's complement.
+ //
+ return (UINT16) (0x10000 - CheckSum);
+}
+
+
+/**
+ Returns the sum of all elements in a buffer of 32-bit values. During
+ calculation, the carry bits are dropped.
+
+ This function calculates the sum of the 32-bit values in the buffer
+ specified by Buffer and Length. The carry bits in result of addition are dropped.
+ The 32-bit result is returned. If Length is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the sum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Sum The sum of Buffer with carry bits dropped during additions.
+
+**/
+UINT32
+EFIAPI
+CalculateSum32 (
+ IN CONST UINT32 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT32 Sum;
+ UINTN Count;
+ UINTN Total;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN) Buffer & 0x3) == 0);
+ ASSERT ((Length & 0x3) == 0);
+ ASSERT (Length <= (MAX_ADDRESS - ((UINTN) Buffer) + 1));
+
+ Total = Length / sizeof (*Buffer);
+ for (Sum = 0, Count = 0; Count < Total; Count++) {
+ Sum = Sum + *(Buffer + Count);
+ }
+
+ return Sum;
+}
+
+
+/**
+ Returns the two's complement checksum of all elements in a buffer of
+ 32-bit values.
+
+ This function first calculates the sum of the 32-bit values in the buffer
+ specified by Buffer and Length. The carry bits in the result of addition
+ are dropped. Then, the two's complement of the sum is returned. If Length
+ is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the checksum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Checksum The 2's complement checksum of Buffer.
+
+**/
+UINT32
+EFIAPI
+CalculateCheckSum32 (
+ IN CONST UINT32 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT32 CheckSum;
+
+ CheckSum = CalculateSum32 (Buffer, Length);
+
+ //
+ // Return the checksum based on 2's complement.
+ //
+ return (UINT32) ((UINT32)(-1) - CheckSum + 1);
+}
+
+
+/**
+ Returns the sum of all elements in a buffer of 64-bit values. During
+ calculation, the carry bits are dropped.
+
+ This function calculates the sum of the 64-bit values in the buffer
+ specified by Buffer and Length. The carry bits in result of addition are dropped.
+ The 64-bit result is returned. If Length is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the sum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Sum The sum of Buffer with carry bits dropped during additions.
+
+**/
+UINT64
+EFIAPI
+CalculateSum64 (
+ IN CONST UINT64 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT64 Sum;
+ UINTN Count;
+ UINTN Total;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN) Buffer & 0x7) == 0);
+ ASSERT ((Length & 0x7) == 0);
+ ASSERT (Length <= (MAX_ADDRESS - ((UINTN) Buffer) + 1));
+
+ Total = Length / sizeof (*Buffer);
+ for (Sum = 0, Count = 0; Count < Total; Count++) {
+ Sum = Sum + *(Buffer + Count);
+ }
+
+ return Sum;
+}
+
+
+/**
+ Returns the two's complement checksum of all elements in a buffer of
+ 64-bit values.
+
+ This function first calculates the sum of the 64-bit values in the buffer
+ specified by Buffer and Length. The carry bits in the result of addition
+ are dropped. Then, the two's complement of the sum is returned. If Length
+ is 0, then 0 is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to carry out the checksum operation.
+ @param Length The size, in bytes, of Buffer.
+
+ @return Checksum The 2's complement checksum of Buffer.
+
+**/
+UINT64
+EFIAPI
+CalculateCheckSum64 (
+ IN CONST UINT64 *Buffer,
+ IN UINTN Length
+ )
+{
+ UINT64 CheckSum;
+
+ CheckSum = CalculateSum64 (Buffer, Length);
+
+ //
+ // Return the checksum based on 2's complement.
+ //
+ return (UINT64) ((UINT64)(-1) - CheckSum + 1);
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED CONST UINT32 mCrcTable[256] = {
+ 0x00000000,
+ 0x77073096,
+ 0xEE0E612C,
+ 0x990951BA,
+ 0x076DC419,
+ 0x706AF48F,
+ 0xE963A535,
+ 0x9E6495A3,
+ 0x0EDB8832,
+ 0x79DCB8A4,
+ 0xE0D5E91E,
+ 0x97D2D988,
+ 0x09B64C2B,
+ 0x7EB17CBD,
+ 0xE7B82D07,
+ 0x90BF1D91,
+ 0x1DB71064,
+ 0x6AB020F2,
+ 0xF3B97148,
+ 0x84BE41DE,
+ 0x1ADAD47D,
+ 0x6DDDE4EB,
+ 0xF4D4B551,
+ 0x83D385C7,
+ 0x136C9856,
+ 0x646BA8C0,
+ 0xFD62F97A,
+ 0x8A65C9EC,
+ 0x14015C4F,
+ 0x63066CD9,
+ 0xFA0F3D63,
+ 0x8D080DF5,
+ 0x3B6E20C8,
+ 0x4C69105E,
+ 0xD56041E4,
+ 0xA2677172,
+ 0x3C03E4D1,
+ 0x4B04D447,
+ 0xD20D85FD,
+ 0xA50AB56B,
+ 0x35B5A8FA,
+ 0x42B2986C,
+ 0xDBBBC9D6,
+ 0xACBCF940,
+ 0x32D86CE3,
+ 0x45DF5C75,
+ 0xDCD60DCF,
+ 0xABD13D59,
+ 0x26D930AC,
+ 0x51DE003A,
+ 0xC8D75180,
+ 0xBFD06116,
+ 0x21B4F4B5,
+ 0x56B3C423,
+ 0xCFBA9599,
+ 0xB8BDA50F,
+ 0x2802B89E,
+ 0x5F058808,
+ 0xC60CD9B2,
+ 0xB10BE924,
+ 0x2F6F7C87,
+ 0x58684C11,
+ 0xC1611DAB,
+ 0xB6662D3D,
+ 0x76DC4190,
+ 0x01DB7106,
+ 0x98D220BC,
+ 0xEFD5102A,
+ 0x71B18589,
+ 0x06B6B51F,
+ 0x9FBFE4A5,
+ 0xE8B8D433,
+ 0x7807C9A2,
+ 0x0F00F934,
+ 0x9609A88E,
+ 0xE10E9818,
+ 0x7F6A0DBB,
+ 0x086D3D2D,
+ 0x91646C97,
+ 0xE6635C01,
+ 0x6B6B51F4,
+ 0x1C6C6162,
+ 0x856530D8,
+ 0xF262004E,
+ 0x6C0695ED,
+ 0x1B01A57B,
+ 0x8208F4C1,
+ 0xF50FC457,
+ 0x65B0D9C6,
+ 0x12B7E950,
+ 0x8BBEB8EA,
+ 0xFCB9887C,
+ 0x62DD1DDF,
+ 0x15DA2D49,
+ 0x8CD37CF3,
+ 0xFBD44C65,
+ 0x4DB26158,
+ 0x3AB551CE,
+ 0xA3BC0074,
+ 0xD4BB30E2,
+ 0x4ADFA541,
+ 0x3DD895D7,
+ 0xA4D1C46D,
+ 0xD3D6F4FB,
+ 0x4369E96A,
+ 0x346ED9FC,
+ 0xAD678846,
+ 0xDA60B8D0,
+ 0x44042D73,
+ 0x33031DE5,
+ 0xAA0A4C5F,
+ 0xDD0D7CC9,
+ 0x5005713C,
+ 0x270241AA,
+ 0xBE0B1010,
+ 0xC90C2086,
+ 0x5768B525,
+ 0x206F85B3,
+ 0xB966D409,
+ 0xCE61E49F,
+ 0x5EDEF90E,
+ 0x29D9C998,
+ 0xB0D09822,
+ 0xC7D7A8B4,
+ 0x59B33D17,
+ 0x2EB40D81,
+ 0xB7BD5C3B,
+ 0xC0BA6CAD,
+ 0xEDB88320,
+ 0x9ABFB3B6,
+ 0x03B6E20C,
+ 0x74B1D29A,
+ 0xEAD54739,
+ 0x9DD277AF,
+ 0x04DB2615,
+ 0x73DC1683,
+ 0xE3630B12,
+ 0x94643B84,
+ 0x0D6D6A3E,
+ 0x7A6A5AA8,
+ 0xE40ECF0B,
+ 0x9309FF9D,
+ 0x0A00AE27,
+ 0x7D079EB1,
+ 0xF00F9344,
+ 0x8708A3D2,
+ 0x1E01F268,
+ 0x6906C2FE,
+ 0xF762575D,
+ 0x806567CB,
+ 0x196C3671,
+ 0x6E6B06E7,
+ 0xFED41B76,
+ 0x89D32BE0,
+ 0x10DA7A5A,
+ 0x67DD4ACC,
+ 0xF9B9DF6F,
+ 0x8EBEEFF9,
+ 0x17B7BE43,
+ 0x60B08ED5,
+ 0xD6D6A3E8,
+ 0xA1D1937E,
+ 0x38D8C2C4,
+ 0x4FDFF252,
+ 0xD1BB67F1,
+ 0xA6BC5767,
+ 0x3FB506DD,
+ 0x48B2364B,
+ 0xD80D2BDA,
+ 0xAF0A1B4C,
+ 0x36034AF6,
+ 0x41047A60,
+ 0xDF60EFC3,
+ 0xA867DF55,
+ 0x316E8EEF,
+ 0x4669BE79,
+ 0xCB61B38C,
+ 0xBC66831A,
+ 0x256FD2A0,
+ 0x5268E236,
+ 0xCC0C7795,
+ 0xBB0B4703,
+ 0x220216B9,
+ 0x5505262F,
+ 0xC5BA3BBE,
+ 0xB2BD0B28,
+ 0x2BB45A92,
+ 0x5CB36A04,
+ 0xC2D7FFA7,
+ 0xB5D0CF31,
+ 0x2CD99E8B,
+ 0x5BDEAE1D,
+ 0x9B64C2B0,
+ 0xEC63F226,
+ 0x756AA39C,
+ 0x026D930A,
+ 0x9C0906A9,
+ 0xEB0E363F,
+ 0x72076785,
+ 0x05005713,
+ 0x95BF4A82,
+ 0xE2B87A14,
+ 0x7BB12BAE,
+ 0x0CB61B38,
+ 0x92D28E9B,
+ 0xE5D5BE0D,
+ 0x7CDCEFB7,
+ 0x0BDBDF21,
+ 0x86D3D2D4,
+ 0xF1D4E242,
+ 0x68DDB3F8,
+ 0x1FDA836E,
+ 0x81BE16CD,
+ 0xF6B9265B,
+ 0x6FB077E1,
+ 0x18B74777,
+ 0x88085AE6,
+ 0xFF0F6A70,
+ 0x66063BCA,
+ 0x11010B5C,
+ 0x8F659EFF,
+ 0xF862AE69,
+ 0x616BFFD3,
+ 0x166CCF45,
+ 0xA00AE278,
+ 0xD70DD2EE,
+ 0x4E048354,
+ 0x3903B3C2,
+ 0xA7672661,
+ 0xD06016F7,
+ 0x4969474D,
+ 0x3E6E77DB,
+ 0xAED16A4A,
+ 0xD9D65ADC,
+ 0x40DF0B66,
+ 0x37D83BF0,
+ 0xA9BCAE53,
+ 0xDEBB9EC5,
+ 0x47B2CF7F,
+ 0x30B5FFE9,
+ 0xBDBDF21C,
+ 0xCABAC28A,
+ 0x53B39330,
+ 0x24B4A3A6,
+ 0xBAD03605,
+ 0xCDD70693,
+ 0x54DE5729,
+ 0x23D967BF,
+ 0xB3667A2E,
+ 0xC4614AB8,
+ 0x5D681B02,
+ 0x2A6F2B94,
+ 0xB40BBE37,
+ 0xC30C8EA1,
+ 0x5A05DF1B,
+ 0x2D02EF8D
+};
+
+/**
+ Computes and returns a 32-bit CRC for a data buffer.
+ CRC32 value bases on ITU-T V.42.
+
+ If Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param[in] Buffer A pointer to the buffer on which the 32-bit CRC is to be computed.
+ @param[in] Length The number of bytes in the buffer Data.
+
+ @retval Crc32 The 32-bit CRC was computed for the data buffer.
+
+**/
+UINT32
+EFIAPI
+CalculateCrc32(
+ IN VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ UINTN Index;
+ UINT32 Crc;
+ UINT8 *Ptr;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (Length <= (MAX_ADDRESS - ((UINTN) Buffer) + 1));
+
+ //
+ // Compute CRC
+ //
+ Crc = 0xffffffff;
+ for (Index = 0, Ptr = Buffer; Index < Length; Index++, Ptr++) {
+ Crc = (Crc >> 8) ^ mCrcTable[(UINT8) Crc ^ *Ptr];
+ }
+
+ return Crc ^ 0xffffffff;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/ChkStkGcc.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ChkStkGcc.c
new file mode 100644
index 0000000..7f07ba2
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ChkStkGcc.c
@@ -0,0 +1,18 @@
+/** @file
+ Provides hack function for passng GCC build.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Hack function for passing GCC build.
+**/
+VOID
+__chkstk()
+{
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/Cpu.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Cpu.c
new file mode 100644
index 0000000..689246f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Cpu.c
@@ -0,0 +1,59 @@
+/** @file
+ Base Library CPU Functions for all architectures.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+
+/**
+ Disables CPU interrupts and returns the interrupt state prior to the disable
+ operation.
+
+ @retval TRUE CPU interrupts were enabled on entry to this call.
+ @retval FALSE CPU interrupts were disabled on entry to this call.
+
+**/
+BOOLEAN
+EFIAPI
+SaveAndDisableInterrupts (
+ VOID
+ )
+{
+ BOOLEAN InterruptState;
+
+ InterruptState = GetInterruptState ();
+ DisableInterrupts ();
+ return InterruptState;
+}
+
+/**
+ Set the current CPU interrupt state.
+
+ Sets the current CPU interrupt state to the state specified by
+ InterruptState. If InterruptState is TRUE, then interrupts are enabled. If
+ InterruptState is FALSE, then interrupts are disabled. InterruptState is
+ returned.
+
+ @param InterruptState TRUE if interrupts should be enabled. FALSE if
+ interrupts should be disabled.
+
+ @return InterruptState
+
+**/
+BOOLEAN
+EFIAPI
+SetInterruptState (
+ IN BOOLEAN InterruptState
+ )
+{
+ if (InterruptState) {
+ EnableInterrupts ();
+ } else {
+ DisableInterrupts ();
+ }
+ return InterruptState;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/CpuDeadLoop.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/CpuDeadLoop.c
new file mode 100644
index 0000000..3cd3043
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/CpuDeadLoop.c
@@ -0,0 +1,34 @@
+/** @file
+ Base Library CPU Functions for all architectures.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+#include <Base.h>
+#include <Library/BaseLib.h>
+
+/**
+ Executes an infinite loop.
+
+ Forces the CPU to execute an infinite loop. A debugger may be used to skip
+ past the loop and the code that follows the loop must execute properly. This
+ implies that the infinite loop must not cause the code that follow it to be
+ optimized away.
+
+**/
+VOID
+EFIAPI
+CpuDeadLoop (
+ VOID
+ )
+{
+ volatile UINTN Index;
+
+ for (Index = 0; Index == 0;) {
+ CpuPause();
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivS64x64Remainder.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivS64x64Remainder.c
new file mode 100644
index 0000000..bdf25b8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivS64x64Remainder.c
@@ -0,0 +1,47 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Divides a 64-bit signed integer by a 64-bit signed integer and generates a
+ 64-bit signed result and a optional 64-bit signed remainder.
+
+ This function divides the 64-bit signed value Dividend by the 64-bit signed
+ value Divisor and generates a 64-bit signed quotient. If Remainder is not
+ NULL, then the 64-bit signed remainder is returned in Remainder. This
+ function returns the 64-bit signed quotient.
+
+ It is the caller's responsibility to not call this function with a Divisor of 0.
+ If Divisor is 0, then the quotient and remainder should be assumed to be
+ the largest negative integer.
+
+ If Divisor is 0, then ASSERT().
+
+ @param Dividend A 64-bit signed value.
+ @param Divisor A 64-bit signed value.
+ @param Remainder A pointer to a 64-bit signed value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+INT64
+EFIAPI
+DivS64x64Remainder (
+ IN INT64 Dividend,
+ IN INT64 Divisor,
+ OUT INT64 *Remainder OPTIONAL
+ )
+{
+ ASSERT (Divisor != 0);
+ return InternalMathDivRemS64x64 (Dividend, Divisor, Remainder);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32.c
new file mode 100644
index 0000000..fa377ec
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32.c
@@ -0,0 +1,39 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and generates
+ a 64-bit unsigned result.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. This
+ function returns the 64-bit unsigned quotient.
+
+ If Divisor is 0, then ASSERT().
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+DivU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ )
+{
+ ASSERT (Divisor != 0);
+ return InternalMathDivU64x32 (Dividend, Divisor);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32Remainder.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32Remainder.c
new file mode 100644
index 0000000..df9d331
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x32Remainder.c
@@ -0,0 +1,43 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and generates
+ a 64-bit unsigned result and an optional 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 32-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ If Divisor is 0, then ASSERT().
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+ @param Remainder A pointer to a 32-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+DivU64x32Remainder (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor,
+ OUT UINT32 *Remainder OPTIONAL
+ )
+{
+ ASSERT (Divisor != 0);
+ return InternalMathDivRemU64x32 (Dividend, Divisor, Remainder);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x64Remainder.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x64Remainder.c
new file mode 100644
index 0000000..94dc2b1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/DivU64x64Remainder.c
@@ -0,0 +1,43 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Divides a 64-bit unsigned integer by a 64-bit unsigned integer and generates
+ a 64-bit unsigned result and an optional 64-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 64-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 64-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ If Divisor is 0, then ASSERT().
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 64-bit unsigned value.
+ @param Remainder A pointer to a 64-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+DivU64x64Remainder (
+ IN UINT64 Dividend,
+ IN UINT64 Divisor,
+ OUT UINT64 *Remainder OPTIONAL
+ )
+{
+ ASSERT (Divisor != 0);
+ return InternalMathDivRemU64x64 (Dividend, Divisor, Remainder);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/FilePaths.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/FilePaths.c
new file mode 100644
index 0000000..c2c561a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/FilePaths.c
@@ -0,0 +1,115 @@
+/** @file
+ Defines file-path manipulation functions.
+
+ Copyright (c) 2011 - 2017, Intel Corporation. All rights reserved.<BR>
+ Copyright (c) 2018, Dell Technologies. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+#include <Library/BaseMemoryLib.h>
+#include <Library/BaseLib.h>
+
+/**
+ Removes the last directory or file entry in a path. For a path which is
+ like L"fs0:startup.nsh", it's converted to L"fs0:".
+
+ @param[in,out] Path A pointer to the path to modify.
+
+ @retval FALSE Nothing was found to remove.
+ @retval TRUE A directory or file was removed.
+**/
+BOOLEAN
+EFIAPI
+PathRemoveLastItem(
+ IN OUT CHAR16 *Path
+ )
+{
+ CHAR16 *Walker;
+ CHAR16 *LastSlash;
+ //
+ // get directory name from path... ('chop' off extra)
+ //
+ for ( Walker = Path, LastSlash = NULL
+ ; Walker != NULL && *Walker != CHAR_NULL
+ ; Walker++
+ ){
+ if (*Walker == L'\\' && *(Walker + 1) != CHAR_NULL) {
+ LastSlash = Walker+1;
+ } else if (*Walker == L':' && *(Walker + 1) != L'\\' && *(Walker + 1) != CHAR_NULL) {
+ LastSlash = Walker+1;
+ }
+ }
+ if (LastSlash != NULL) {
+ *LastSlash = CHAR_NULL;
+ return (TRUE);
+ }
+ return (FALSE);
+}
+
+/**
+ Function to clean up paths.
+
+ - Single periods in the path are removed.
+ - Double periods in the path are removed along with a single parent directory.
+ - Forward slashes L'/' are converted to backward slashes L'\'.
+
+ This will be done inline and the existing buffer may be larger than required
+ upon completion.
+
+ @param[in] Path The pointer to the string containing the path.
+
+ @return Returns Path, otherwise returns NULL to indicate that an error has occurred.
+**/
+CHAR16*
+EFIAPI
+PathCleanUpDirectories(
+ IN CHAR16 *Path
+)
+{
+ CHAR16 *TempString;
+
+ if (Path == NULL) {
+ return NULL;
+ }
+
+ //
+ // Replace the '/' with '\'
+ //
+ for (TempString = Path; *TempString != CHAR_NULL; TempString++) {
+ if (*TempString == L'/') {
+ *TempString = L'\\';
+ }
+ }
+
+ //
+ // Replace the "\\" with "\"
+ //
+ while ((TempString = StrStr (Path, L"\\\\")) != NULL) {
+ CopyMem (TempString, TempString + 1, StrSize (TempString + 1));
+ }
+
+ //
+ // Remove all the "\.". E.g.: fs0:\abc\.\def\.
+ //
+ while ((TempString = StrStr (Path, L"\\.\\")) != NULL) {
+ CopyMem (TempString, TempString + 2, StrSize (TempString + 2));
+ }
+ if ((StrLen (Path) >= 2) && (StrCmp (Path + StrLen (Path) - 2, L"\\.") == 0)) {
+ Path[StrLen (Path) - 1] = CHAR_NULL;
+ }
+
+ //
+ // Remove all the "\..". E.g.: fs0:\abc\..\def\..
+ //
+ while (((TempString = StrStr(Path, L"\\..")) != NULL) &&
+ ((*(TempString + 3) == L'\\') || (*(TempString + 3) == CHAR_NULL))
+ ) {
+ *(TempString + 1) = CHAR_NULL;
+ PathRemoveLastItem(Path);
+ if (*(TempString + 3) != CHAR_NULL) {
+ CopyMem (Path + StrLen (Path), TempString + 4, StrSize (TempString + 4));
+ }
+ }
+
+ return Path;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo32.c
new file mode 100644
index 0000000..76f5e3c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo32.c
@@ -0,0 +1,38 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the value of the highest bit set in a 32-bit value. Equivalent to
+ 1 << log2(x).
+
+ This function computes the value of the highest bit set in the 32-bit value
+ specified by Operand. If Operand is zero, then zero is returned.
+
+ @param Operand The 32-bit operand to evaluate.
+
+ @return 1 << HighBitSet32(Operand)
+ @retval 0 Operand is zero.
+
+**/
+UINT32
+EFIAPI
+GetPowerOfTwo32 (
+ IN UINT32 Operand
+ )
+{
+ if (0 == Operand) {
+ return 0;
+ }
+
+ return 1ul << HighBitSet32 (Operand);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo64.c
new file mode 100644
index 0000000..5033076
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/GetPowerOfTwo64.c
@@ -0,0 +1,38 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the value of the highest bit set in a 64-bit value. Equivalent to
+ 1 << log2(x).
+
+ This function computes the value of the highest bit set in the 64-bit value
+ specified by Operand. If Operand is zero, then zero is returned.
+
+ @param Operand The 64-bit operand to evaluate.
+
+ @return 1 << HighBitSet64(Operand)
+ @retval 0 Operand is zero.
+
+**/
+UINT64
+EFIAPI
+GetPowerOfTwo64 (
+ IN UINT64 Operand
+ )
+{
+ if (Operand == 0) {
+ return 0;
+ }
+
+ return LShiftU64 (1, (UINTN) HighBitSet64 (Operand));
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet32.c
new file mode 100644
index 0000000..b3c9ed1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet32.c
@@ -0,0 +1,41 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the bit position of the highest bit set in a 32-bit value. Equivalent
+ to log2(x).
+
+ This function computes the bit position of the highest bit set in the 32-bit
+ value specified by Operand. If Operand is zero, then -1 is returned.
+ Otherwise, a value between 0 and 31 is returned.
+
+ @param Operand The 32-bit operand to evaluate.
+
+ @retval 0..31 Position of the highest bit set in Operand if found.
+ @retval -1 Operand is zero.
+
+**/
+INTN
+EFIAPI
+HighBitSet32 (
+ IN UINT32 Operand
+ )
+{
+ INTN BitIndex;
+
+ if (Operand == 0) {
+ return - 1;
+ }
+ for (BitIndex = 31; (INT32)Operand > 0; BitIndex--, Operand <<= 1);
+ return BitIndex;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet64.c
new file mode 100644
index 0000000..4f06dfc
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/HighBitSet64.c
@@ -0,0 +1,49 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the bit position of the highest bit set in a 64-bit value. Equivalent
+ to log2(x).
+
+ This function computes the bit position of the highest bit set in the 64-bit
+ value specified by Operand. If Operand is zero, then -1 is returned.
+ Otherwise, a value between 0 and 63 is returned.
+
+ @param Operand The 64-bit operand to evaluate.
+
+ @retval 0..63 Position of the highest bit set in Operand if found.
+ @retval -1 Operand is zero.
+
+**/
+INTN
+EFIAPI
+HighBitSet64 (
+ IN UINT64 Operand
+ )
+{
+ if (Operand == (UINT32)Operand) {
+ //
+ // Operand is just a 32-bit integer
+ //
+ return HighBitSet32 ((UINT32)Operand);
+ }
+
+ //
+ // Operand is really a 64-bit integer
+ //
+ if (sizeof (UINTN) == sizeof (UINT32)) {
+ return HighBitSet32 (((UINT32*)&Operand)[1]) + 32;
+ } else {
+ return HighBitSet32 ((UINT32)RShiftU64 (Operand, 32)) + 32;
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU32.c
new file mode 100644
index 0000000..4e671a3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU32.c
@@ -0,0 +1,36 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Rotates a 32-bit integer left between 0 and 31 bits, filling the low bits
+ with the high bits that were rotated.
+
+ This function rotates the 32-bit value Operand to the left by Count bits. The
+ low Count bits are fill with the high Count bits of Operand. The rotated
+ value is returned.
+
+ If Count is greater than 31, then ASSERT().
+
+ @param Operand The 32-bit operand to rotate left.
+ @param Count The number of bits to rotate left.
+
+ @return Operand << Count
+
+**/
+UINT32
+EFIAPI
+LRotU32 (
+ IN UINT32 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 32);
+ return (Operand << Count) | (Operand >> (32 - Count));
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU64.c
new file mode 100644
index 0000000..48f35dc
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LRotU64.c
@@ -0,0 +1,36 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Rotates a 64-bit integer left between 0 and 63 bits, filling the low bits
+ with the high bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the left by Count bits. The
+ low Count bits are fill with the high Count bits of Operand. The rotated
+ value is returned.
+
+ If Count is greater than 63, then ASSERT().
+
+ @param Operand The 64-bit operand to rotate left.
+ @param Count The number of bits to rotate left.
+
+ @return Operand << Count
+
+**/
+UINT64
+EFIAPI
+LRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 64);
+ return InternalMathLRotU64 (Operand, Count);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LShiftU64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LShiftU64.c
new file mode 100644
index 0000000..7b41a3e
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LShiftU64.c
@@ -0,0 +1,35 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Shifts a 64-bit integer left between 0 and 63 bits. The low bits are filled
+ with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the left by Count bits. The
+ low Count bits are set to zero. The shifted value is returned.
+
+ If Count is greater than 63, then ASSERT().
+
+ @param Operand The 64-bit operand to shift left.
+ @param Count The number of bits to shift left.
+
+ @return Operand << Count.
+
+**/
+UINT64
+EFIAPI
+LShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 64);
+ return InternalMathLShiftU64 (Operand, Count);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LinkedList.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LinkedList.c
new file mode 100644
index 0000000..5648c18
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LinkedList.c
@@ -0,0 +1,599 @@
+/** @file
+ Linked List Library Functions.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ If PcdVerifyNodeInList is TRUE, ASSERTs when SecondEntry is or is not part of
+ the same doubly-linked list as FirstEntry depending on the value of InList.
+ Independent of PcdVerifyNodeInList, ASSERTs when FirstEntry is not part of a
+ valid list.
+
+ If FirstEntry is NULL, then ASSERT().
+ If FirstEntry->ForwardLink is NULL, then ASSERT().
+ If FirstEntry->BackLink is NULL, then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and List contains more than
+ PcdMaximumLinkedListLength nodes, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and SecondEntry is NULL, then ASSERT().
+
+ @param FirstEntry A pointer to a node in a linked list.
+ @param SecondEntry A pointer to the node to locate.
+ @param InList Defines whether to check if SecondEntry is or is not part
+ of the same doubly-linked list as FirstEntry.
+
+**/
+#if !defined (MDEPKG_NDEBUG)
+ #define ASSERT_VERIFY_NODE_IN_VALID_LIST(FirstEntry, SecondEntry, InList) \
+ do { \
+ if (FeaturePcdGet (PcdVerifyNodeInList)) { \
+ ASSERT (InList == IsNodeInList ((FirstEntry), (SecondEntry))); \
+ } else { \
+ ASSERT (InternalBaseLibIsListValid (FirstEntry)); \
+ } \
+ } while (FALSE)
+#else
+ #define ASSERT_VERIFY_NODE_IN_VALID_LIST(FirstEntry, SecondEntry, InList)
+#endif
+
+/**
+ Worker function that verifies the validity of this list.
+
+ If List is NULL, then ASSERT().
+ If List->ForwardLink is NULL, then ASSERT().
+ If List->BackLink is NULL, then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and List contains more than
+ PcdMaximumLinkedListLength nodes, then ASSERT().
+
+ @param List A pointer to a node in a linked list.
+
+ @retval TRUE if PcdVerifyNodeInList is FALSE
+ @retval TRUE if DoMembershipCheck is FALSE
+ @retval TRUE if PcdVerifyNodeInList is TRUE and DoMembershipCheck is TRUE
+ and Node is a member of List.
+ @retval FALSE if PcdVerifyNodeInList is TRUE and DoMembershipCheck is TRUE
+ and Node is in not a member of List.
+
+**/
+BOOLEAN
+EFIAPI
+InternalBaseLibIsListValid (
+ IN CONST LIST_ENTRY *List
+ )
+{
+ UINTN Count;
+ CONST LIST_ENTRY *Ptr;
+
+ //
+ // Test the validity of List and Node
+ //
+ ASSERT (List != NULL);
+ ASSERT (List->ForwardLink != NULL);
+ ASSERT (List->BackLink != NULL);
+
+ if (PcdGet32 (PcdMaximumLinkedListLength) > 0) {
+ Count = 0;
+ Ptr = List;
+
+ //
+ // Count the total number of nodes in List.
+ // Exit early if the number of nodes in List >= PcdMaximumLinkedListLength
+ //
+ do {
+ Ptr = Ptr->ForwardLink;
+ Count++;
+ } while ((Ptr != List) && (Count < PcdGet32 (PcdMaximumLinkedListLength)));
+
+ //
+ // return whether linked list is too long
+ //
+ return (BOOLEAN)(Count < PcdGet32 (PcdMaximumLinkedListLength));
+ }
+
+ return TRUE;
+}
+
+/**
+ Checks whether FirstEntry and SecondEntry are part of the same doubly-linked
+ list.
+
+ If FirstEntry is NULL, then ASSERT().
+ If FirstEntry->ForwardLink is NULL, then ASSERT().
+ If FirstEntry->BackLink is NULL, then ASSERT().
+ If SecondEntry is NULL, then ASSERT();
+ If PcdMaximumLinkedListLength is not zero, and List contains more than
+ PcdMaximumLinkedListLength nodes, then ASSERT().
+
+ @param FirstEntry A pointer to a node in a linked list.
+ @param SecondEntry A pointer to the node to locate.
+
+ @retval TRUE SecondEntry is in the same doubly-linked list as FirstEntry.
+ @retval FALSE SecondEntry isn't in the same doubly-linked list as FirstEntry,
+ or FirstEntry is invalid.
+
+**/
+BOOLEAN
+EFIAPI
+IsNodeInList (
+ IN CONST LIST_ENTRY *FirstEntry,
+ IN CONST LIST_ENTRY *SecondEntry
+ )
+{
+ UINTN Count;
+ CONST LIST_ENTRY *Ptr;
+
+ //
+ // ASSERT List not too long
+ //
+ ASSERT (InternalBaseLibIsListValid (FirstEntry));
+
+ ASSERT (SecondEntry != NULL);
+
+ Count = 0;
+ Ptr = FirstEntry;
+
+ //
+ // Check to see if SecondEntry is a member of FirstEntry.
+ // Exit early if the number of nodes in List >= PcdMaximumLinkedListLength
+ //
+ do {
+ Ptr = Ptr->ForwardLink;
+ if (PcdGet32 (PcdMaximumLinkedListLength) > 0) {
+ Count++;
+
+ //
+ // Return if the linked list is too long
+ //
+ if (Count == PcdGet32 (PcdMaximumLinkedListLength)) {
+ return (BOOLEAN)(Ptr == SecondEntry);
+ }
+ }
+
+ if (Ptr == SecondEntry) {
+ return TRUE;
+ }
+ } while (Ptr != FirstEntry);
+
+ return FALSE;
+}
+
+/**
+ Initializes the head node of a doubly-linked list, and returns the pointer to
+ the head node of the doubly-linked list.
+
+ Initializes the forward and backward links of a new linked list. After
+ initializing a linked list with this function, the other linked list
+ functions may be used to add and remove nodes from the linked list. It is up
+ to the caller of this function to allocate the memory for ListHead.
+
+ If ListHead is NULL, then ASSERT().
+
+ @param ListHead A pointer to the head node of a new doubly-linked list.
+
+ @return ListHead
+
+**/
+LIST_ENTRY *
+EFIAPI
+InitializeListHead (
+ IN OUT LIST_ENTRY *ListHead
+ )
+
+{
+ ASSERT (ListHead != NULL);
+
+ ListHead->ForwardLink = ListHead;
+ ListHead->BackLink = ListHead;
+ return ListHead;
+}
+
+/**
+ Adds a node to the beginning of a doubly-linked list, and returns the pointer
+ to the head node of the doubly-linked list.
+
+ Adds the node Entry at the beginning of the doubly-linked list denoted by
+ ListHead, and returns ListHead.
+
+ If ListHead is NULL, then ASSERT().
+ If Entry is NULL, then ASSERT().
+ If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and prior to insertion the number
+ of nodes in ListHead, including the ListHead node, is greater than or
+ equal to PcdMaximumLinkedListLength, then ASSERT().
+
+ @param ListHead A pointer to the head node of a doubly-linked list.
+ @param Entry A pointer to a node that is to be inserted at the beginning
+ of a doubly-linked list.
+
+ @return ListHead
+
+**/
+LIST_ENTRY *
+EFIAPI
+InsertHeadList (
+ IN OUT LIST_ENTRY *ListHead,
+ IN OUT LIST_ENTRY *Entry
+ )
+{
+ //
+ // ASSERT List not too long and Entry is not one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (ListHead, Entry, FALSE);
+
+ Entry->ForwardLink = ListHead->ForwardLink;
+ Entry->BackLink = ListHead;
+ Entry->ForwardLink->BackLink = Entry;
+ ListHead->ForwardLink = Entry;
+ return ListHead;
+}
+
+/**
+ Adds a node to the end of a doubly-linked list, and returns the pointer to
+ the head node of the doubly-linked list.
+
+ Adds the node Entry to the end of the doubly-linked list denoted by ListHead,
+ and returns ListHead.
+
+ If ListHead is NULL, then ASSERT().
+ If Entry is NULL, then ASSERT().
+ If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and prior to insertion the number
+ of nodes in ListHead, including the ListHead node, is greater than or
+ equal to PcdMaximumLinkedListLength, then ASSERT().
+
+ @param ListHead A pointer to the head node of a doubly-linked list.
+ @param Entry A pointer to a node that is to be added at the end of the
+ doubly-linked list.
+
+ @return ListHead
+
+**/
+LIST_ENTRY *
+EFIAPI
+InsertTailList (
+ IN OUT LIST_ENTRY *ListHead,
+ IN OUT LIST_ENTRY *Entry
+ )
+{
+ //
+ // ASSERT List not too long and Entry is not one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (ListHead, Entry, FALSE);
+
+ Entry->ForwardLink = ListHead;
+ Entry->BackLink = ListHead->BackLink;
+ Entry->BackLink->ForwardLink = Entry;
+ ListHead->BackLink = Entry;
+ return ListHead;
+}
+
+/**
+ Retrieves the first node of a doubly-linked list.
+
+ Returns the first node of a doubly-linked list. List must have been
+ initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead().
+ If List is empty, then List is returned.
+
+ If List is NULL, then ASSERT().
+ If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes
+ in List, including the List node, is greater than or equal to
+ PcdMaximumLinkedListLength, then ASSERT().
+
+ @param List A pointer to the head node of a doubly-linked list.
+
+ @return The first node of a doubly-linked list.
+ @retval List The list is empty.
+
+**/
+LIST_ENTRY *
+EFIAPI
+GetFirstNode (
+ IN CONST LIST_ENTRY *List
+ )
+{
+ //
+ // ASSERT List not too long
+ //
+ ASSERT (InternalBaseLibIsListValid (List));
+
+ return List->ForwardLink;
+}
+
+/**
+ Retrieves the next node of a doubly-linked list.
+
+ Returns the node of a doubly-linked list that follows Node.
+ List must have been initialized with INTIALIZE_LIST_HEAD_VARIABLE()
+ or InitializeListHead(). If List is empty, then List is returned.
+
+ If List is NULL, then ASSERT().
+ If Node is NULL, then ASSERT().
+ If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and List contains more than
+ PcdMaximumLinkedListLength nodes, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSERT().
+
+ @param List A pointer to the head node of a doubly-linked list.
+ @param Node A pointer to a node in the doubly-linked list.
+
+ @return A pointer to the next node if one exists. Otherwise List is returned.
+
+**/
+LIST_ENTRY *
+EFIAPI
+GetNextNode (
+ IN CONST LIST_ENTRY *List,
+ IN CONST LIST_ENTRY *Node
+ )
+{
+ //
+ // ASSERT List not too long and Node is one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (List, Node, TRUE);
+
+ return Node->ForwardLink;
+}
+
+/**
+ Retrieves the previous node of a doubly-linked list.
+
+ Returns the node of a doubly-linked list that precedes Node.
+ List must have been initialized with INTIALIZE_LIST_HEAD_VARIABLE()
+ or InitializeListHead(). If List is empty, then List is returned.
+
+ If List is NULL, then ASSERT().
+ If Node is NULL, then ASSERT().
+ If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and List contains more than
+ PcdMaximumLinkedListLength nodes, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSERT().
+
+ @param List A pointer to the head node of a doubly-linked list.
+ @param Node A pointer to a node in the doubly-linked list.
+
+ @return A pointer to the previous node if one exists. Otherwise List is returned.
+
+**/
+LIST_ENTRY *
+EFIAPI
+GetPreviousNode (
+ IN CONST LIST_ENTRY *List,
+ IN CONST LIST_ENTRY *Node
+ )
+{
+ //
+ // ASSERT List not too long and Node is one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (List, Node, TRUE);
+
+ return Node->BackLink;
+}
+
+/**
+ Checks to see if a doubly-linked list is empty or not.
+
+ Checks to see if the doubly-linked list is empty. If the linked list contains
+ zero nodes, this function returns TRUE. Otherwise, it returns FALSE.
+
+ If ListHead is NULL, then ASSERT().
+ If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes
+ in List, including the List node, is greater than or equal to
+ PcdMaximumLinkedListLength, then ASSERT().
+
+ @param ListHead A pointer to the head node of a doubly-linked list.
+
+ @retval TRUE The linked list is empty.
+ @retval FALSE The linked list is not empty.
+
+**/
+BOOLEAN
+EFIAPI
+IsListEmpty (
+ IN CONST LIST_ENTRY *ListHead
+ )
+{
+ //
+ // ASSERT List not too long
+ //
+ ASSERT (InternalBaseLibIsListValid (ListHead));
+
+ return (BOOLEAN)(ListHead->ForwardLink == ListHead);
+}
+
+/**
+ Determines if a node in a doubly-linked list is the head node of a the same
+ doubly-linked list. This function is typically used to terminate a loop that
+ traverses all the nodes in a doubly-linked list starting with the head node.
+
+ Returns TRUE if Node is equal to List. Returns FALSE if Node is one of the
+ nodes in the doubly-linked list specified by List. List must have been
+ initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead().
+
+ If List is NULL, then ASSERT().
+ If Node is NULL, then ASSERT().
+ If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead(),
+ then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes
+ in List, including the List node, is greater than or equal to
+ PcdMaximumLinkedListLength, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and Node is not a node in List and Node is not
+ equal to List, then ASSERT().
+
+ @param List A pointer to the head node of a doubly-linked list.
+ @param Node A pointer to a node in the doubly-linked list.
+
+ @retval TRUE Node is the head of the doubly-linked list pointed by List.
+ @retval FALSE Node is not the head of the doubly-linked list pointed by List.
+
+**/
+BOOLEAN
+EFIAPI
+IsNull (
+ IN CONST LIST_ENTRY *List,
+ IN CONST LIST_ENTRY *Node
+ )
+{
+ //
+ // ASSERT List not too long and Node is one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (List, Node, TRUE);
+
+ return (BOOLEAN)(Node == List);
+}
+
+/**
+ Determines if a node the last node in a doubly-linked list.
+
+ Returns TRUE if Node is the last node in the doubly-linked list specified by
+ List. Otherwise, FALSE is returned. List must have been initialized with
+ INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead().
+
+ If List is NULL, then ASSERT().
+ If Node is NULL, then ASSERT().
+ If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or
+ InitializeListHead(), then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes
+ in List, including the List node, is greater than or equal to
+ PcdMaximumLinkedListLength, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSERT().
+
+ @param List A pointer to the head node of a doubly-linked list.
+ @param Node A pointer to a node in the doubly-linked list.
+
+ @retval TRUE Node is the last node in the linked list.
+ @retval FALSE Node is not the last node in the linked list.
+
+**/
+BOOLEAN
+EFIAPI
+IsNodeAtEnd (
+ IN CONST LIST_ENTRY *List,
+ IN CONST LIST_ENTRY *Node
+ )
+{
+ //
+ // ASSERT List not too long and Node is one of the nodes of List
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (List, Node, TRUE);
+
+ return (BOOLEAN)(!IsNull (List, Node) && List->BackLink == Node);
+}
+
+/**
+ Swaps the location of two nodes in a doubly-linked list, and returns the
+ first node after the swap.
+
+ If FirstEntry is identical to SecondEntry, then SecondEntry is returned.
+ Otherwise, the location of the FirstEntry node is swapped with the location
+ of the SecondEntry node in a doubly-linked list. SecondEntry must be in the
+ same double linked list as FirstEntry and that double linked list must have
+ been initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead().
+ SecondEntry is returned after the nodes are swapped.
+
+ If FirstEntry is NULL, then ASSERT().
+ If SecondEntry is NULL, then ASSERT().
+ If PcdVerifyNodeInList is TRUE and SecondEntry and FirstEntry are not in the
+ same linked list, then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes in the
+ linked list containing the FirstEntry and SecondEntry nodes, including
+ the FirstEntry and SecondEntry nodes, is greater than or equal to
+ PcdMaximumLinkedListLength, then ASSERT().
+
+ @param FirstEntry A pointer to a node in a linked list.
+ @param SecondEntry A pointer to another node in the same linked list.
+
+ @return SecondEntry.
+
+**/
+LIST_ENTRY *
+EFIAPI
+SwapListEntries (
+ IN OUT LIST_ENTRY *FirstEntry,
+ IN OUT LIST_ENTRY *SecondEntry
+ )
+{
+ LIST_ENTRY *Ptr;
+
+ if (FirstEntry == SecondEntry) {
+ return SecondEntry;
+ }
+
+ //
+ // ASSERT Entry1 and Entry2 are in the same linked list
+ //
+ ASSERT_VERIFY_NODE_IN_VALID_LIST (FirstEntry, SecondEntry, TRUE);
+
+ //
+ // Ptr is the node pointed to by FirstEntry->ForwardLink
+ //
+ Ptr = RemoveEntryList (FirstEntry);
+
+ //
+ // If FirstEntry immediately follows SecondEntry, FirstEntry will be placed
+ // immediately in front of SecondEntry
+ //
+ if (Ptr->BackLink == SecondEntry) {
+ return InsertTailList (SecondEntry, FirstEntry);
+ }
+
+ //
+ // Ptr == SecondEntry means SecondEntry immediately follows FirstEntry,
+ // then there are no further steps necessary
+ //
+ if (Ptr == InsertHeadList (SecondEntry, FirstEntry)) {
+ return Ptr;
+ }
+
+ //
+ // Move SecondEntry to the front of Ptr
+ //
+ RemoveEntryList (SecondEntry);
+ InsertTailList (Ptr, SecondEntry);
+ return SecondEntry;
+}
+
+/**
+ Removes a node from a doubly-linked list, and returns the node that follows
+ the removed node.
+
+ Removes the node Entry from a doubly-linked list. It is up to the caller of
+ this function to release the memory used by this node if that is required. On
+ exit, the node following Entry in the doubly-linked list is returned. If
+ Entry is the only node in the linked list, then the head node of the linked
+ list is returned.
+
+ If Entry is NULL, then ASSERT().
+ If Entry is the head node of an empty list, then ASSERT().
+ If PcdMaximumLinkedListLength is not zero, and the number of nodes in the
+ linked list containing Entry, including the Entry node, is greater than
+ or equal to PcdMaximumLinkedListLength, then ASSERT().
+
+ @param Entry A pointer to a node in a linked list.
+
+ @return Entry.
+
+**/
+LIST_ENTRY *
+EFIAPI
+RemoveEntryList (
+ IN CONST LIST_ENTRY *Entry
+ )
+{
+ ASSERT (!IsListEmpty (Entry));
+
+ Entry->ForwardLink->BackLink = Entry->BackLink;
+ Entry->BackLink->ForwardLink = Entry->ForwardLink;
+ return Entry->ForwardLink;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LongJump.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LongJump.c
new file mode 100644
index 0000000..1d88e41
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LongJump.c
@@ -0,0 +1,41 @@
+/** @file
+ Long Jump functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Restores the CPU context that was saved with SetJump().
+
+ Restores the CPU context from the buffer specified by JumpBuffer. This
+ function never returns to the caller. Instead is resumes execution based on
+ the state of JumpBuffer.
+
+ If JumpBuffer is NULL, then ASSERT().
+ For IPF CPUs, if JumpBuffer is not aligned on a 16-byte boundary, then ASSERT().
+ If Value is 0, then ASSERT().
+
+ @param JumpBuffer A pointer to CPU context buffer.
+ @param Value The value to return when the SetJump() context is
+ restored and must be non-zero.
+
+**/
+VOID
+EFIAPI
+LongJump (
+ IN BASE_LIBRARY_JUMP_BUFFER *JumpBuffer,
+ IN UINTN Value
+ )
+{
+ InternalAssertJumpBuffer (JumpBuffer);
+ ASSERT (Value != 0);
+
+ InternalLongJump (JumpBuffer, Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet32.c
new file mode 100644
index 0000000..8383c79
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet32.c
@@ -0,0 +1,41 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the bit position of the lowest bit set in a 32-bit value.
+
+ This function computes the bit position of the lowest bit set in the 32-bit
+ value specified by Operand. If Operand is zero, then -1 is returned.
+ Otherwise, a value between 0 and 31 is returned.
+
+ @param Operand The 32-bit operand to evaluate.
+
+ @retval 0..31 The lowest bit set in Operand was found.
+ @retval -1 Operand is zero.
+
+**/
+INTN
+EFIAPI
+LowBitSet32 (
+ IN UINT32 Operand
+ )
+{
+ INTN BitIndex;
+
+ if (Operand == 0) {
+ return -1;
+ }
+
+ for (BitIndex = 0; 0 == (Operand & 1); BitIndex++, Operand >>= 1);
+ return BitIndex;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet64.c
new file mode 100644
index 0000000..349ed52
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/LowBitSet64.c
@@ -0,0 +1,44 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Returns the bit position of the lowest bit set in a 64-bit value.
+
+ This function computes the bit position of the lowest bit set in the 64-bit
+ value specified by Operand. If Operand is zero, then -1 is returned.
+ Otherwise, a value between 0 and 63 is returned.
+
+ @param Operand The 64-bit operand to evaluate.
+
+ @retval 0..63 The lowest bit set in Operand was found.
+ @retval -1 Operand is zero.
+
+
+**/
+INTN
+EFIAPI
+LowBitSet64 (
+ IN UINT64 Operand
+ )
+{
+ INTN BitIndex;
+
+ if (Operand == 0) {
+ return -1;
+ }
+
+ for (BitIndex = 0;
+ (Operand & 1) == 0;
+ BitIndex++, Operand = RShiftU64 (Operand, 1));
+ return BitIndex;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/Math64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Math64.c
new file mode 100644
index 0000000..154b97a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Math64.c
@@ -0,0 +1,362 @@
+/** @file
+ Leaf math worker functions that require 64-bit arithmetic support from the
+ compiler.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Shifts a 64-bit integer left between 0 and 63 bits. The low bits
+ are filled with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the left by Count bits. The
+ low Count bits are set to zero. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift left.
+ @param Count The number of bits to shift left.
+
+ @return Operand << Count.
+
+**/
+UINT64
+EFIAPI
+InternalMathLShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ return Operand << Count;
+}
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. This high bits
+ are filled with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to zero. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand >> Count.
+
+**/
+UINT64
+EFIAPI
+InternalMathRShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ return Operand >> Count;
+}
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. The high bits
+ are filled with original integer's bit 63. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to bit 63 of Operand. The shifted value is returned.
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand arithmetically shifted right by Count.
+
+**/
+UINT64
+EFIAPI
+InternalMathARShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ INTN TestValue;
+
+ //
+ // Test if this compiler supports arithmetic shift
+ //
+ TestValue = (INTN)((INT64)(1ULL << 63) >> 63);
+ if (TestValue == -1) {
+ //
+ // Arithmetic shift is supported
+ //
+ return (UINT64)((INT64)Operand >> Count);
+ }
+
+ //
+ // Arithmetic is not supported
+ //
+ return (Operand >> Count) |
+ ((INTN)Operand < 0 ? ~((UINTN)-1 >> Count) : 0);
+}
+
+
+/**
+ Rotates a 64-bit integer left between 0 and 63 bits, filling
+ the low bits with the high bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the left by Count bits. The
+ low Count bits are fill with the high Count bits of Operand. The rotated
+ value is returned.
+
+ @param Operand The 64-bit operand to rotate left.
+ @param Count The number of bits to rotate left.
+
+ @return Operand <<< Count.
+
+**/
+UINT64
+EFIAPI
+InternalMathLRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ return (Operand << Count) | (Operand >> (64 - Count));
+}
+
+/**
+ Rotates a 64-bit integer right between 0 and 63 bits, filling
+ the high bits with the high low bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the right by Count bits.
+ The high Count bits are fill with the low Count bits of Operand. The rotated
+ value is returned.
+
+ @param Operand The 64-bit operand to rotate right.
+ @param Count The number of bits to rotate right.
+
+ @return Operand >>> Count.
+
+**/
+UINT64
+EFIAPI
+InternalMathRRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ return (Operand >> Count) | (Operand << (64 - Count));
+}
+
+/**
+ Switches the endianess of a 64-bit integer.
+
+ This function swaps the bytes in a 64-bit unsigned value to switch the value
+ from little endian to big endian or vice versa. The byte swapped value is
+ returned.
+
+ @param Operand A 64-bit unsigned value.
+
+ @return The byte swapped Operand.
+
+**/
+UINT64
+EFIAPI
+InternalMathSwapBytes64 (
+ IN UINT64 Operand
+ )
+{
+ UINT64 LowerBytes;
+ UINT64 HigherBytes;
+
+ LowerBytes = (UINT64) SwapBytes32 ((UINT32) Operand);
+ HigherBytes = (UINT64) SwapBytes32 ((UINT32) (Operand >> 32));
+
+ return (LowerBytes << 32 | HigherBytes);
+}
+
+/**
+ Multiplies a 64-bit unsigned integer by a 32-bit unsigned integer
+ and generates a 64-bit unsigned result.
+
+ This function multiplies the 64-bit unsigned value Multiplicand by the 32-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 32-bit unsigned value.
+
+ @return Multiplicand * Multiplier
+
+**/
+UINT64
+EFIAPI
+InternalMathMultU64x32 (
+ IN UINT64 Multiplicand,
+ IN UINT32 Multiplier
+ )
+{
+ return Multiplicand * Multiplier;
+}
+
+
+/**
+ Multiplies a 64-bit unsigned integer by a 64-bit unsigned integer
+ and generates a 64-bit unsigned result.
+
+ This function multiplies the 64-bit unsigned value Multiplicand by the 64-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 64-bit unsigned value.
+
+ @return Multiplicand * Multiplier.
+
+**/
+UINT64
+EFIAPI
+InternalMathMultU64x64 (
+ IN UINT64 Multiplicand,
+ IN UINT64 Multiplier
+ )
+{
+ return Multiplicand * Multiplier;
+}
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 64-bit unsigned result.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. This
+ function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend / Divisor.
+
+**/
+UINT64
+EFIAPI
+InternalMathDivU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ )
+{
+ return Dividend / Divisor;
+}
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 32-bit remainder. This function
+ returns the 32-bit unsigned remainder.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend % Divisor.
+
+**/
+UINT32
+EFIAPI
+InternalMathModU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ )
+{
+ return (UINT32)(Dividend % Divisor);
+}
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 64-bit unsigned result and an optional 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 32-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+ @param Remainder A pointer to a 32-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor.
+
+**/
+UINT64
+EFIAPI
+InternalMathDivRemU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor,
+ OUT UINT32 *Remainder OPTIONAL
+ )
+{
+ if (Remainder != NULL) {
+ *Remainder = (UINT32)(Dividend % Divisor);
+ }
+ return Dividend / Divisor;
+}
+
+/**
+ Divides a 64-bit unsigned integer by a 64-bit unsigned integer and
+ generates a 64-bit unsigned result and an optional 64-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 64-bit
+ unsigned value Divisor and generates a 64-bit unsigned quotient. If Remainder
+ is not NULL, then the 64-bit unsigned remainder is returned in Remainder.
+ This function returns the 64-bit unsigned quotient.
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 64-bit unsigned value.
+ @param Remainder A pointer to a 64-bit unsigned value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor
+
+**/
+UINT64
+EFIAPI
+InternalMathDivRemU64x64 (
+ IN UINT64 Dividend,
+ IN UINT64 Divisor,
+ OUT UINT64 *Remainder OPTIONAL
+ )
+{
+ if (Remainder != NULL) {
+ *Remainder = Dividend % Divisor;
+ }
+ return Dividend / Divisor;
+}
+
+/**
+ Divides a 64-bit signed integer by a 64-bit signed integer and
+ generates a 64-bit signed result and an optional 64-bit signed remainder.
+
+ This function divides the 64-bit signed value Dividend by the 64-bit
+ signed value Divisor and generates a 64-bit signed quotient. If Remainder
+ is not NULL, then the 64-bit signed remainder is returned in Remainder.
+ This function returns the 64-bit signed quotient.
+
+ @param Dividend A 64-bit signed value.
+ @param Divisor A 64-bit signed value.
+ @param Remainder A pointer to a 64-bit signed value. This parameter is
+ optional and may be NULL.
+
+ @return Dividend / Divisor.
+
+**/
+INT64
+EFIAPI
+InternalMathDivRemS64x64 (
+ IN INT64 Dividend,
+ IN INT64 Divisor,
+ OUT INT64 *Remainder OPTIONAL
+ )
+{
+ if (Remainder != NULL) {
+ *Remainder = Dividend % Divisor;
+ }
+ return Dividend / Divisor;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/ModU64x32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ModU64x32.c
new file mode 100644
index 0000000..ee99ab3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/ModU64x32.c
@@ -0,0 +1,39 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Divides a 64-bit unsigned integer by a 32-bit unsigned integer and generates
+ a 32-bit unsigned remainder.
+
+ This function divides the 64-bit unsigned value Dividend by the 32-bit
+ unsigned value Divisor and generates a 32-bit remainder. This function
+ returns the 32-bit unsigned remainder.
+
+ If Divisor is 0, then ASSERT().
+
+ @param Dividend A 64-bit unsigned value.
+ @param Divisor A 32-bit unsigned value.
+
+ @return Dividend % Divisor.
+
+**/
+UINT32
+EFIAPI
+ModU64x32 (
+ IN UINT64 Dividend,
+ IN UINT32 Divisor
+ )
+{
+ ASSERT (Divisor != 0);
+ return InternalMathModU64x32 (Dividend, Divisor);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultS64x64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultS64x64.c
new file mode 100644
index 0000000..b5c745f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultS64x64.c
@@ -0,0 +1,36 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Multiplies a 64-bit signed integer by a 64-bit signed integer and generates a
+ 64-bit signed result.
+
+ This function multiplies the 64-bit signed value Multiplicand by the 64-bit
+ signed value Multiplier and generates a 64-bit signed result. This 64-bit
+ signed result is returned.
+
+ @param Multiplicand A 64-bit signed value.
+ @param Multiplier A 64-bit signed value.
+
+ @return Multiplicand * Multiplier.
+
+**/
+INT64
+EFIAPI
+MultS64x64 (
+ IN INT64 Multiplicand,
+ IN INT64 Multiplier
+ )
+{
+ return (INT64)MultU64x64 ((UINT64) Multiplicand, (UINT64) Multiplier);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x32.c
new file mode 100644
index 0000000..2bbff51
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x32.c
@@ -0,0 +1,40 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Multiplies a 64-bit unsigned integer by a 32-bit unsigned integer and
+ generates a 64-bit unsigned result.
+
+ This function multiplies the 64-bit unsigned value Multiplicand by the 32-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 32-bit unsigned value.
+
+ @return Multiplicand * Multiplier.
+
+**/
+UINT64
+EFIAPI
+MultU64x32 (
+ IN UINT64 Multiplicand,
+ IN UINT32 Multiplier
+ )
+{
+ UINT64 Result;
+
+ Result = InternalMathMultU64x32 (Multiplicand, Multiplier);
+
+ return Result;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x64.c
new file mode 100644
index 0000000..e1ee9f1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/MultU64x64.c
@@ -0,0 +1,40 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Multiplies a 64-bit unsigned integer by a 64-bit unsigned integer and
+ generates a 64-bit unsigned result.
+
+ This function multiplies the 64-bit unsigned value Multiplicand by the 64-bit
+ unsigned value Multiplier and generates a 64-bit unsigned result. This 64-
+ bit unsigned result is returned.
+
+ @param Multiplicand A 64-bit unsigned value.
+ @param Multiplier A 64-bit unsigned value.
+
+ @return Multiplicand * Multiplier.
+
+**/
+UINT64
+EFIAPI
+MultU64x64 (
+ IN UINT64 Multiplicand,
+ IN UINT64 Multiplier
+ )
+{
+ UINT64 Result;
+
+ Result = InternalMathMultU64x64 (Multiplicand, Multiplier);
+
+ return Result;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU32.c
new file mode 100644
index 0000000..3956fad
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU32.c
@@ -0,0 +1,36 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Rotates a 32-bit integer right between 0 and 31 bits, filling the high bits
+ with the low bits that were rotated.
+
+ This function rotates the 32-bit value Operand to the right by Count bits.
+ The high Count bits are fill with the low Count bits of Operand. The rotated
+ value is returned.
+
+ If Count is greater than 31, then ASSERT().
+
+ @param Operand The 32-bit operand to rotate right.
+ @param Count The number of bits to rotate right.
+
+ @return Operand >> Count.
+
+**/
+UINT32
+EFIAPI
+RRotU32 (
+ IN UINT32 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 32);
+ return (Operand >> Count) | (Operand << (32 - Count));
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU64.c
new file mode 100644
index 0000000..e07ffd6
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RRotU64.c
@@ -0,0 +1,36 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Rotates a 64-bit integer right between 0 and 63 bits, filling the high bits
+ with the high low bits that were rotated.
+
+ This function rotates the 64-bit value Operand to the right by Count bits.
+ The high Count bits are fill with the low Count bits of Operand. The rotated
+ value is returned.
+
+ If Count is greater than 63, then ASSERT().
+
+ @param Operand The 64-bit operand to rotate right.
+ @param Count The number of bits to rotate right.
+
+ @return Operand >> Count.
+
+**/
+UINT64
+EFIAPI
+RRotU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 64);
+ return InternalMathRRotU64 (Operand, Count);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/RShiftU64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RShiftU64.c
new file mode 100644
index 0000000..20f94f7
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/RShiftU64.c
@@ -0,0 +1,35 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Shifts a 64-bit integer right between 0 and 63 bits. This high bits are
+ filled with zeros. The shifted value is returned.
+
+ This function shifts the 64-bit value Operand to the right by Count bits. The
+ high Count bits are set to zero. The shifted value is returned.
+
+ If Count is greater than 63, then ASSERT().
+
+ @param Operand The 64-bit operand to shift right.
+ @param Count The number of bits to shift right.
+
+ @return Operand >> Count.
+
+**/
+UINT64
+EFIAPI
+RShiftU64 (
+ IN UINT64 Operand,
+ IN UINTN Count
+ )
+{
+ ASSERT (Count < 64);
+ return InternalMathRShiftU64 (Operand, Count);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SafeString.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SafeString.c
new file mode 100644
index 0000000..3bb23ca
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SafeString.c
@@ -0,0 +1,3535 @@
+/** @file
+ Safe String functions.
+
+ Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+#define RSIZE_MAX (PcdGet32 (PcdMaximumUnicodeStringLength))
+
+#define ASCII_RSIZE_MAX (PcdGet32 (PcdMaximumAsciiStringLength))
+
+#define SAFE_STRING_CONSTRAINT_CHECK(Expression, Status) \
+ do { \
+ if (!(Expression)) { \
+ DEBUG ((DEBUG_VERBOSE, \
+ "%a(%d) %a: SAFE_STRING_CONSTRAINT_CHECK(%a) failed. Return %r\n", \
+ __FILE__, __LINE__, __FUNCTION__, #Expression, Status)); \
+ return Status; \
+ } \
+ } while (FALSE)
+
+/**
+ Returns if 2 memory blocks are overlapped.
+
+ @param Base1 Base address of 1st memory block.
+ @param Size1 Size of 1st memory block.
+ @param Base2 Base address of 2nd memory block.
+ @param Size2 Size of 2nd memory block.
+
+ @retval TRUE 2 memory blocks are overlapped.
+ @retval FALSE 2 memory blocks are not overlapped.
+**/
+BOOLEAN
+InternalSafeStringIsOverlap (
+ IN VOID *Base1,
+ IN UINTN Size1,
+ IN VOID *Base2,
+ IN UINTN Size2
+ )
+{
+ if ((((UINTN)Base1 >= (UINTN)Base2) && ((UINTN)Base1 < (UINTN)Base2 + Size2)) ||
+ (((UINTN)Base2 >= (UINTN)Base1) && ((UINTN)Base2 < (UINTN)Base1 + Size1))) {
+ return TRUE;
+ }
+ return FALSE;
+}
+
+/**
+ Returns if 2 Unicode strings are not overlapped.
+
+ @param Str1 Start address of 1st Unicode string.
+ @param Size1 The number of char in 1st Unicode string,
+ including terminating null char.
+ @param Str2 Start address of 2nd Unicode string.
+ @param Size2 The number of char in 2nd Unicode string,
+ including terminating null char.
+
+ @retval TRUE 2 Unicode strings are NOT overlapped.
+ @retval FALSE 2 Unicode strings are overlapped.
+**/
+BOOLEAN
+InternalSafeStringNoStrOverlap (
+ IN CHAR16 *Str1,
+ IN UINTN Size1,
+ IN CHAR16 *Str2,
+ IN UINTN Size2
+ )
+{
+ return !InternalSafeStringIsOverlap (Str1, Size1 * sizeof(CHAR16), Str2, Size2 * sizeof(CHAR16));
+}
+
+/**
+ Returns if 2 Ascii strings are not overlapped.
+
+ @param Str1 Start address of 1st Ascii string.
+ @param Size1 The number of char in 1st Ascii string,
+ including terminating null char.
+ @param Str2 Start address of 2nd Ascii string.
+ @param Size2 The number of char in 2nd Ascii string,
+ including terminating null char.
+
+ @retval TRUE 2 Ascii strings are NOT overlapped.
+ @retval FALSE 2 Ascii strings are overlapped.
+**/
+BOOLEAN
+InternalSafeStringNoAsciiStrOverlap (
+ IN CHAR8 *Str1,
+ IN UINTN Size1,
+ IN CHAR8 *Str2,
+ IN UINTN Size2
+ )
+{
+ return !InternalSafeStringIsOverlap (Str1, Size1, Str2, Size2);
+}
+
+/**
+ Returns the length of a Null-terminated Unicode string.
+
+ This function is similar as strlen_s defined in C11.
+
+ If String is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+ @param MaxSize The maximum number of Destination Unicode
+ char, including terminating null char.
+
+ @retval 0 If String is NULL.
+ @retval MaxSize If there is no null character in the first MaxSize characters of String.
+ @return The number of characters that percede the terminating null character.
+
+**/
+UINTN
+EFIAPI
+StrnLenS (
+ IN CONST CHAR16 *String,
+ IN UINTN MaxSize
+ )
+{
+ UINTN Length;
+
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // If String is a null pointer or MaxSize is 0, then the StrnLenS function returns zero.
+ //
+ if ((String == NULL) || (MaxSize == 0)) {
+ return 0;
+ }
+
+ //
+ // Otherwise, the StrnLenS function returns the number of characters that precede the
+ // terminating null character. If there is no null character in the first MaxSize characters of
+ // String then StrnLenS returns MaxSize. At most the first MaxSize characters of String shall
+ // be accessed by StrnLenS.
+ //
+ Length = 0;
+ while (String[Length] != 0) {
+ if (Length >= MaxSize - 1) {
+ return MaxSize;
+ }
+ Length++;
+ }
+ return Length;
+}
+
+/**
+ Returns the size of a Null-terminated Unicode string in bytes, including the
+ Null terminator.
+
+ This function returns the size of the Null-terminated Unicode string
+ specified by String in bytes, including the Null terminator.
+
+ If String is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+ @param MaxSize The maximum number of Destination Unicode
+ char, including the Null terminator.
+
+ @retval 0 If String is NULL.
+ @retval (sizeof (CHAR16) * (MaxSize + 1))
+ If there is no Null terminator in the first MaxSize characters of
+ String.
+ @return The size of the Null-terminated Unicode string in bytes, including
+ the Null terminator.
+
+**/
+UINTN
+EFIAPI
+StrnSizeS (
+ IN CONST CHAR16 *String,
+ IN UINTN MaxSize
+ )
+{
+ //
+ // If String is a null pointer, then the StrnSizeS function returns zero.
+ //
+ if (String == NULL) {
+ return 0;
+ }
+
+ //
+ // Otherwise, the StrnSizeS function returns the size of the Null-terminated
+ // Unicode string in bytes, including the Null terminator. If there is no
+ // Null terminator in the first MaxSize characters of String, then StrnSizeS
+ // returns (sizeof (CHAR16) * (MaxSize + 1)) to keep a consistent map with
+ // the StrnLenS function.
+ //
+ return (StrnLenS (String, MaxSize) + 1) * sizeof (*String);
+}
+
+/**
+ Copies the string pointed to by Source (including the terminating null char)
+ to the array pointed to by Destination.
+
+ This function is similar as strcpy_s defined in C11.
+
+ If Destination is not aligned on a 16-bit boundary, then ASSERT().
+ If Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Unicode string.
+
+ @retval RETURN_SUCCESS String is copied.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+StrCpyS (
+ OUT CHAR16 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR16 *Source
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. DestMax shall be greater than StrnLenS(Source, DestMax).
+ //
+ SourceLen = StrnLenS (Source, DestMax);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoStrOverlap (Destination, DestMax, (CHAR16 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The StrCpyS function copies the string pointed to by Source (including the terminating
+ // null character) into the array pointed to by Destination.
+ //
+ while (*Source != 0) {
+ *(Destination++) = *(Source++);
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Copies not more than Length successive char from the string pointed to by
+ Source to the array pointed to by Destination. If no null char is copied from
+ Source, then Destination[Length] is always set to null.
+
+ This function is similar as strncpy_s defined in C11.
+
+ If Length > 0 and Destination is not aligned on a 16-bit boundary, then ASSERT().
+ If Length > 0 and Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Unicode string.
+ @param Length The maximum number of Unicode characters to copy.
+
+ @retval RETURN_SUCCESS String is copied.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than
+ MIN(StrLen(Source), Length).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+StrnCpyS (
+ OUT CHAR16 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR16 *Source,
+ IN UINTN Length
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither DestMax nor Length shall be greater than RSIZE_MAX
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. If Length is not less than DestMax, then DestMax shall be greater than StrnLenS(Source, DestMax).
+ //
+ SourceLen = StrnLenS (Source, MIN (DestMax, Length));
+ if (Length >= DestMax) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoStrOverlap (Destination, DestMax, (CHAR16 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The StrnCpyS function copies not more than Length successive characters (characters that
+ // follow a null character are not copied) from the array pointed to by Source to the array
+ // pointed to by Destination. If no null character was copied from Source, then Destination[Length] is set to a null
+ // character.
+ //
+ while ((SourceLen > 0) && (*Source != 0)) {
+ *(Destination++) = *(Source++);
+ SourceLen--;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Appends a copy of the string pointed to by Source (including the terminating
+ null char) to the end of the string pointed to by Destination.
+
+ This function is similar as strcat_s defined in C11.
+
+ If Destination is not aligned on a 16-bit boundary, then ASSERT().
+ If Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Unicode string.
+
+ @retval RETURN_SUCCESS String is appended.
+ @retval RETURN_BAD_BUFFER_SIZE If DestMax is NOT greater than
+ StrLen(Destination).
+ @retval RETURN_BUFFER_TOO_SMALL If (DestMax - StrLen(Destination)) is NOT
+ greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+StrCatS (
+ IN OUT CHAR16 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR16 *Source
+ )
+{
+ UINTN DestLen;
+ UINTN CopyLen;
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // Let CopyLen denote the value DestMax - StrnLenS(Destination, DestMax) upon entry to StrCatS.
+ //
+ DestLen = StrnLenS (Destination, DestMax);
+ CopyLen = DestMax - DestLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. CopyLen shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen != 0), RETURN_BAD_BUFFER_SIZE);
+
+ //
+ // 5. CopyLen shall be greater than StrnLenS(Source, CopyLen).
+ //
+ SourceLen = StrnLenS (Source, CopyLen);
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 6. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoStrOverlap (Destination, DestMax, (CHAR16 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The StrCatS function appends a copy of the string pointed to by Source (including the
+ // terminating null character) to the end of the string pointed to by Destination. The initial character
+ // from Source overwrites the null character at the end of Destination.
+ //
+ Destination = Destination + DestLen;
+ while (*Source != 0) {
+ *(Destination++) = *(Source++);
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Appends not more than Length successive char from the string pointed to by
+ Source to the end of the string pointed to by Destination. If no null char is
+ copied from Source, then Destination[StrLen(Destination) + Length] is always
+ set to null.
+
+ This function is similar as strncat_s defined in C11.
+
+ If Destination is not aligned on a 16-bit boundary, then ASSERT().
+ If Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Unicode string.
+ @param Length The maximum number of Unicode characters to copy.
+
+ @retval RETURN_SUCCESS String is appended.
+ @retval RETURN_BAD_BUFFER_SIZE If DestMax is NOT greater than
+ StrLen(Destination).
+ @retval RETURN_BUFFER_TOO_SMALL If (DestMax - StrLen(Destination)) is NOT
+ greater than MIN(StrLen(Source), Length).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+StrnCatS (
+ IN OUT CHAR16 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR16 *Source,
+ IN UINTN Length
+ )
+{
+ UINTN DestLen;
+ UINTN CopyLen;
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // Let CopyLen denote the value DestMax - StrnLenS(Destination, DestMax) upon entry to StrnCatS.
+ //
+ DestLen = StrnLenS (Destination, DestMax);
+ CopyLen = DestMax - DestLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither DestMax nor Length shall be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. CopyLen shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen != 0), RETURN_BAD_BUFFER_SIZE);
+
+ //
+ // 5. If Length is not less than CopyLen, then CopyLen shall be greater than StrnLenS(Source, CopyLen).
+ //
+ SourceLen = StrnLenS (Source, MIN (CopyLen, Length));
+ if (Length >= CopyLen) {
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 6. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoStrOverlap (Destination, DestMax, (CHAR16 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The StrnCatS function appends not more than Length successive characters (characters
+ // that follow a null character are not copied) from the array pointed to by Source to the end of
+ // the string pointed to by Destination. The initial character from Source overwrites the null character at
+ // the end of Destination. If no null character was copied from Source, then Destination[DestMax-CopyLen+Length] is set to
+ // a null character.
+ //
+ Destination = Destination + DestLen;
+ while ((SourceLen > 0) && (*Source != 0)) {
+ *(Destination++) = *(Source++);
+ SourceLen--;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode decimal string to a value of type UINTN.
+
+ This function outputs a value of type UINTN by interpreting the contents of
+ the Unicode string specified by String as a decimal number. The format of the
+ input Unicode string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before
+ [decimal digits]. The running zero in the beginning of [decimal digits] will
+ be ignored. Then, the function stops at the first character that is a not a
+ valid decimal character or a Null-terminator, whichever one comes first.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If String has no valid decimal digits in the above format, then 0 is stored
+ at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINTN, then
+ MAX_UINTN is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ decimal digits right after the optional pad spaces, the value of String is
+ stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINTN.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrDecimalToUintnS (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT UINTN *Data
+ )
+{
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((StrnLenS (String, RSIZE_MAX + 1) <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == L' ') || (*String == L'\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == L'0') {
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalIsDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINTN, then MAX_UINTN is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > ((MAX_UINTN - (*String - L'0')) / 10)) {
+ *Data = MAX_UINTN;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = *Data * 10 + (*String - L'0');
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode decimal string to a value of type UINT64.
+
+ This function outputs a value of type UINT64 by interpreting the contents of
+ the Unicode string specified by String as a decimal number. The format of the
+ input Unicode string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before
+ [decimal digits]. The running zero in the beginning of [decimal digits] will
+ be ignored. Then, the function stops at the first character that is a not a
+ valid decimal character or a Null-terminator, whichever one comes first.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If String has no valid decimal digits in the above format, then 0 is stored
+ at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINT64, then
+ MAX_UINT64 is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ decimal digits right after the optional pad spaces, the value of String is
+ stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINT64.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrDecimalToUint64S (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT UINT64 *Data
+ )
+{
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((StrnLenS (String, RSIZE_MAX + 1) <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == L' ') || (*String == L'\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == L'0') {
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalIsDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINT64, then MAX_UINT64 is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > DivU64x32 (MAX_UINT64 - (*String - L'0'), 10)) {
+ *Data = MAX_UINT64;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = MultU64x32 (*Data, 10) + (*String - L'0');
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode hexadecimal string to a value of type
+ UINTN.
+
+ This function outputs a value of type UINTN by interpreting the contents of
+ the Unicode string specified by String as a hexadecimal number. The format of
+ the input Unicode string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix.
+ If "x" appears in the input string, it must be prefixed with at least one 0.
+ The function will ignore the pad space, which includes spaces or tab
+ characters, before [zeros], [x] or [hexadecimal digit]. The running zero
+ before [x] or [hexadecimal digit] will be ignored. Then, the decoding starts
+ after [x] or the first valid hexadecimal digit. Then, the function stops at
+ the first character that is a not a valid hexadecimal character or NULL,
+ whichever one comes first.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If String has no valid hexadecimal digits in the above format, then 0 is
+ stored at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINTN, then
+ MAX_UINTN is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ hexadecimal digits right after the optional pad spaces, the value of String
+ is stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINTN.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrHexToUintnS (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT UINTN *Data
+ )
+{
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((StrnLenS (String, RSIZE_MAX + 1) <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == L' ') || (*String == L'\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == L'0') {
+ String++;
+ }
+
+ if (CharToUpper (*String) == L'X') {
+ if (*(String - 1) != L'0') {
+ *Data = 0;
+ return RETURN_SUCCESS;
+ }
+ //
+ // Skip the 'X'
+ //
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalIsHexaDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINTN, then MAX_UINTN is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > ((MAX_UINTN - InternalHexCharToUintn (*String)) >> 4)) {
+ *Data = MAX_UINTN;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = (*Data << 4) + InternalHexCharToUintn (*String);
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode hexadecimal string to a value of type
+ UINT64.
+
+ This function outputs a value of type UINT64 by interpreting the contents of
+ the Unicode string specified by String as a hexadecimal number. The format of
+ the input Unicode string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix.
+ If "x" appears in the input string, it must be prefixed with at least one 0.
+ The function will ignore the pad space, which includes spaces or tab
+ characters, before [zeros], [x] or [hexadecimal digit]. The running zero
+ before [x] or [hexadecimal digit] will be ignored. Then, the decoding starts
+ after [x] or the first valid hexadecimal digit. Then, the function stops at
+ the first character that is a not a valid hexadecimal character or NULL,
+ whichever one comes first.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If String has no valid hexadecimal digits in the above format, then 0 is
+ stored at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINT64, then
+ MAX_UINT64 is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ hexadecimal digits right after the optional pad spaces, the value of String
+ is stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINT64.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrHexToUint64S (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT UINT64 *Data
+ )
+{
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((StrnLenS (String, RSIZE_MAX + 1) <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == L' ') || (*String == L'\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == L'0') {
+ String++;
+ }
+
+ if (CharToUpper (*String) == L'X') {
+ if (*(String - 1) != L'0') {
+ *Data = 0;
+ return RETURN_SUCCESS;
+ }
+ //
+ // Skip the 'X'
+ //
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalIsHexaDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINT64, then MAX_UINT64 is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > RShiftU64 (MAX_UINT64 - InternalHexCharToUintn (*String), 4)) {
+ *Data = MAX_UINT64;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = LShiftU64 (*Data, 4) + InternalHexCharToUintn (*String);
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode string to IPv6 address and prefix length.
+
+ This function outputs a value of type IPv6_ADDRESS and may output a value
+ of type UINT8 by interpreting the contents of the Unicode string specified
+ by String. The format of the input Unicode string String is as follows:
+
+ X:X:X:X:X:X:X:X[/P]
+
+ X contains one to four hexadecimal digit characters in the range [0-9], [a-f] and
+ [A-F]. X is converted to a value of type UINT16, whose low byte is stored in low
+ memory address and high byte is stored in high memory address. P contains decimal
+ digit characters in the range [0-9]. The running zero in the beginning of P will
+ be ignored. /P is optional.
+
+ When /P is not in the String, the function stops at the first character that is
+ not a valid hexadecimal digit character after eight X's are converted.
+
+ When /P is in the String, the function stops at the first character that is not
+ a valid decimal digit character after P is converted.
+
+ "::" can be used to compress one or more groups of X when X contains only 0.
+ The "::" can only appear once in the String.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If EndPointer is not NULL and Address is translated from String, a pointer
+ to the character that stopped the scan is stored at the location pointed to
+ by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Address Pointer to the converted IPv6 address.
+ @param PrefixLength Pointer to the converted IPv6 address prefix
+ length. MAX_UINT8 is returned when /P is
+ not in the String.
+
+ @retval RETURN_SUCCESS Address is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If X contains more than four hexadecimal
+ digit characters.
+ If String contains "::" and number of X
+ is not less than 8.
+ If P starts with character that is not a
+ valid decimal digit character.
+ If the decimal number converted from P
+ exceeds 128.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrToIpv6Address (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT IPv6_ADDRESS *Address,
+ OUT UINT8 *PrefixLength OPTIONAL
+ )
+{
+ RETURN_STATUS Status;
+ UINTN AddressIndex;
+ UINTN Uintn;
+ IPv6_ADDRESS LocalAddress;
+ UINT8 LocalPrefixLength;
+ CONST CHAR16 *Pointer;
+ CHAR16 *End;
+ UINTN CompressStart;
+ BOOLEAN ExpectPrefix;
+
+ LocalPrefixLength = MAX_UINT8;
+ CompressStart = ARRAY_SIZE (Address->Addr);
+ ExpectPrefix = FALSE;
+
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. None of String or Guid shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Address != NULL), RETURN_INVALID_PARAMETER);
+
+ for (Pointer = String, AddressIndex = 0; AddressIndex < ARRAY_SIZE (Address->Addr) + 1;) {
+ if (!InternalIsHexaDecimalDigitCharacter (*Pointer)) {
+ if (*Pointer != L':') {
+ //
+ // ":" or "/" should be followed by digit characters.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+
+ //
+ // Meet second ":" after previous ":" or "/"
+ // or meet first ":" in the beginning of String.
+ //
+ if (ExpectPrefix) {
+ //
+ // ":" shall not be after "/"
+ //
+ return RETURN_UNSUPPORTED;
+ }
+
+ if (CompressStart != ARRAY_SIZE (Address->Addr) || AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // "::" can only appear once.
+ // "::" can only appear when address is not full length.
+ //
+ return RETURN_UNSUPPORTED;
+ } else {
+ //
+ // Remember the start of zero compressing.
+ //
+ CompressStart = AddressIndex;
+ Pointer++;
+
+ if (CompressStart == 0) {
+ if (*Pointer != L':') {
+ //
+ // Single ":" shall not be in the beginning of String.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ Pointer++;
+ }
+ }
+ }
+
+ if (!InternalIsHexaDecimalDigitCharacter (*Pointer)) {
+ if (*Pointer == L'/') {
+ //
+ // Might be optional "/P" after "::".
+ //
+ if (CompressStart != AddressIndex) {
+ return RETURN_UNSUPPORTED;
+ }
+ } else {
+ break;
+ }
+ } else {
+ if (!ExpectPrefix) {
+ //
+ // Get X.
+ //
+ Status = StrHexToUintnS (Pointer, &End, &Uintn);
+ if (RETURN_ERROR (Status) || End - Pointer > 4) {
+ //
+ // Number of hexadecimal digit characters is no more than 4.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ Pointer = End;
+ //
+ // Uintn won't exceed MAX_UINT16 if number of hexadecimal digit characters is no more than 4.
+ //
+ ASSERT (AddressIndex + 1 < ARRAY_SIZE (Address->Addr));
+ LocalAddress.Addr[AddressIndex] = (UINT8) ((UINT16) Uintn >> 8);
+ LocalAddress.Addr[AddressIndex + 1] = (UINT8) Uintn;
+ AddressIndex += 2;
+ } else {
+ //
+ // Get P, then exit the loop.
+ //
+ Status = StrDecimalToUintnS (Pointer, &End, &Uintn);
+ if (RETURN_ERROR (Status) || End == Pointer || Uintn > 128) {
+ //
+ // Prefix length should not exceed 128.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ LocalPrefixLength = (UINT8) Uintn;
+ Pointer = End;
+ break;
+ }
+ }
+
+ //
+ // Skip ':' or "/"
+ //
+ if (*Pointer == L'/') {
+ ExpectPrefix = TRUE;
+ } else if (*Pointer == L':') {
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // Meet additional ":" after all 8 16-bit address
+ //
+ break;
+ }
+ } else {
+ //
+ // Meet other character that is not "/" or ":" after all 8 16-bit address
+ //
+ break;
+ }
+ Pointer++;
+ }
+
+ if ((AddressIndex == ARRAY_SIZE (Address->Addr) && CompressStart != ARRAY_SIZE (Address->Addr)) ||
+ (AddressIndex != ARRAY_SIZE (Address->Addr) && CompressStart == ARRAY_SIZE (Address->Addr))
+ ) {
+ //
+ // Full length of address shall not have compressing zeros.
+ // Non-full length of address shall have compressing zeros.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ CopyMem (&Address->Addr[0], &LocalAddress.Addr[0], CompressStart);
+ ZeroMem (&Address->Addr[CompressStart], ARRAY_SIZE (Address->Addr) - AddressIndex);
+ if (AddressIndex > CompressStart) {
+ CopyMem (
+ &Address->Addr[CompressStart + ARRAY_SIZE (Address->Addr) - AddressIndex],
+ &LocalAddress.Addr[CompressStart],
+ AddressIndex - CompressStart
+ );
+ }
+
+ if (PrefixLength != NULL) {
+ *PrefixLength = LocalPrefixLength;
+ }
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR16 *) Pointer;
+ }
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode string to IPv4 address and prefix length.
+
+ This function outputs a value of type IPv4_ADDRESS and may output a value
+ of type UINT8 by interpreting the contents of the Unicode string specified
+ by String. The format of the input Unicode string String is as follows:
+
+ D.D.D.D[/P]
+
+ D and P are decimal digit characters in the range [0-9]. The running zero in
+ the beginning of D and P will be ignored. /P is optional.
+
+ When /P is not in the String, the function stops at the first character that is
+ not a valid decimal digit character after four D's are converted.
+
+ When /P is in the String, the function stops at the first character that is not
+ a valid decimal digit character after P is converted.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ If EndPointer is not NULL and Address is translated from String, a pointer
+ to the character that stopped the scan is stored at the location pointed to
+ by EndPointer.
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Address Pointer to the converted IPv4 address.
+ @param PrefixLength Pointer to the converted IPv4 address prefix
+ length. MAX_UINT8 is returned when /P is
+ not in the String.
+
+ @retval RETURN_SUCCESS Address is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If String is not in the correct format.
+ If any decimal number converted from D
+ exceeds 255.
+ If the decimal number converted from P
+ exceeds 32.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrToIpv4Address (
+ IN CONST CHAR16 *String,
+ OUT CHAR16 **EndPointer, OPTIONAL
+ OUT IPv4_ADDRESS *Address,
+ OUT UINT8 *PrefixLength OPTIONAL
+ )
+{
+ RETURN_STATUS Status;
+ UINTN AddressIndex;
+ UINTN Uintn;
+ IPv4_ADDRESS LocalAddress;
+ UINT8 LocalPrefixLength;
+ CHAR16 *Pointer;
+
+ LocalPrefixLength = MAX_UINT8;
+
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. None of String or Guid shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Address != NULL), RETURN_INVALID_PARAMETER);
+
+ for (Pointer = (CHAR16 *) String, AddressIndex = 0; AddressIndex < ARRAY_SIZE (Address->Addr) + 1;) {
+ if (!InternalIsDecimalDigitCharacter (*Pointer)) {
+ //
+ // D or P contains invalid characters.
+ //
+ break;
+ }
+
+ //
+ // Get D or P.
+ //
+ Status = StrDecimalToUintnS ((CONST CHAR16 *) Pointer, &Pointer, &Uintn);
+ if (RETURN_ERROR (Status)) {
+ return RETURN_UNSUPPORTED;
+ }
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // It's P.
+ //
+ if (Uintn > 32) {
+ return RETURN_UNSUPPORTED;
+ }
+ LocalPrefixLength = (UINT8) Uintn;
+ } else {
+ //
+ // It's D.
+ //
+ if (Uintn > MAX_UINT8) {
+ return RETURN_UNSUPPORTED;
+ }
+ LocalAddress.Addr[AddressIndex] = (UINT8) Uintn;
+ AddressIndex++;
+ }
+
+ //
+ // Check the '.' or '/', depending on the AddressIndex.
+ //
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ if (*Pointer == L'/') {
+ //
+ // '/P' is in the String.
+ // Skip "/" and get P in next loop.
+ //
+ Pointer++;
+ } else {
+ //
+ // '/P' is not in the String.
+ //
+ break;
+ }
+ } else if (AddressIndex < ARRAY_SIZE (Address->Addr)) {
+ if (*Pointer == L'.') {
+ //
+ // D should be followed by '.'
+ //
+ Pointer++;
+ } else {
+ return RETURN_UNSUPPORTED;
+ }
+ }
+ }
+
+ if (AddressIndex < ARRAY_SIZE (Address->Addr)) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ CopyMem (Address, &LocalAddress, sizeof (*Address));
+ if (PrefixLength != NULL) {
+ *PrefixLength = LocalPrefixLength;
+ }
+ if (EndPointer != NULL) {
+ *EndPointer = Pointer;
+ }
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode GUID string to a value of type
+ EFI_GUID.
+
+ This function outputs a GUID value by interpreting the contents of
+ the Unicode string specified by String. The format of the input
+ Unicode string String consists of 36 characters, as follows:
+
+ aabbccdd-eeff-gghh-iijj-kkllmmnnoopp
+
+ The pairs aa - pp are two characters in the range [0-9], [a-f] and
+ [A-F], with each pair representing a single byte hexadecimal value.
+
+ The mapping between String and the EFI_GUID structure is as follows:
+ aa Data1[24:31]
+ bb Data1[16:23]
+ cc Data1[8:15]
+ dd Data1[0:7]
+ ee Data2[8:15]
+ ff Data2[0:7]
+ gg Data3[8:15]
+ hh Data3[0:7]
+ ii Data4[0:7]
+ jj Data4[8:15]
+ kk Data4[16:23]
+ ll Data4[24:31]
+ mm Data4[32:39]
+ nn Data4[40:47]
+ oo Data4[48:55]
+ pp Data4[56:63]
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param Guid Pointer to the converted GUID.
+
+ @retval RETURN_SUCCESS Guid is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If String is not as the above format.
+
+**/
+RETURN_STATUS
+EFIAPI
+StrToGuid (
+ IN CONST CHAR16 *String,
+ OUT GUID *Guid
+ )
+{
+ RETURN_STATUS Status;
+ GUID LocalGuid;
+
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. None of String or Guid shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Guid != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // Get aabbccdd in big-endian.
+ //
+ Status = StrHexToBytes (String, 2 * sizeof (LocalGuid.Data1), (UINT8 *) &LocalGuid.Data1, sizeof (LocalGuid.Data1));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data1)] != L'-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data1 = SwapBytes32 (LocalGuid.Data1);
+ String += 2 * sizeof (LocalGuid.Data1) + 1;
+
+ //
+ // Get eeff in big-endian.
+ //
+ Status = StrHexToBytes (String, 2 * sizeof (LocalGuid.Data2), (UINT8 *) &LocalGuid.Data2, sizeof (LocalGuid.Data2));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data2)] != L'-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data2 = SwapBytes16 (LocalGuid.Data2);
+ String += 2 * sizeof (LocalGuid.Data2) + 1;
+
+ //
+ // Get gghh in big-endian.
+ //
+ Status = StrHexToBytes (String, 2 * sizeof (LocalGuid.Data3), (UINT8 *) &LocalGuid.Data3, sizeof (LocalGuid.Data3));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data3)] != L'-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data3 = SwapBytes16 (LocalGuid.Data3);
+ String += 2 * sizeof (LocalGuid.Data3) + 1;
+
+ //
+ // Get iijj.
+ //
+ Status = StrHexToBytes (String, 2 * 2, &LocalGuid.Data4[0], 2);
+ if (RETURN_ERROR (Status) || String[2 * 2] != L'-') {
+ return RETURN_UNSUPPORTED;
+ }
+ String += 2 * 2 + 1;
+
+ //
+ // Get kkllmmnnoopp.
+ //
+ Status = StrHexToBytes (String, 2 * 6, &LocalGuid.Data4[2], 6);
+ if (RETURN_ERROR (Status)) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ CopyGuid (Guid, &LocalGuid);
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode hexadecimal string to a byte array.
+
+ This function outputs a byte array by interpreting the contents of
+ the Unicode string specified by String in hexadecimal format. The format of
+ the input Unicode string String is:
+
+ [XX]*
+
+ X is a hexadecimal digit character in the range [0-9], [a-f] and [A-F].
+ The function decodes every two hexadecimal digit characters as one byte. The
+ decoding stops after Length of characters and outputs Buffer containing
+ (Length / 2) bytes.
+
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+
+ @param String Pointer to a Null-terminated Unicode string.
+ @param Length The number of Unicode characters to decode.
+ @param Buffer Pointer to the converted bytes array.
+ @param MaxBufferSize The maximum size of Buffer.
+
+ @retval RETURN_SUCCESS Buffer is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If Length is not multiple of 2.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and Length is greater than
+ PcdMaximumUnicodeStringLength.
+ @retval RETURN_UNSUPPORTED If Length of characters from String contain
+ a character that is not valid hexadecimal
+ digit characters, or a Null-terminator.
+ @retval RETURN_BUFFER_TOO_SMALL If MaxBufferSize is less than (Length / 2).
+**/
+RETURN_STATUS
+EFIAPI
+StrHexToBytes (
+ IN CONST CHAR16 *String,
+ IN UINTN Length,
+ OUT UINT8 *Buffer,
+ IN UINTN MaxBufferSize
+ )
+{
+ UINTN Index;
+
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ //
+ // 1. None of String or Buffer shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Buffer != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Length shall not be greater than RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. Length shall not be odd.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (((Length & BIT0) == 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. MaxBufferSize shall equal to or greater than Length / 2.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((MaxBufferSize >= Length / 2), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. String shall not contains invalid hexadecimal digits.
+ //
+ for (Index = 0; Index < Length; Index++) {
+ if (!InternalIsHexaDecimalDigitCharacter (String[Index])) {
+ break;
+ }
+ }
+ if (Index != Length) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ //
+ // Convert the hex string to bytes.
+ //
+ for(Index = 0; Index < Length; Index++) {
+
+ //
+ // For even characters, write the upper nibble for each buffer byte,
+ // and for even characters, the lower nibble.
+ //
+ if ((Index & BIT0) == 0) {
+ Buffer[Index / 2] = (UINT8) InternalHexCharToUintn (String[Index]) << 4;
+ } else {
+ Buffer[Index / 2] |= (UINT8) InternalHexCharToUintn (String[Index]);
+ }
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Returns the length of a Null-terminated Ascii string.
+
+ This function is similar as strlen_s defined in C11.
+
+ @param String A pointer to a Null-terminated Ascii string.
+ @param MaxSize The maximum number of Destination Ascii
+ char, including terminating null char.
+
+ @retval 0 If String is NULL.
+ @retval MaxSize If there is no null character in the first MaxSize characters of String.
+ @return The number of characters that percede the terminating null character.
+
+**/
+UINTN
+EFIAPI
+AsciiStrnLenS (
+ IN CONST CHAR8 *String,
+ IN UINTN MaxSize
+ )
+{
+ UINTN Length;
+
+ //
+ // If String is a null pointer or MaxSize is 0, then the AsciiStrnLenS function returns zero.
+ //
+ if ((String == NULL) || (MaxSize == 0)) {
+ return 0;
+ }
+
+ //
+ // Otherwise, the AsciiStrnLenS function returns the number of characters that precede the
+ // terminating null character. If there is no null character in the first MaxSize characters of
+ // String then AsciiStrnLenS returns MaxSize. At most the first MaxSize characters of String shall
+ // be accessed by AsciiStrnLenS.
+ //
+ Length = 0;
+ while (String[Length] != 0) {
+ if (Length >= MaxSize - 1) {
+ return MaxSize;
+ }
+ Length++;
+ }
+ return Length;
+}
+
+/**
+ Returns the size of a Null-terminated Ascii string in bytes, including the
+ Null terminator.
+
+ This function returns the size of the Null-terminated Ascii string specified
+ by String in bytes, including the Null terminator.
+
+ @param String A pointer to a Null-terminated Ascii string.
+ @param MaxSize The maximum number of Destination Ascii
+ char, including the Null terminator.
+
+ @retval 0 If String is NULL.
+ @retval (sizeof (CHAR8) * (MaxSize + 1))
+ If there is no Null terminator in the first MaxSize characters of
+ String.
+ @return The size of the Null-terminated Ascii string in bytes, including the
+ Null terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiStrnSizeS (
+ IN CONST CHAR8 *String,
+ IN UINTN MaxSize
+ )
+{
+ //
+ // If String is a null pointer, then the AsciiStrnSizeS function returns
+ // zero.
+ //
+ if (String == NULL) {
+ return 0;
+ }
+
+ //
+ // Otherwise, the AsciiStrnSizeS function returns the size of the
+ // Null-terminated Ascii string in bytes, including the Null terminator. If
+ // there is no Null terminator in the first MaxSize characters of String,
+ // then AsciiStrnSizeS returns (sizeof (CHAR8) * (MaxSize + 1)) to keep a
+ // consistent map with the AsciiStrnLenS function.
+ //
+ return (AsciiStrnLenS (String, MaxSize) + 1) * sizeof (*String);
+}
+
+/**
+ Copies the string pointed to by Source (including the terminating null char)
+ to the array pointed to by Destination.
+
+ This function is similar as strcpy_s defined in C11.
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Ascii string.
+ @param DestMax The maximum number of Destination Ascii
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Ascii string.
+
+ @retval RETURN_SUCCESS String is copied.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrCpyS (
+ OUT CHAR8 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR8 *Source
+ )
+{
+ UINTN SourceLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. DestMax shall be greater than AsciiStrnLenS(Source, DestMax).
+ //
+ SourceLen = AsciiStrnLenS (Source, DestMax);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoAsciiStrOverlap (Destination, DestMax, (CHAR8 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The AsciiStrCpyS function copies the string pointed to by Source (including the terminating
+ // null character) into the array pointed to by Destination.
+ //
+ while (*Source != 0) {
+ *(Destination++) = *(Source++);
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Copies not more than Length successive char from the string pointed to by
+ Source to the array pointed to by Destination. If no null char is copied from
+ Source, then Destination[Length] is always set to null.
+
+ This function is similar as strncpy_s defined in C11.
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Ascii string.
+ @param DestMax The maximum number of Destination Ascii
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Ascii string.
+ @param Length The maximum number of Ascii characters to copy.
+
+ @retval RETURN_SUCCESS String is copied.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than
+ MIN(StrLen(Source), Length).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrnCpyS (
+ OUT CHAR8 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR8 *Source,
+ IN UINTN Length
+ )
+{
+ UINTN SourceLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither DestMax nor Length shall be greater than ASCII_RSIZE_MAX
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. If Length is not less than DestMax, then DestMax shall be greater than AsciiStrnLenS(Source, DestMax).
+ //
+ SourceLen = AsciiStrnLenS (Source, MIN (DestMax, Length));
+ if (Length >= DestMax) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoAsciiStrOverlap (Destination, DestMax, (CHAR8 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The AsciiStrnCpyS function copies not more than Length successive characters (characters that
+ // follow a null character are not copied) from the array pointed to by Source to the array
+ // pointed to by Destination. If no null character was copied from Source, then Destination[Length] is set to a null
+ // character.
+ //
+ while ((SourceLen > 0) && (*Source != 0)) {
+ *(Destination++) = *(Source++);
+ SourceLen--;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Appends a copy of the string pointed to by Source (including the terminating
+ null char) to the end of the string pointed to by Destination.
+
+ This function is similar as strcat_s defined in C11.
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Ascii string.
+ @param DestMax The maximum number of Destination Ascii
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Ascii string.
+
+ @retval RETURN_SUCCESS String is appended.
+ @retval RETURN_BAD_BUFFER_SIZE If DestMax is NOT greater than
+ StrLen(Destination).
+ @retval RETURN_BUFFER_TOO_SMALL If (DestMax - StrLen(Destination)) is NOT
+ greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrCatS (
+ IN OUT CHAR8 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR8 *Source
+ )
+{
+ UINTN DestLen;
+ UINTN CopyLen;
+ UINTN SourceLen;
+
+ //
+ // Let CopyLen denote the value DestMax - AsciiStrnLenS(Destination, DestMax) upon entry to AsciiStrCatS.
+ //
+ DestLen = AsciiStrnLenS (Destination, DestMax);
+ CopyLen = DestMax - DestLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. CopyLen shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen != 0), RETURN_BAD_BUFFER_SIZE);
+
+ //
+ // 5. CopyLen shall be greater than AsciiStrnLenS(Source, CopyLen).
+ //
+ SourceLen = AsciiStrnLenS (Source, CopyLen);
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 6. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoAsciiStrOverlap (Destination, DestMax, (CHAR8 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The AsciiStrCatS function appends a copy of the string pointed to by Source (including the
+ // terminating null character) to the end of the string pointed to by Destination. The initial character
+ // from Source overwrites the null character at the end of Destination.
+ //
+ Destination = Destination + DestLen;
+ while (*Source != 0) {
+ *(Destination++) = *(Source++);
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Appends not more than Length successive char from the string pointed to by
+ Source to the end of the string pointed to by Destination. If no null char is
+ copied from Source, then Destination[StrLen(Destination) + Length] is always
+ set to null.
+
+ This function is similar as strncat_s defined in C11.
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Destination A pointer to a Null-terminated Ascii string.
+ @param DestMax The maximum number of Destination Ascii
+ char, including terminating null char.
+ @param Source A pointer to a Null-terminated Ascii string.
+ @param Length The maximum number of Ascii characters to copy.
+
+ @retval RETURN_SUCCESS String is appended.
+ @retval RETURN_BAD_BUFFER_SIZE If DestMax is NOT greater than
+ StrLen(Destination).
+ @retval RETURN_BUFFER_TOO_SMALL If (DestMax - StrLen(Destination)) is NOT
+ greater than MIN(StrLen(Source), Length).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrnCatS (
+ IN OUT CHAR8 *Destination,
+ IN UINTN DestMax,
+ IN CONST CHAR8 *Source,
+ IN UINTN Length
+ )
+{
+ UINTN DestLen;
+ UINTN CopyLen;
+ UINTN SourceLen;
+
+ //
+ // Let CopyLen denote the value DestMax - AsciiStrnLenS(Destination, DestMax) upon entry to AsciiStrnCatS.
+ //
+ DestLen = AsciiStrnLenS (Destination, DestMax);
+ CopyLen = DestMax - DestLen;
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither DestMax nor Length shall be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. CopyLen shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen != 0), RETURN_BAD_BUFFER_SIZE);
+
+ //
+ // 5. If Length is not less than CopyLen, then CopyLen shall be greater than AsciiStrnLenS(Source, CopyLen).
+ //
+ SourceLen = AsciiStrnLenS (Source, MIN (CopyLen, Length));
+ if (Length >= CopyLen) {
+ SAFE_STRING_CONSTRAINT_CHECK ((CopyLen > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 6. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (InternalSafeStringNoAsciiStrOverlap (Destination, DestMax, (CHAR8 *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // The AsciiStrnCatS function appends not more than Length successive characters (characters
+ // that follow a null character are not copied) from the array pointed to by Source to the end of
+ // the string pointed to by Destination. The initial character from Source overwrites the null character at
+ // the end of Destination. If no null character was copied from Source, then Destination[DestMax-CopyLen+Length] is set to
+ // a null character.
+ //
+ Destination = Destination + DestLen;
+ while ((SourceLen > 0) && (*Source != 0)) {
+ *(Destination++) = *(Source++);
+ SourceLen--;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Ascii decimal string to a value of type UINTN.
+
+ This function outputs a value of type UINTN by interpreting the contents of
+ the Ascii string specified by String as a decimal number. The format of the
+ input Ascii string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before
+ [decimal digits]. The running zero in the beginning of [decimal digits] will
+ be ignored. Then, the function stops at the first character that is a not a
+ valid decimal character or a Null-terminator, whichever one comes first.
+
+ If String has no valid decimal digits in the above format, then 0 is stored
+ at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINTN, then
+ MAX_UINTN is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ decimal digits right after the optional pad spaces, the value of String is
+ stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Ascii string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than
+ PcdMaximumAsciiStringLength Ascii
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINTN.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrDecimalToUintnS (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT UINTN *Data
+ )
+{
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((AsciiStrnLenS (String, ASCII_RSIZE_MAX + 1) <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == ' ') || (*String == '\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == '0') {
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalAsciiIsDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINTN, then MAX_UINTN is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > ((MAX_UINTN - (*String - '0')) / 10)) {
+ *Data = MAX_UINTN;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = *Data * 10 + (*String - '0');
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Ascii decimal string to a value of type UINT64.
+
+ This function outputs a value of type UINT64 by interpreting the contents of
+ the Ascii string specified by String as a decimal number. The format of the
+ input Ascii string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before
+ [decimal digits]. The running zero in the beginning of [decimal digits] will
+ be ignored. Then, the function stops at the first character that is a not a
+ valid decimal character or a Null-terminator, whichever one comes first.
+
+ If String has no valid decimal digits in the above format, then 0 is stored
+ at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINT64, then
+ MAX_UINT64 is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ decimal digits right after the optional pad spaces, the value of String is
+ stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Ascii string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than
+ PcdMaximumAsciiStringLength Ascii
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINT64.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrDecimalToUint64S (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT UINT64 *Data
+ )
+{
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((AsciiStrnLenS (String, ASCII_RSIZE_MAX + 1) <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == ' ') || (*String == '\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == '0') {
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalAsciiIsDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINT64, then MAX_UINT64 is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > DivU64x32 (MAX_UINT64 - (*String - '0'), 10)) {
+ *Data = MAX_UINT64;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = MultU64x32 (*Data, 10) + (*String - '0');
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Ascii hexadecimal string to a value of type UINTN.
+
+ This function outputs a value of type UINTN by interpreting the contents of
+ the Ascii string specified by String as a hexadecimal number. The format of
+ the input Ascii string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix. If
+ "x" appears in the input string, it must be prefixed with at least one 0. The
+ function will ignore the pad space, which includes spaces or tab characters,
+ before [zeros], [x] or [hexadecimal digits]. The running zero before [x] or
+ [hexadecimal digits] will be ignored. Then, the decoding starts after [x] or
+ the first valid hexadecimal digit. Then, the function stops at the first
+ character that is a not a valid hexadecimal character or Null-terminator,
+ whichever on comes first.
+
+ If String has no valid hexadecimal digits in the above format, then 0 is
+ stored at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINTN, then
+ MAX_UINTN is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ hexadecimal digits right after the optional pad spaces, the value of String
+ is stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Ascii string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than
+ PcdMaximumAsciiStringLength Ascii
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINTN.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrHexToUintnS (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT UINTN *Data
+ )
+{
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((AsciiStrnLenS (String, ASCII_RSIZE_MAX + 1) <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == ' ') || (*String == '\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == '0') {
+ String++;
+ }
+
+ if (AsciiCharToUpper (*String) == 'X') {
+ if (*(String - 1) != '0') {
+ *Data = 0;
+ return RETURN_SUCCESS;
+ }
+ //
+ // Skip the 'X'
+ //
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalAsciiIsHexaDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINTN, then MAX_UINTN is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > ((MAX_UINTN - InternalAsciiHexCharToUintn (*String)) >> 4)) {
+ *Data = MAX_UINTN;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = (*Data << 4) + InternalAsciiHexCharToUintn (*String);
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Ascii hexadecimal string to a value of type UINT64.
+
+ This function outputs a value of type UINT64 by interpreting the contents of
+ the Ascii string specified by String as a hexadecimal number. The format of
+ the input Ascii string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix. If
+ "x" appears in the input string, it must be prefixed with at least one 0. The
+ function will ignore the pad space, which includes spaces or tab characters,
+ before [zeros], [x] or [hexadecimal digits]. The running zero before [x] or
+ [hexadecimal digits] will be ignored. Then, the decoding starts after [x] or
+ the first valid hexadecimal digit. Then, the function stops at the first
+ character that is a not a valid hexadecimal character or Null-terminator,
+ whichever on comes first.
+
+ If String has no valid hexadecimal digits in the above format, then 0 is
+ stored at the location pointed to by Data.
+ If the number represented by String exceeds the range defined by UINT64, then
+ MAX_UINT64 is stored at the location pointed to by Data.
+
+ If EndPointer is not NULL, a pointer to the character that stopped the scan
+ is stored at the location pointed to by EndPointer. If String has no valid
+ hexadecimal digits right after the optional pad spaces, the value of String
+ is stored at the location pointed to by EndPointer.
+
+ @param String Pointer to a Null-terminated Ascii string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Data Pointer to the converted value.
+
+ @retval RETURN_SUCCESS Value is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than
+ PcdMaximumAsciiStringLength Ascii
+ characters, not including the
+ Null-terminator.
+ @retval RETURN_UNSUPPORTED If the number represented by String exceeds
+ the range defined by UINT64.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrHexToUint64S (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT UINT64 *Data
+ )
+{
+ //
+ // 1. Neither String nor Data shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Data != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. The length of String shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((AsciiStrnLenS (String, ASCII_RSIZE_MAX + 1) <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+
+ //
+ // Ignore the pad spaces (space or tab)
+ //
+ while ((*String == ' ') || (*String == '\t')) {
+ String++;
+ }
+
+ //
+ // Ignore leading Zeros after the spaces
+ //
+ while (*String == '0') {
+ String++;
+ }
+
+ if (AsciiCharToUpper (*String) == 'X') {
+ if (*(String - 1) != '0') {
+ *Data = 0;
+ return RETURN_SUCCESS;
+ }
+ //
+ // Skip the 'X'
+ //
+ String++;
+ }
+
+ *Data = 0;
+
+ while (InternalAsciiIsHexaDecimalDigitCharacter (*String)) {
+ //
+ // If the number represented by String overflows according to the range
+ // defined by UINT64, then MAX_UINT64 is stored in *Data and
+ // RETURN_UNSUPPORTED is returned.
+ //
+ if (*Data > RShiftU64 (MAX_UINT64 - InternalAsciiHexCharToUintn (*String), 4)) {
+ *Data = MAX_UINT64;
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_UNSUPPORTED;
+ }
+
+ *Data = LShiftU64 (*Data, 4) + InternalAsciiHexCharToUintn (*String);
+ String++;
+ }
+
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) String;
+ }
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated Unicode string to a Null-terminated
+ ASCII string.
+
+ This function is similar to AsciiStrCpyS.
+
+ This function converts the content of the Unicode string Source
+ to the ASCII string Destination by copying the lower 8 bits of
+ each Unicode character. The function terminates the ASCII string
+ Destination by appending a Null-terminator character at the end.
+
+ The caller is responsible to make sure Destination points to a buffer with size
+ equal or greater than ((StrLen (Source) + 1) * sizeof (CHAR8)) in bytes.
+
+ If any Unicode characters in Source contain non-zero value in
+ the upper 8 bits, then ASSERT().
+
+ If Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Source The pointer to a Null-terminated Unicode string.
+ @param Destination The pointer to a Null-terminated ASCII string.
+ @param DestMax The maximum number of Destination Ascii
+ char, including terminating null char.
+
+ @retval RETURN_SUCCESS String is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+
+**/
+RETURN_STATUS
+EFIAPI
+UnicodeStrToAsciiStrS (
+ IN CONST CHAR16 *Source,
+ OUT CHAR8 *Destination,
+ IN UINTN DestMax
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than ASCII_RSIZE_MAX or RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. DestMax shall be greater than StrnLenS (Source, DestMax).
+ //
+ SourceLen = StrnLenS (Source, DestMax);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (!InternalSafeStringIsOverlap (Destination, DestMax, (VOID *)Source, (SourceLen + 1) * sizeof(CHAR16)), RETURN_ACCESS_DENIED);
+
+ //
+ // convert string
+ //
+ while (*Source != '\0') {
+ //
+ // If any Unicode characters in Source contain
+ // non-zero value in the upper 8 bits, then ASSERT().
+ //
+ ASSERT (*Source < 0x100);
+ *(Destination++) = (CHAR8) *(Source++);
+ }
+ *Destination = '\0';
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert not more than Length successive characters from a Null-terminated
+ Unicode string to a Null-terminated Ascii string. If no null char is copied
+ from Source, then Destination[Length] is always set to null.
+
+ This function converts not more than Length successive characters from the
+ Unicode string Source to the Ascii string Destination by copying the lower 8
+ bits of each Unicode character. The function terminates the Ascii string
+ Destination by appending a Null-terminator character at the end.
+
+ The caller is responsible to make sure Destination points to a buffer with
+ size not smaller than ((MIN(StrLen(Source), Length) + 1) * sizeof (CHAR8))
+ in bytes.
+
+ If any Unicode characters in Source contain non-zero value in the upper 8
+ bits, then ASSERT().
+ If Source is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then Destination and DestinationLength are
+ unmodified.
+
+ @param Source The pointer to a Null-terminated Unicode string.
+ @param Length The maximum number of Unicode characters to
+ convert.
+ @param Destination The pointer to a Null-terminated Ascii string.
+ @param DestMax The maximum number of Destination Ascii char,
+ including terminating null char.
+ @param DestinationLength The number of Unicode characters converted.
+
+ @retval RETURN_SUCCESS String is converted.
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If DestinationLength is NULL.
+ If PcdMaximumAsciiStringLength is not zero,
+ and Length or DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and Length or DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If DestMax is 0.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than
+ MIN(StrLen(Source), Length).
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+
+**/
+RETURN_STATUS
+EFIAPI
+UnicodeStrnToAsciiStrS (
+ IN CONST CHAR16 *Source,
+ IN UINTN Length,
+ OUT CHAR8 *Destination,
+ IN UINTN DestMax,
+ OUT UINTN *DestinationLength
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Source & BIT0) == 0);
+
+ //
+ // 1. None of Destination, Source or DestinationLength shall be a null
+ // pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestinationLength != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither Length nor DestMax shall be greater than ASCII_RSIZE_MAX or
+ // RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. If Length is not less than DestMax, then DestMax shall be greater than
+ // StrnLenS(Source, DestMax).
+ //
+ SourceLen = StrnLenS (Source, DestMax);
+ if (Length >= DestMax) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (!InternalSafeStringIsOverlap (Destination, DestMax, (VOID *)Source, (SourceLen + 1) * sizeof(CHAR16)), RETURN_ACCESS_DENIED);
+
+ *DestinationLength = 0;
+
+ //
+ // Convert string
+ //
+ while ((*Source != 0) && (SourceLen > 0)) {
+ //
+ // If any Unicode characters in Source contain non-zero value in the upper
+ // 8 bits, then ASSERT().
+ //
+ ASSERT (*Source < 0x100);
+ *(Destination++) = (CHAR8) *(Source++);
+ SourceLen--;
+ (*DestinationLength)++;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert one Null-terminated ASCII string to a Null-terminated
+ Unicode string.
+
+ This function is similar to StrCpyS.
+
+ This function converts the contents of the ASCII string Source to the Unicode
+ string Destination. The function terminates the Unicode string Destination by
+ appending a Null-terminator character at the end.
+
+ The caller is responsible to make sure Destination points to a buffer with size
+ equal or greater than ((AsciiStrLen (Source) + 1) * sizeof (CHAR16)) in bytes.
+
+ If Destination is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then the Destination is unmodified.
+
+ @param Source The pointer to a Null-terminated ASCII string.
+ @param Destination The pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode
+ char, including terminating null char.
+
+ @retval RETURN_SUCCESS String is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than StrLen(Source).
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If PcdMaximumUnicodeStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If PcdMaximumAsciiStringLength is not zero,
+ and DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrToUnicodeStrS (
+ IN CONST CHAR8 *Source,
+ OUT CHAR16 *Destination,
+ IN UINTN DestMax
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+
+ //
+ // 1. Neither Destination nor Source shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. DestMax shall not be greater than RSIZE_MAX or ASCII_RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. DestMax shall be greater than AsciiStrnLenS(Source, DestMax).
+ //
+ SourceLen = AsciiStrnLenS (Source, DestMax);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (!InternalSafeStringIsOverlap (Destination, DestMax * sizeof(CHAR16), (VOID *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ //
+ // Convert string
+ //
+ while (*Source != '\0') {
+ *(Destination++) = (CHAR16)(UINT8)*(Source++);
+ }
+ *Destination = '\0';
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert not more than Length successive characters from a Null-terminated
+ Ascii string to a Null-terminated Unicode string. If no null char is copied
+ from Source, then Destination[Length] is always set to null.
+
+ This function converts not more than Length successive characters from the
+ Ascii string Source to the Unicode string Destination. The function
+ terminates the Unicode string Destination by appending a Null-terminator
+ character at the end.
+
+ The caller is responsible to make sure Destination points to a buffer with
+ size not smaller than
+ ((MIN(AsciiStrLen(Source), Length) + 1) * sizeof (CHAR8)) in bytes.
+
+ If Destination is not aligned on a 16-bit boundary, then ASSERT().
+
+ If an error is returned, then Destination and DestinationLength are
+ unmodified.
+
+ @param Source The pointer to a Null-terminated Ascii string.
+ @param Length The maximum number of Ascii characters to convert.
+ @param Destination The pointer to a Null-terminated Unicode string.
+ @param DestMax The maximum number of Destination Unicode char,
+ including terminating null char.
+ @param DestinationLength The number of Ascii characters converted.
+
+ @retval RETURN_SUCCESS String is converted.
+ @retval RETURN_INVALID_PARAMETER If Destination is NULL.
+ If Source is NULL.
+ If DestinationLength is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and Length or DestMax is greater than
+ PcdMaximumUnicodeStringLength.
+ If PcdMaximumAsciiStringLength is not zero,
+ and Length or DestMax is greater than
+ PcdMaximumAsciiStringLength.
+ If DestMax is 0.
+ @retval RETURN_BUFFER_TOO_SMALL If DestMax is NOT greater than
+ MIN(AsciiStrLen(Source), Length).
+ @retval RETURN_ACCESS_DENIED If Source and Destination overlap.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrnToUnicodeStrS (
+ IN CONST CHAR8 *Source,
+ IN UINTN Length,
+ OUT CHAR16 *Destination,
+ IN UINTN DestMax,
+ OUT UINTN *DestinationLength
+ )
+{
+ UINTN SourceLen;
+
+ ASSERT (((UINTN) Destination & BIT0) == 0);
+
+ //
+ // 1. None of Destination, Source or DestinationLength shall be a null
+ // pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((Destination != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Source != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestinationLength != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Neither Length nor DestMax shall be greater than ASCII_RSIZE_MAX or
+ // RSIZE_MAX.
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. DestMax shall not equal zero.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax != 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. If Length is not less than DestMax, then DestMax shall be greater than
+ // AsciiStrnLenS(Source, DestMax).
+ //
+ SourceLen = AsciiStrnLenS (Source, DestMax);
+ if (Length >= DestMax) {
+ SAFE_STRING_CONSTRAINT_CHECK ((DestMax > SourceLen), RETURN_BUFFER_TOO_SMALL);
+ }
+
+ //
+ // 5. Copying shall not take place between objects that overlap.
+ //
+ if (SourceLen > Length) {
+ SourceLen = Length;
+ }
+ SAFE_STRING_CONSTRAINT_CHECK (!InternalSafeStringIsOverlap (Destination, DestMax * sizeof(CHAR16), (VOID *)Source, SourceLen + 1), RETURN_ACCESS_DENIED);
+
+ *DestinationLength = 0;
+
+ //
+ // Convert string
+ //
+ while ((*Source != 0) && (SourceLen > 0)) {
+ *(Destination++) = (CHAR16)(UINT8)*(Source++);
+ SourceLen--;
+ (*DestinationLength)++;
+ }
+ *Destination = 0;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated ASCII string to IPv6 address and prefix length.
+
+ This function outputs a value of type IPv6_ADDRESS and may output a value
+ of type UINT8 by interpreting the contents of the ASCII string specified
+ by String. The format of the input ASCII string String is as follows:
+
+ X:X:X:X:X:X:X:X[/P]
+
+ X contains one to four hexadecimal digit characters in the range [0-9], [a-f] and
+ [A-F]. X is converted to a value of type UINT16, whose low byte is stored in low
+ memory address and high byte is stored in high memory address. P contains decimal
+ digit characters in the range [0-9]. The running zero in the beginning of P will
+ be ignored. /P is optional.
+
+ When /P is not in the String, the function stops at the first character that is
+ not a valid hexadecimal digit character after eight X's are converted.
+
+ When /P is in the String, the function stops at the first character that is not
+ a valid decimal digit character after P is converted.
+
+ "::" can be used to compress one or more groups of X when X contains only 0.
+ The "::" can only appear once in the String.
+
+ If EndPointer is not NULL and Address is translated from String, a pointer
+ to the character that stopped the scan is stored at the location pointed to
+ by EndPointer.
+
+ @param String Pointer to a Null-terminated ASCII string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Address Pointer to the converted IPv6 address.
+ @param PrefixLength Pointer to the converted IPv6 address prefix
+ length. MAX_UINT8 is returned when /P is
+ not in the String.
+
+ @retval RETURN_SUCCESS Address is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If X contains more than four hexadecimal
+ digit characters.
+ If String contains "::" and number of X
+ is not less than 8.
+ If P starts with character that is not a
+ valid decimal digit character.
+ If the decimal number converted from P
+ exceeds 128.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrToIpv6Address (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT IPv6_ADDRESS *Address,
+ OUT UINT8 *PrefixLength OPTIONAL
+ )
+{
+ RETURN_STATUS Status;
+ UINTN AddressIndex;
+ UINTN Uintn;
+ IPv6_ADDRESS LocalAddress;
+ UINT8 LocalPrefixLength;
+ CONST CHAR8 *Pointer;
+ CHAR8 *End;
+ UINTN CompressStart;
+ BOOLEAN ExpectPrefix;
+
+ LocalPrefixLength = MAX_UINT8;
+ CompressStart = ARRAY_SIZE (Address->Addr);
+ ExpectPrefix = FALSE;
+
+ //
+ // None of String or Address shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Address != NULL), RETURN_INVALID_PARAMETER);
+
+ for (Pointer = String, AddressIndex = 0; AddressIndex < ARRAY_SIZE (Address->Addr) + 1;) {
+ if (!InternalAsciiIsHexaDecimalDigitCharacter (*Pointer)) {
+ if (*Pointer != ':') {
+ //
+ // ":" or "/" should be followed by digit characters.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+
+ //
+ // Meet second ":" after previous ":" or "/"
+ // or meet first ":" in the beginning of String.
+ //
+ if (ExpectPrefix) {
+ //
+ // ":" shall not be after "/"
+ //
+ return RETURN_UNSUPPORTED;
+ }
+
+ if (CompressStart != ARRAY_SIZE (Address->Addr) || AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // "::" can only appear once.
+ // "::" can only appear when address is not full length.
+ //
+ return RETURN_UNSUPPORTED;
+ } else {
+ //
+ // Remember the start of zero compressing.
+ //
+ CompressStart = AddressIndex;
+ Pointer++;
+
+ if (CompressStart == 0) {
+ if (*Pointer != ':') {
+ //
+ // Single ":" shall not be in the beginning of String.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ Pointer++;
+ }
+ }
+ }
+
+ if (!InternalAsciiIsHexaDecimalDigitCharacter (*Pointer)) {
+ if (*Pointer == '/') {
+ //
+ // Might be optional "/P" after "::".
+ //
+ if (CompressStart != AddressIndex) {
+ return RETURN_UNSUPPORTED;
+ }
+ } else {
+ break;
+ }
+ } else {
+ if (!ExpectPrefix) {
+ //
+ // Get X.
+ //
+ Status = AsciiStrHexToUintnS (Pointer, &End, &Uintn);
+ if (RETURN_ERROR (Status) || End - Pointer > 4) {
+ //
+ // Number of hexadecimal digit characters is no more than 4.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ Pointer = End;
+ //
+ // Uintn won't exceed MAX_UINT16 if number of hexadecimal digit characters is no more than 4.
+ //
+ ASSERT (AddressIndex + 1 < ARRAY_SIZE (Address->Addr));
+ LocalAddress.Addr[AddressIndex] = (UINT8) ((UINT16) Uintn >> 8);
+ LocalAddress.Addr[AddressIndex + 1] = (UINT8) Uintn;
+ AddressIndex += 2;
+ } else {
+ //
+ // Get P, then exit the loop.
+ //
+ Status = AsciiStrDecimalToUintnS (Pointer, &End, &Uintn);
+ if (RETURN_ERROR (Status) || End == Pointer || Uintn > 128) {
+ //
+ // Prefix length should not exceed 128.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ LocalPrefixLength = (UINT8) Uintn;
+ Pointer = End;
+ break;
+ }
+ }
+
+ //
+ // Skip ':' or "/"
+ //
+ if (*Pointer == '/') {
+ ExpectPrefix = TRUE;
+ } else if (*Pointer == ':') {
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // Meet additional ":" after all 8 16-bit address
+ //
+ break;
+ }
+ } else {
+ //
+ // Meet other character that is not "/" or ":" after all 8 16-bit address
+ //
+ break;
+ }
+ Pointer++;
+ }
+
+ if ((AddressIndex == ARRAY_SIZE (Address->Addr) && CompressStart != ARRAY_SIZE (Address->Addr)) ||
+ (AddressIndex != ARRAY_SIZE (Address->Addr) && CompressStart == ARRAY_SIZE (Address->Addr))
+ ) {
+ //
+ // Full length of address shall not have compressing zeros.
+ // Non-full length of address shall have compressing zeros.
+ //
+ return RETURN_UNSUPPORTED;
+ }
+ CopyMem (&Address->Addr[0], &LocalAddress.Addr[0], CompressStart);
+ ZeroMem (&Address->Addr[CompressStart], ARRAY_SIZE (Address->Addr) - AddressIndex);
+ if (AddressIndex > CompressStart) {
+ CopyMem (
+ &Address->Addr[CompressStart + ARRAY_SIZE (Address->Addr) - AddressIndex],
+ &LocalAddress.Addr[CompressStart],
+ AddressIndex - CompressStart
+ );
+
+ }
+
+ if (PrefixLength != NULL) {
+ *PrefixLength = LocalPrefixLength;
+ }
+ if (EndPointer != NULL) {
+ *EndPointer = (CHAR8 *) Pointer;
+ }
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated ASCII string to IPv4 address and prefix length.
+
+ This function outputs a value of type IPv4_ADDRESS and may output a value
+ of type UINT8 by interpreting the contents of the ASCII string specified
+ by String. The format of the input ASCII string String is as follows:
+
+ D.D.D.D[/P]
+
+ D and P are decimal digit characters in the range [0-9]. The running zero in
+ the beginning of D and P will be ignored. /P is optional.
+
+ When /P is not in the String, the function stops at the first character that is
+ not a valid decimal digit character after four D's are converted.
+
+ When /P is in the String, the function stops at the first character that is not
+ a valid decimal digit character after P is converted.
+
+ If EndPointer is not NULL and Address is translated from String, a pointer
+ to the character that stopped the scan is stored at the location pointed to
+ by EndPointer.
+
+ @param String Pointer to a Null-terminated ASCII string.
+ @param EndPointer Pointer to character that stops scan.
+ @param Address Pointer to the converted IPv4 address.
+ @param PrefixLength Pointer to the converted IPv4 address prefix
+ length. MAX_UINT8 is returned when /P is
+ not in the String.
+
+ @retval RETURN_SUCCESS Address is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If String is not in the correct format.
+ If any decimal number converted from D
+ exceeds 255.
+ If the decimal number converted from P
+ exceeds 32.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrToIpv4Address (
+ IN CONST CHAR8 *String,
+ OUT CHAR8 **EndPointer, OPTIONAL
+ OUT IPv4_ADDRESS *Address,
+ OUT UINT8 *PrefixLength OPTIONAL
+ )
+{
+ RETURN_STATUS Status;
+ UINTN AddressIndex;
+ UINTN Uintn;
+ IPv4_ADDRESS LocalAddress;
+ UINT8 LocalPrefixLength;
+ CHAR8 *Pointer;
+
+ LocalPrefixLength = MAX_UINT8;
+
+ //
+ // None of String or Address shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Address != NULL), RETURN_INVALID_PARAMETER);
+
+ for (Pointer = (CHAR8 *) String, AddressIndex = 0; AddressIndex < ARRAY_SIZE (Address->Addr) + 1;) {
+ if (!InternalAsciiIsDecimalDigitCharacter (*Pointer)) {
+ //
+ // D or P contains invalid characters.
+ //
+ break;
+ }
+
+ //
+ // Get D or P.
+ //
+ Status = AsciiStrDecimalToUintnS ((CONST CHAR8 *) Pointer, &Pointer, &Uintn);
+ if (RETURN_ERROR (Status)) {
+ return RETURN_UNSUPPORTED;
+ }
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ //
+ // It's P.
+ //
+ if (Uintn > 32) {
+ return RETURN_UNSUPPORTED;
+ }
+ LocalPrefixLength = (UINT8) Uintn;
+ } else {
+ //
+ // It's D.
+ //
+ if (Uintn > MAX_UINT8) {
+ return RETURN_UNSUPPORTED;
+ }
+ LocalAddress.Addr[AddressIndex] = (UINT8) Uintn;
+ AddressIndex++;
+ }
+
+ //
+ // Check the '.' or '/', depending on the AddressIndex.
+ //
+ if (AddressIndex == ARRAY_SIZE (Address->Addr)) {
+ if (*Pointer == '/') {
+ //
+ // '/P' is in the String.
+ // Skip "/" and get P in next loop.
+ //
+ Pointer++;
+ } else {
+ //
+ // '/P' is not in the String.
+ //
+ break;
+ }
+ } else if (AddressIndex < ARRAY_SIZE (Address->Addr)) {
+ if (*Pointer == '.') {
+ //
+ // D should be followed by '.'
+ //
+ Pointer++;
+ } else {
+ return RETURN_UNSUPPORTED;
+ }
+ }
+ }
+
+ if (AddressIndex < ARRAY_SIZE (Address->Addr)) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ CopyMem (Address, &LocalAddress, sizeof (*Address));
+ if (PrefixLength != NULL) {
+ *PrefixLength = LocalPrefixLength;
+ }
+ if (EndPointer != NULL) {
+ *EndPointer = Pointer;
+ }
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated ASCII GUID string to a value of type
+ EFI_GUID.
+
+ This function outputs a GUID value by interpreting the contents of
+ the ASCII string specified by String. The format of the input
+ ASCII string String consists of 36 characters, as follows:
+
+ aabbccdd-eeff-gghh-iijj-kkllmmnnoopp
+
+ The pairs aa - pp are two characters in the range [0-9], [a-f] and
+ [A-F], with each pair representing a single byte hexadecimal value.
+
+ The mapping between String and the EFI_GUID structure is as follows:
+ aa Data1[24:31]
+ bb Data1[16:23]
+ cc Data1[8:15]
+ dd Data1[0:7]
+ ee Data2[8:15]
+ ff Data2[0:7]
+ gg Data3[8:15]
+ hh Data3[0:7]
+ ii Data4[0:7]
+ jj Data4[8:15]
+ kk Data4[16:23]
+ ll Data4[24:31]
+ mm Data4[32:39]
+ nn Data4[40:47]
+ oo Data4[48:55]
+ pp Data4[56:63]
+
+ @param String Pointer to a Null-terminated ASCII string.
+ @param Guid Pointer to the converted GUID.
+
+ @retval RETURN_SUCCESS Guid is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ @retval RETURN_UNSUPPORTED If String is not as the above format.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrToGuid (
+ IN CONST CHAR8 *String,
+ OUT GUID *Guid
+ )
+{
+ RETURN_STATUS Status;
+ GUID LocalGuid;
+
+ //
+ // None of String or Guid shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Guid != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // Get aabbccdd in big-endian.
+ //
+ Status = AsciiStrHexToBytes (String, 2 * sizeof (LocalGuid.Data1), (UINT8 *) &LocalGuid.Data1, sizeof (LocalGuid.Data1));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data1)] != '-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data1 = SwapBytes32 (LocalGuid.Data1);
+ String += 2 * sizeof (LocalGuid.Data1) + 1;
+
+ //
+ // Get eeff in big-endian.
+ //
+ Status = AsciiStrHexToBytes (String, 2 * sizeof (LocalGuid.Data2), (UINT8 *) &LocalGuid.Data2, sizeof (LocalGuid.Data2));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data2)] != '-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data2 = SwapBytes16 (LocalGuid.Data2);
+ String += 2 * sizeof (LocalGuid.Data2) + 1;
+
+ //
+ // Get gghh in big-endian.
+ //
+ Status = AsciiStrHexToBytes (String, 2 * sizeof (LocalGuid.Data3), (UINT8 *) &LocalGuid.Data3, sizeof (LocalGuid.Data3));
+ if (RETURN_ERROR (Status) || String[2 * sizeof (LocalGuid.Data3)] != '-') {
+ return RETURN_UNSUPPORTED;
+ }
+ //
+ // Convert big-endian to little-endian.
+ //
+ LocalGuid.Data3 = SwapBytes16 (LocalGuid.Data3);
+ String += 2 * sizeof (LocalGuid.Data3) + 1;
+
+ //
+ // Get iijj.
+ //
+ Status = AsciiStrHexToBytes (String, 2 * 2, &LocalGuid.Data4[0], 2);
+ if (RETURN_ERROR (Status) || String[2 * 2] != '-') {
+ return RETURN_UNSUPPORTED;
+ }
+ String += 2 * 2 + 1;
+
+ //
+ // Get kkllmmnnoopp.
+ //
+ Status = AsciiStrHexToBytes (String, 2 * 6, &LocalGuid.Data4[2], 6);
+ if (RETURN_ERROR (Status)) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ CopyGuid (Guid, &LocalGuid);
+ return RETURN_SUCCESS;
+}
+
+/**
+ Convert a Null-terminated ASCII hexadecimal string to a byte array.
+
+ This function outputs a byte array by interpreting the contents of
+ the ASCII string specified by String in hexadecimal format. The format of
+ the input ASCII string String is:
+
+ [XX]*
+
+ X is a hexadecimal digit character in the range [0-9], [a-f] and [A-F].
+ The function decodes every two hexadecimal digit characters as one byte. The
+ decoding stops after Length of characters and outputs Buffer containing
+ (Length / 2) bytes.
+
+ @param String Pointer to a Null-terminated ASCII string.
+ @param Length The number of ASCII characters to decode.
+ @param Buffer Pointer to the converted bytes array.
+ @param MaxBufferSize The maximum size of Buffer.
+
+ @retval RETURN_SUCCESS Buffer is translated from String.
+ @retval RETURN_INVALID_PARAMETER If String is NULL.
+ If Data is NULL.
+ If Length is not multiple of 2.
+ If PcdMaximumAsciiStringLength is not zero,
+ and Length is greater than
+ PcdMaximumAsciiStringLength.
+ @retval RETURN_UNSUPPORTED If Length of characters from String contain
+ a character that is not valid hexadecimal
+ digit characters, or a Null-terminator.
+ @retval RETURN_BUFFER_TOO_SMALL If MaxBufferSize is less than (Length / 2).
+**/
+RETURN_STATUS
+EFIAPI
+AsciiStrHexToBytes (
+ IN CONST CHAR8 *String,
+ IN UINTN Length,
+ OUT UINT8 *Buffer,
+ IN UINTN MaxBufferSize
+ )
+{
+ UINTN Index;
+
+ //
+ // 1. None of String or Buffer shall be a null pointer.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((String != NULL), RETURN_INVALID_PARAMETER);
+ SAFE_STRING_CONSTRAINT_CHECK ((Buffer != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. Length shall not be greater than ASCII_RSIZE_MAX.
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_STRING_CONSTRAINT_CHECK ((Length <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+
+ //
+ // 3. Length shall not be odd.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK (((Length & BIT0) == 0), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. MaxBufferSize shall equal to or greater than Length / 2.
+ //
+ SAFE_STRING_CONSTRAINT_CHECK ((MaxBufferSize >= Length / 2), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // 5. String shall not contains invalid hexadecimal digits.
+ //
+ for (Index = 0; Index < Length; Index++) {
+ if (!InternalAsciiIsHexaDecimalDigitCharacter (String[Index])) {
+ break;
+ }
+ }
+ if (Index != Length) {
+ return RETURN_UNSUPPORTED;
+ }
+
+ //
+ // Convert the hex string to bytes.
+ //
+ for(Index = 0; Index < Length; Index++) {
+
+ //
+ // For even characters, write the upper nibble for each buffer byte,
+ // and for even characters, the lower nibble.
+ //
+ if ((Index & BIT0) == 0) {
+ Buffer[Index / 2] = (UINT8) InternalAsciiHexCharToUintn (String[Index]) << 4;
+ } else {
+ Buffer[Index / 2] |= (UINT8) InternalAsciiHexCharToUintn (String[Index]);
+ }
+ }
+ return RETURN_SUCCESS;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SetJump.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SetJump.c
new file mode 100644
index 0000000..516f92f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SetJump.c
@@ -0,0 +1,34 @@
+/** @file
+ Internal ASSERT () functions for SetJump.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Worker function that checks ASSERT condition for JumpBuffer
+
+ Checks ASSERT condition for JumpBuffer.
+
+ If JumpBuffer is NULL, then ASSERT().
+ For IPF CPUs, if JumpBuffer is not aligned on a 16-byte boundary, then ASSERT().
+
+ @param JumpBuffer A pointer to CPU context buffer.
+
+**/
+VOID
+EFIAPI
+InternalAssertJumpBuffer (
+ IN BASE_LIBRARY_JUMP_BUFFER *JumpBuffer
+ )
+{
+ ASSERT (JumpBuffer != NULL);
+
+ ASSERT (((UINTN)JumpBuffer & (BASE_LIBRARY_JUMP_BUFFER_ALIGNMENT - 1)) == 0);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/String.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/String.c
new file mode 100644
index 0000000..f4854f3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/String.c
@@ -0,0 +1,1644 @@
+/** @file
+ Unicode and ASCII string primitives.
+
+ Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+
+/**
+ Returns the length of a Null-terminated Unicode string.
+
+ This function returns the number of Unicode characters in the Null-terminated
+ Unicode string specified by String.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned on a 16-bit boundary, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the
+ Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @return The length of String.
+
+**/
+UINTN
+EFIAPI
+StrLen (
+ IN CONST CHAR16 *String
+ )
+{
+ UINTN Length;
+
+ ASSERT (String != NULL);
+ ASSERT (((UINTN) String & BIT0) == 0);
+
+ for (Length = 0; *String != L'\0'; String++, Length++) {
+ //
+ // If PcdMaximumUnicodeStringLength is not zero,
+ // length should not more than PcdMaximumUnicodeStringLength
+ //
+ if (PcdGet32 (PcdMaximumUnicodeStringLength) != 0) {
+ ASSERT (Length < PcdGet32 (PcdMaximumUnicodeStringLength));
+ }
+ }
+ return Length;
+}
+
+/**
+ Returns the size of a Null-terminated Unicode string in bytes, including the
+ Null terminator.
+
+ This function returns the size, in bytes, of the Null-terminated Unicode string
+ specified by String.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned on a 16-bit boundary, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the
+ Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @return The size of String.
+
+**/
+UINTN
+EFIAPI
+StrSize (
+ IN CONST CHAR16 *String
+ )
+{
+ return (StrLen (String) + 1) * sizeof (*String);
+}
+
+/**
+ Compares two Null-terminated Unicode strings, and returns the difference
+ between the first mismatched Unicode characters.
+
+ This function compares the Null-terminated Unicode string FirstString to the
+ Null-terminated Unicode string SecondString. If FirstString is identical to
+ SecondString, then 0 is returned. Otherwise, the value returned is the first
+ mismatched Unicode character in SecondString subtracted from the first
+ mismatched Unicode character in FirstString.
+
+ If FirstString is NULL, then ASSERT().
+ If FirstString is not aligned on a 16-bit boundary, then ASSERT().
+ If SecondString is NULL, then ASSERT().
+ If SecondString is not aligned on a 16-bit boundary, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and FirstString contains more
+ than PcdMaximumUnicodeStringLength Unicode characters, not including the
+ Null-terminator, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and SecondString contains more
+ than PcdMaximumUnicodeStringLength Unicode characters, not including the
+ Null-terminator, then ASSERT().
+
+ @param FirstString A pointer to a Null-terminated Unicode string.
+ @param SecondString A pointer to a Null-terminated Unicode string.
+
+ @retval 0 FirstString is identical to SecondString.
+ @return others FirstString is not identical to SecondString.
+
+**/
+INTN
+EFIAPI
+StrCmp (
+ IN CONST CHAR16 *FirstString,
+ IN CONST CHAR16 *SecondString
+ )
+{
+ //
+ // ASSERT both strings are less long than PcdMaximumUnicodeStringLength
+ //
+ ASSERT (StrSize (FirstString) != 0);
+ ASSERT (StrSize (SecondString) != 0);
+
+ while ((*FirstString != L'\0') && (*FirstString == *SecondString)) {
+ FirstString++;
+ SecondString++;
+ }
+ return *FirstString - *SecondString;
+}
+
+/**
+ Compares up to a specified length the contents of two Null-terminated Unicode strings,
+ and returns the difference between the first mismatched Unicode characters.
+
+ This function compares the Null-terminated Unicode string FirstString to the
+ Null-terminated Unicode string SecondString. At most, Length Unicode
+ characters will be compared. If Length is 0, then 0 is returned. If
+ FirstString is identical to SecondString, then 0 is returned. Otherwise, the
+ value returned is the first mismatched Unicode character in SecondString
+ subtracted from the first mismatched Unicode character in FirstString.
+
+ If Length > 0 and FirstString is NULL, then ASSERT().
+ If Length > 0 and FirstString is not aligned on a 16-bit boundary, then ASSERT().
+ If Length > 0 and SecondString is NULL, then ASSERT().
+ If Length > 0 and SecondString is not aligned on a 16-bit boundary, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and Length is greater than
+ PcdMaximumUnicodeStringLength, then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and FirstString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the Null-terminator,
+ then ASSERT().
+ If PcdMaximumUnicodeStringLength is not zero, and SecondString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param FirstString A pointer to a Null-terminated Unicode string.
+ @param SecondString A pointer to a Null-terminated Unicode string.
+ @param Length The maximum number of Unicode characters to compare.
+
+ @retval 0 FirstString is identical to SecondString.
+ @return others FirstString is not identical to SecondString.
+
+**/
+INTN
+EFIAPI
+StrnCmp (
+ IN CONST CHAR16 *FirstString,
+ IN CONST CHAR16 *SecondString,
+ IN UINTN Length
+ )
+{
+ if (Length == 0) {
+ return 0;
+ }
+
+ //
+ // ASSERT both strings are less long than PcdMaximumUnicodeStringLength.
+ // Length tests are performed inside StrLen().
+ //
+ ASSERT (StrSize (FirstString) != 0);
+ ASSERT (StrSize (SecondString) != 0);
+
+ if (PcdGet32 (PcdMaximumUnicodeStringLength) != 0) {
+ ASSERT (Length <= PcdGet32 (PcdMaximumUnicodeStringLength));
+ }
+
+ while ((*FirstString != L'\0') &&
+ (*SecondString != L'\0') &&
+ (*FirstString == *SecondString) &&
+ (Length > 1)) {
+ FirstString++;
+ SecondString++;
+ Length--;
+ }
+
+ return *FirstString - *SecondString;
+}
+
+
+/**
+ Returns the first occurrence of a Null-terminated Unicode sub-string
+ in a Null-terminated Unicode string.
+
+ This function scans the contents of the Null-terminated Unicode string
+ specified by String and returns the first occurrence of SearchString.
+ If SearchString is not found in String, then NULL is returned. If
+ the length of SearchString is zero, then String is
+ returned.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned on a 16-bit boundary, then ASSERT().
+ If SearchString is NULL, then ASSERT().
+ If SearchString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If PcdMaximumUnicodeStringLength is not zero, and SearchString
+ or String contains more than PcdMaximumUnicodeStringLength Unicode
+ characters, not including the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+ @param SearchString A pointer to a Null-terminated Unicode string to search for.
+
+ @retval NULL If the SearchString does not appear in String.
+ @return others If there is a match.
+
+**/
+CHAR16 *
+EFIAPI
+StrStr (
+ IN CONST CHAR16 *String,
+ IN CONST CHAR16 *SearchString
+ )
+{
+ CONST CHAR16 *FirstMatch;
+ CONST CHAR16 *SearchStringTmp;
+
+ //
+ // ASSERT both strings are less long than PcdMaximumUnicodeStringLength.
+ // Length tests are performed inside StrLen().
+ //
+ ASSERT (StrSize (String) != 0);
+ ASSERT (StrSize (SearchString) != 0);
+
+ if (*SearchString == L'\0') {
+ return (CHAR16 *) String;
+ }
+
+ while (*String != L'\0') {
+ SearchStringTmp = SearchString;
+ FirstMatch = String;
+
+ while ((*String == *SearchStringTmp)
+ && (*String != L'\0')) {
+ String++;
+ SearchStringTmp++;
+ }
+
+ if (*SearchStringTmp == L'\0') {
+ return (CHAR16 *) FirstMatch;
+ }
+
+ if (*String == L'\0') {
+ return NULL;
+ }
+
+ String = FirstMatch + 1;
+ }
+
+ return NULL;
+}
+
+/**
+ Check if a Unicode character is a decimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid decimal character is from
+ L'0' to L'9'.
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a decmial character.
+ @retval FALSE If the Char is not a decmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalIsDecimalDigitCharacter (
+ IN CHAR16 Char
+ )
+{
+ return (BOOLEAN) (Char >= L'0' && Char <= L'9');
+}
+
+/**
+ Convert a Unicode character to upper case only if
+ it maps to a valid small-case ASCII character.
+
+ This internal function only deal with Unicode character
+ which maps to a valid small-case ASCII character, i.e.
+ L'a' to L'z'. For other Unicode character, the input character
+ is returned directly.
+
+ @param Char The character to convert.
+
+ @retval LowerCharacter If the Char is with range L'a' to L'z'.
+ @retval Unchanged Otherwise.
+
+**/
+CHAR16
+EFIAPI
+CharToUpper (
+ IN CHAR16 Char
+ )
+{
+ if (Char >= L'a' && Char <= L'z') {
+ return (CHAR16) (Char - (L'a' - L'A'));
+ }
+
+ return Char;
+}
+
+/**
+ Convert a Unicode character to numerical value.
+
+ This internal function only deal with Unicode character
+ which maps to a valid hexadecimal ASII character, i.e.
+ L'0' to L'9', L'a' to L'f' or L'A' to L'F'. For other
+ Unicode character, the value returned does not make sense.
+
+ @param Char The character to convert.
+
+ @return The numerical value converted.
+
+**/
+UINTN
+EFIAPI
+InternalHexCharToUintn (
+ IN CHAR16 Char
+ )
+{
+ if (InternalIsDecimalDigitCharacter (Char)) {
+ return Char - L'0';
+ }
+
+ return (10 + CharToUpper (Char) - L'A');
+}
+
+/**
+ Check if a Unicode character is a hexadecimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid hexadecimal character is
+ L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
+
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a hexadecmial character.
+ @retval FALSE If the Char is not a hexadecmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalIsHexaDecimalDigitCharacter (
+ IN CHAR16 Char
+ )
+{
+
+ return (BOOLEAN) (InternalIsDecimalDigitCharacter (Char) ||
+ (Char >= L'A' && Char <= L'F') ||
+ (Char >= L'a' && Char <= L'f'));
+}
+
+/**
+ Convert a Null-terminated Unicode decimal string to a value of
+ type UINTN.
+
+ This function returns a value of type UINTN by interpreting the contents
+ of the Unicode string specified by String as a decimal number. The format
+ of the input Unicode string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The
+ function will ignore the pad space, which includes spaces or
+ tab characters, before [decimal digits]. The running zero in the
+ beginning of [decimal digits] will be ignored. Then, the function
+ stops at the first character that is a not a valid decimal character
+ or a Null-terminator, whichever one comes first.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+ If String has only pad spaces, then 0 is returned.
+ If String has no pad spaces or valid decimal digits,
+ then 0 is returned.
+ If the number represented by String overflows according
+ to the range defined by UINTN, then MAX_UINTN is returned.
+
+ If PcdMaximumUnicodeStringLength is not zero, and String contains
+ more than PcdMaximumUnicodeStringLength Unicode characters, not including
+ the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @retval Value translated from String.
+
+**/
+UINTN
+EFIAPI
+StrDecimalToUintn (
+ IN CONST CHAR16 *String
+ )
+{
+ UINTN Result;
+
+ StrDecimalToUintnS (String, (CHAR16 **) NULL, &Result);
+ return Result;
+}
+
+
+/**
+ Convert a Null-terminated Unicode decimal string to a value of
+ type UINT64.
+
+ This function returns a value of type UINT64 by interpreting the contents
+ of the Unicode string specified by String as a decimal number. The format
+ of the input Unicode string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The
+ function will ignore the pad space, which includes spaces or
+ tab characters, before [decimal digits]. The running zero in the
+ beginning of [decimal digits] will be ignored. Then, the function
+ stops at the first character that is a not a valid decimal character
+ or a Null-terminator, whichever one comes first.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+ If String has only pad spaces, then 0 is returned.
+ If String has no pad spaces or valid decimal digits,
+ then 0 is returned.
+ If the number represented by String overflows according
+ to the range defined by UINT64, then MAX_UINT64 is returned.
+
+ If PcdMaximumUnicodeStringLength is not zero, and String contains
+ more than PcdMaximumUnicodeStringLength Unicode characters, not including
+ the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @retval Value translated from String.
+
+**/
+UINT64
+EFIAPI
+StrDecimalToUint64 (
+ IN CONST CHAR16 *String
+ )
+{
+ UINT64 Result;
+
+ StrDecimalToUint64S (String, (CHAR16 **) NULL, &Result);
+ return Result;
+}
+
+/**
+ Convert a Null-terminated Unicode hexadecimal string to a value of type UINTN.
+
+ This function returns a value of type UINTN by interpreting the contents
+ of the Unicode string specified by String as a hexadecimal number.
+ The format of the input Unicode string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix.
+ If "x" appears in the input string, it must be prefixed with at least one 0.
+ The function will ignore the pad space, which includes spaces or tab characters,
+ before [zeros], [x] or [hexadecimal digit]. The running zero before [x] or
+ [hexadecimal digit] will be ignored. Then, the decoding starts after [x] or the
+ first valid hexadecimal digit. Then, the function stops at the first character that is
+ a not a valid hexadecimal character or NULL, whichever one comes first.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+ If String has only pad spaces, then zero is returned.
+ If String has no leading pad spaces, leading zeros or valid hexadecimal digits,
+ then zero is returned.
+ If the number represented by String overflows according to the range defined by
+ UINTN, then MAX_UINTN is returned.
+
+ If PcdMaximumUnicodeStringLength is not zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @retval Value translated from String.
+
+**/
+UINTN
+EFIAPI
+StrHexToUintn (
+ IN CONST CHAR16 *String
+ )
+{
+ UINTN Result;
+
+ StrHexToUintnS (String, (CHAR16 **) NULL, &Result);
+ return Result;
+}
+
+
+/**
+ Convert a Null-terminated Unicode hexadecimal string to a value of type UINT64.
+
+ This function returns a value of type UINT64 by interpreting the contents
+ of the Unicode string specified by String as a hexadecimal number.
+ The format of the input Unicode string String is
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix.
+ If "x" appears in the input string, it must be prefixed with at least one 0.
+ The function will ignore the pad space, which includes spaces or tab characters,
+ before [zeros], [x] or [hexadecimal digit]. The running zero before [x] or
+ [hexadecimal digit] will be ignored. Then, the decoding starts after [x] or the
+ first valid hexadecimal digit. Then, the function stops at the first character that is
+ a not a valid hexadecimal character or NULL, whichever one comes first.
+
+ If String is NULL, then ASSERT().
+ If String is not aligned in a 16-bit boundary, then ASSERT().
+ If String has only pad spaces, then zero is returned.
+ If String has no leading pad spaces, leading zeros or valid hexadecimal digits,
+ then zero is returned.
+ If the number represented by String overflows according to the range defined by
+ UINT64, then MAX_UINT64 is returned.
+
+ If PcdMaximumUnicodeStringLength is not zero, and String contains more than
+ PcdMaximumUnicodeStringLength Unicode characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @retval Value translated from String.
+
+**/
+UINT64
+EFIAPI
+StrHexToUint64 (
+ IN CONST CHAR16 *String
+ )
+{
+ UINT64 Result;
+
+ StrHexToUint64S (String, (CHAR16 **) NULL, &Result);
+ return Result;
+}
+
+/**
+ Check if a ASCII character is a decimal character.
+
+ This internal function checks if a Unicode character is a
+ decimal character. The valid decimal character is from
+ '0' to '9'.
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a decmial character.
+ @retval FALSE If the Char is not a decmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalAsciiIsDecimalDigitCharacter (
+ IN CHAR8 Char
+ )
+{
+ return (BOOLEAN) (Char >= '0' && Char <= '9');
+}
+
+/**
+ Check if a ASCII character is a hexadecimal character.
+
+ This internal function checks if a ASCII character is a
+ decimal character. The valid hexadecimal character is
+ L'0' to L'9', L'a' to L'f', or L'A' to L'F'.
+
+
+ @param Char The character to check against.
+
+ @retval TRUE If the Char is a hexadecmial character.
+ @retval FALSE If the Char is not a hexadecmial character.
+
+**/
+BOOLEAN
+EFIAPI
+InternalAsciiIsHexaDecimalDigitCharacter (
+ IN CHAR8 Char
+ )
+{
+
+ return (BOOLEAN) (InternalAsciiIsDecimalDigitCharacter (Char) ||
+ (Char >= 'A' && Char <= 'F') ||
+ (Char >= 'a' && Char <= 'f'));
+}
+
+
+/**
+ Returns the length of a Null-terminated ASCII string.
+
+ This function returns the number of ASCII characters in the Null-terminated
+ ASCII string specified by String.
+
+ If Length > 0 and Destination is NULL, then ASSERT().
+ If Length > 0 and Source is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and String contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @return The length of String.
+
+**/
+UINTN
+EFIAPI
+AsciiStrLen (
+ IN CONST CHAR8 *String
+ )
+{
+ UINTN Length;
+
+ ASSERT (String != NULL);
+
+ for (Length = 0; *String != '\0'; String++, Length++) {
+ //
+ // If PcdMaximumUnicodeStringLength is not zero,
+ // length should not more than PcdMaximumUnicodeStringLength
+ //
+ if (PcdGet32 (PcdMaximumAsciiStringLength) != 0) {
+ ASSERT (Length < PcdGet32 (PcdMaximumAsciiStringLength));
+ }
+ }
+ return Length;
+}
+
+/**
+ Returns the size of a Null-terminated ASCII string in bytes, including the
+ Null terminator.
+
+ This function returns the size, in bytes, of the Null-terminated ASCII string
+ specified by String.
+
+ If String is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and String contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @return The size of String.
+
+**/
+UINTN
+EFIAPI
+AsciiStrSize (
+ IN CONST CHAR8 *String
+ )
+{
+ return (AsciiStrLen (String) + 1) * sizeof (*String);
+}
+
+/**
+ Compares two Null-terminated ASCII strings, and returns the difference
+ between the first mismatched ASCII characters.
+
+ This function compares the Null-terminated ASCII string FirstString to the
+ Null-terminated ASCII string SecondString. If FirstString is identical to
+ SecondString, then 0 is returned. Otherwise, the value returned is the first
+ mismatched ASCII character in SecondString subtracted from the first
+ mismatched ASCII character in FirstString.
+
+ If FirstString is NULL, then ASSERT().
+ If SecondString is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and FirstString contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and SecondString contains more
+ than PcdMaximumAsciiStringLength ASCII characters, not including the
+ Null-terminator, then ASSERT().
+
+ @param FirstString A pointer to a Null-terminated ASCII string.
+ @param SecondString A pointer to a Null-terminated ASCII string.
+
+ @retval ==0 FirstString is identical to SecondString.
+ @retval !=0 FirstString is not identical to SecondString.
+
+**/
+INTN
+EFIAPI
+AsciiStrCmp (
+ IN CONST CHAR8 *FirstString,
+ IN CONST CHAR8 *SecondString
+ )
+{
+ //
+ // ASSERT both strings are less long than PcdMaximumAsciiStringLength
+ //
+ ASSERT (AsciiStrSize (FirstString));
+ ASSERT (AsciiStrSize (SecondString));
+
+ while ((*FirstString != '\0') && (*FirstString == *SecondString)) {
+ FirstString++;
+ SecondString++;
+ }
+
+ return *FirstString - *SecondString;
+}
+
+/**
+ Converts a lowercase Ascii character to upper one.
+
+ If Chr is lowercase Ascii character, then converts it to upper one.
+
+ If Value >= 0xA0, then ASSERT().
+ If (Value & 0x0F) >= 0x0A, then ASSERT().
+
+ @param Chr one Ascii character
+
+ @return The uppercase value of Ascii character
+
+**/
+CHAR8
+EFIAPI
+AsciiCharToUpper (
+ IN CHAR8 Chr
+ )
+{
+ return (UINT8) ((Chr >= 'a' && Chr <= 'z') ? Chr - ('a' - 'A') : Chr);
+}
+
+/**
+ Convert a ASCII character to numerical value.
+
+ This internal function only deal with Unicode character
+ which maps to a valid hexadecimal ASII character, i.e.
+ '0' to '9', 'a' to 'f' or 'A' to 'F'. For other
+ ASCII character, the value returned does not make sense.
+
+ @param Char The character to convert.
+
+ @return The numerical value converted.
+
+**/
+UINTN
+EFIAPI
+InternalAsciiHexCharToUintn (
+ IN CHAR8 Char
+ )
+{
+ if (InternalIsDecimalDigitCharacter (Char)) {
+ return Char - '0';
+ }
+
+ return (10 + AsciiCharToUpper (Char) - 'A');
+}
+
+
+/**
+ Performs a case insensitive comparison of two Null-terminated ASCII strings,
+ and returns the difference between the first mismatched ASCII characters.
+
+ This function performs a case insensitive comparison of the Null-terminated
+ ASCII string FirstString to the Null-terminated ASCII string SecondString. If
+ FirstString is identical to SecondString, then 0 is returned. Otherwise, the
+ value returned is the first mismatched lower case ASCII character in
+ SecondString subtracted from the first mismatched lower case ASCII character
+ in FirstString.
+
+ If FirstString is NULL, then ASSERT().
+ If SecondString is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and FirstString contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero and SecondString contains more
+ than PcdMaximumAsciiStringLength ASCII characters, not including the
+ Null-terminator, then ASSERT().
+
+ @param FirstString A pointer to a Null-terminated ASCII string.
+ @param SecondString A pointer to a Null-terminated ASCII string.
+
+ @retval ==0 FirstString is identical to SecondString using case insensitive
+ comparisons.
+ @retval !=0 FirstString is not identical to SecondString using case
+ insensitive comparisons.
+
+**/
+INTN
+EFIAPI
+AsciiStriCmp (
+ IN CONST CHAR8 *FirstString,
+ IN CONST CHAR8 *SecondString
+ )
+{
+ CHAR8 UpperFirstString;
+ CHAR8 UpperSecondString;
+
+ //
+ // ASSERT both strings are less long than PcdMaximumAsciiStringLength
+ //
+ ASSERT (AsciiStrSize (FirstString));
+ ASSERT (AsciiStrSize (SecondString));
+
+ UpperFirstString = AsciiCharToUpper (*FirstString);
+ UpperSecondString = AsciiCharToUpper (*SecondString);
+ while ((*FirstString != '\0') && (*SecondString != '\0') && (UpperFirstString == UpperSecondString)) {
+ FirstString++;
+ SecondString++;
+ UpperFirstString = AsciiCharToUpper (*FirstString);
+ UpperSecondString = AsciiCharToUpper (*SecondString);
+ }
+
+ return UpperFirstString - UpperSecondString;
+}
+
+/**
+ Compares two Null-terminated ASCII strings with maximum lengths, and returns
+ the difference between the first mismatched ASCII characters.
+
+ This function compares the Null-terminated ASCII string FirstString to the
+ Null-terminated ASCII string SecondString. At most, Length ASCII characters
+ will be compared. If Length is 0, then 0 is returned. If FirstString is
+ identical to SecondString, then 0 is returned. Otherwise, the value returned
+ is the first mismatched ASCII character in SecondString subtracted from the
+ first mismatched ASCII character in FirstString.
+
+ If Length > 0 and FirstString is NULL, then ASSERT().
+ If Length > 0 and SecondString is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero, and Length is greater than
+ PcdMaximumAsciiStringLength, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero, and FirstString contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero, and SecondString contains more than
+ PcdMaximumAsciiStringLength ASCII characters, not including the Null-terminator,
+ then ASSERT().
+
+ @param FirstString A pointer to a Null-terminated ASCII string.
+ @param SecondString A pointer to a Null-terminated ASCII string.
+ @param Length The maximum number of ASCII characters for compare.
+
+ @retval ==0 FirstString is identical to SecondString.
+ @retval !=0 FirstString is not identical to SecondString.
+
+**/
+INTN
+EFIAPI
+AsciiStrnCmp (
+ IN CONST CHAR8 *FirstString,
+ IN CONST CHAR8 *SecondString,
+ IN UINTN Length
+ )
+{
+ if (Length == 0) {
+ return 0;
+ }
+
+ //
+ // ASSERT both strings are less long than PcdMaximumAsciiStringLength
+ //
+ ASSERT (AsciiStrSize (FirstString));
+ ASSERT (AsciiStrSize (SecondString));
+
+ if (PcdGet32 (PcdMaximumAsciiStringLength) != 0) {
+ ASSERT (Length <= PcdGet32 (PcdMaximumAsciiStringLength));
+ }
+
+ while ((*FirstString != '\0') &&
+ (*SecondString != '\0') &&
+ (*FirstString == *SecondString) &&
+ (Length > 1)) {
+ FirstString++;
+ SecondString++;
+ Length--;
+ }
+ return *FirstString - *SecondString;
+}
+
+
+/**
+ Returns the first occurrence of a Null-terminated ASCII sub-string
+ in a Null-terminated ASCII string.
+
+ This function scans the contents of the ASCII string specified by String
+ and returns the first occurrence of SearchString. If SearchString is not
+ found in String, then NULL is returned. If the length of SearchString is zero,
+ then String is returned.
+
+ If String is NULL, then ASSERT().
+ If SearchString is NULL, then ASSERT().
+
+ If PcdMaximumAsciiStringLength is not zero, and SearchString or
+ String contains more than PcdMaximumAsciiStringLength Unicode characters
+ not including the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+ @param SearchString A pointer to a Null-terminated ASCII string to search for.
+
+ @retval NULL If the SearchString does not appear in String.
+ @retval others If there is a match return the first occurrence of SearchingString.
+ If the length of SearchString is zero,return String.
+
+**/
+CHAR8 *
+EFIAPI
+AsciiStrStr (
+ IN CONST CHAR8 *String,
+ IN CONST CHAR8 *SearchString
+ )
+{
+ CONST CHAR8 *FirstMatch;
+ CONST CHAR8 *SearchStringTmp;
+
+ //
+ // ASSERT both strings are less long than PcdMaximumAsciiStringLength
+ //
+ ASSERT (AsciiStrSize (String) != 0);
+ ASSERT (AsciiStrSize (SearchString) != 0);
+
+ if (*SearchString == '\0') {
+ return (CHAR8 *) String;
+ }
+
+ while (*String != '\0') {
+ SearchStringTmp = SearchString;
+ FirstMatch = String;
+
+ while ((*String == *SearchStringTmp)
+ && (*String != '\0')) {
+ String++;
+ SearchStringTmp++;
+ }
+
+ if (*SearchStringTmp == '\0') {
+ return (CHAR8 *) FirstMatch;
+ }
+
+ if (*String == '\0') {
+ return NULL;
+ }
+
+ String = FirstMatch + 1;
+ }
+
+ return NULL;
+}
+
+/**
+ Convert a Null-terminated ASCII decimal string to a value of type
+ UINTN.
+
+ This function returns a value of type UINTN by interpreting the contents
+ of the ASCII string String as a decimal number. The format of the input
+ ASCII string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before the digits.
+ The running zero in the beginning of [decimal digits] will be ignored. Then, the
+ function stops at the first character that is a not a valid decimal character or
+ Null-terminator, whichever on comes first.
+
+ If String has only pad spaces, then 0 is returned.
+ If String has no pad spaces or valid decimal digits, then 0 is returned.
+ If the number represented by String overflows according to the range defined by
+ UINTN, then MAX_UINTN is returned.
+ If String is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero, and String contains more than
+ PcdMaximumAsciiStringLength ASCII characters not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @retval Value translated from String.
+
+**/
+UINTN
+EFIAPI
+AsciiStrDecimalToUintn (
+ IN CONST CHAR8 *String
+ )
+{
+ UINTN Result;
+
+ AsciiStrDecimalToUintnS (String, (CHAR8 **) NULL, &Result);
+ return Result;
+}
+
+
+/**
+ Convert a Null-terminated ASCII decimal string to a value of type
+ UINT64.
+
+ This function returns a value of type UINT64 by interpreting the contents
+ of the ASCII string String as a decimal number. The format of the input
+ ASCII string String is:
+
+ [spaces] [decimal digits].
+
+ The valid decimal digit character is in the range [0-9]. The function will
+ ignore the pad space, which includes spaces or tab characters, before the digits.
+ The running zero in the beginning of [decimal digits] will be ignored. Then, the
+ function stops at the first character that is a not a valid decimal character or
+ Null-terminator, whichever on comes first.
+
+ If String has only pad spaces, then 0 is returned.
+ If String has no pad spaces or valid decimal digits, then 0 is returned.
+ If the number represented by String overflows according to the range defined by
+ UINT64, then MAX_UINT64 is returned.
+ If String is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero, and String contains more than
+ PcdMaximumAsciiStringLength ASCII characters not including the Null-terminator,
+ then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @retval Value translated from String.
+
+**/
+UINT64
+EFIAPI
+AsciiStrDecimalToUint64 (
+ IN CONST CHAR8 *String
+ )
+{
+ UINT64 Result;
+
+ AsciiStrDecimalToUint64S (String, (CHAR8 **) NULL, &Result);
+ return Result;
+}
+
+/**
+ Convert a Null-terminated ASCII hexadecimal string to a value of type UINTN.
+
+ This function returns a value of type UINTN by interpreting the contents of
+ the ASCII string String as a hexadecimal number. The format of the input ASCII
+ string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix. If "x"
+ appears in the input string, it must be prefixed with at least one 0. The function
+ will ignore the pad space, which includes spaces or tab characters, before [zeros],
+ [x] or [hexadecimal digits]. The running zero before [x] or [hexadecimal digits]
+ will be ignored. Then, the decoding starts after [x] or the first valid hexadecimal
+ digit. Then, the function stops at the first character that is a not a valid
+ hexadecimal character or Null-terminator, whichever on comes first.
+
+ If String has only pad spaces, then 0 is returned.
+ If String has no leading pad spaces, leading zeros or valid hexadecimal digits, then
+ 0 is returned.
+
+ If the number represented by String overflows according to the range defined by UINTN,
+ then MAX_UINTN is returned.
+ If String is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than PcdMaximumAsciiStringLength ASCII characters not including
+ the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @retval Value translated from String.
+
+**/
+UINTN
+EFIAPI
+AsciiStrHexToUintn (
+ IN CONST CHAR8 *String
+ )
+{
+ UINTN Result;
+
+ AsciiStrHexToUintnS (String, (CHAR8 **) NULL, &Result);
+ return Result;
+}
+
+
+/**
+ Convert a Null-terminated ASCII hexadecimal string to a value of type UINT64.
+
+ This function returns a value of type UINT64 by interpreting the contents of
+ the ASCII string String as a hexadecimal number. The format of the input ASCII
+ string String is:
+
+ [spaces][zeros][x][hexadecimal digits].
+
+ The valid hexadecimal digit character is in the range [0-9], [a-f] and [A-F].
+ The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix. If "x"
+ appears in the input string, it must be prefixed with at least one 0. The function
+ will ignore the pad space, which includes spaces or tab characters, before [zeros],
+ [x] or [hexadecimal digits]. The running zero before [x] or [hexadecimal digits]
+ will be ignored. Then, the decoding starts after [x] or the first valid hexadecimal
+ digit. Then, the function stops at the first character that is a not a valid
+ hexadecimal character or Null-terminator, whichever on comes first.
+
+ If String has only pad spaces, then 0 is returned.
+ If String has no leading pad spaces, leading zeros or valid hexadecimal digits, then
+ 0 is returned.
+
+ If the number represented by String overflows according to the range defined by UINT64,
+ then MAX_UINT64 is returned.
+ If String is NULL, then ASSERT().
+ If PcdMaximumAsciiStringLength is not zero,
+ and String contains more than PcdMaximumAsciiStringLength ASCII characters not including
+ the Null-terminator, then ASSERT().
+
+ @param String A pointer to a Null-terminated ASCII string.
+
+ @retval Value translated from String.
+
+**/
+UINT64
+EFIAPI
+AsciiStrHexToUint64 (
+ IN CONST CHAR8 *String
+ )
+{
+ UINT64 Result;
+
+ AsciiStrHexToUint64S (String, (CHAR8 **) NULL, &Result);
+ return Result;
+}
+
+
+STATIC CHAR8 EncodingTable[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
+ "abcdefghijklmnopqrstuvwxyz"
+ "0123456789+/";
+
+/**
+ Convert binary data to a Base64 encoded ascii string based on RFC4648.
+
+ Produce a Null-terminated Ascii string in the output buffer specified by Destination and DestinationSize.
+ The Ascii string is produced by converting the data string specified by Source and SourceLength.
+
+ @param Source Input UINT8 data
+ @param SourceLength Number of UINT8 bytes of data
+ @param Destination Pointer to output string buffer
+ @param DestinationSize Size of ascii buffer. Set to 0 to get the size needed.
+ Caller is responsible for passing in buffer of DestinationSize
+
+ @retval RETURN_SUCCESS When ascii buffer is filled in.
+ @retval RETURN_INVALID_PARAMETER If Source is NULL or DestinationSize is NULL.
+ @retval RETURN_INVALID_PARAMETER If SourceLength or DestinationSize is bigger than (MAX_ADDRESS - (UINTN)Destination).
+ @retval RETURN_BUFFER_TOO_SMALL If SourceLength is 0 and DestinationSize is <1.
+ @retval RETURN_BUFFER_TOO_SMALL If Destination is NULL or DestinationSize is smaller than required buffersize.
+
+**/
+RETURN_STATUS
+EFIAPI
+Base64Encode (
+ IN CONST UINT8 *Source,
+ IN UINTN SourceLength,
+ OUT CHAR8 *Destination OPTIONAL,
+ IN OUT UINTN *DestinationSize
+ )
+{
+
+ UINTN RequiredSize;
+ UINTN Left;
+
+ //
+ // Check pointers, and SourceLength is valid
+ //
+ if ((Source == NULL) || (DestinationSize == NULL)) {
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Allow for RFC 4648 test vector 1
+ //
+ if (SourceLength == 0) {
+ if (*DestinationSize < 1) {
+ *DestinationSize = 1;
+ return RETURN_BUFFER_TOO_SMALL;
+ }
+ *DestinationSize = 1;
+ *Destination = '\0';
+ return RETURN_SUCCESS;
+ }
+
+ //
+ // Check if SourceLength or DestinationSize is valid
+ //
+ if ((SourceLength >= (MAX_ADDRESS - (UINTN)Source)) || (*DestinationSize >= (MAX_ADDRESS - (UINTN)Destination))){
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // 4 ascii per 3 bytes + NULL
+ //
+ RequiredSize = ((SourceLength + 2) / 3) * 4 + 1;
+ if ((Destination == NULL) || *DestinationSize < RequiredSize) {
+ *DestinationSize = RequiredSize;
+ return RETURN_BUFFER_TOO_SMALL;
+ }
+
+ Left = SourceLength;
+
+ //
+ // Encode 24 bits (three bytes) into 4 ascii characters
+ //
+ while (Left >= 3) {
+
+ *Destination++ = EncodingTable[( Source[0] & 0xfc) >> 2 ];
+ *Destination++ = EncodingTable[((Source[0] & 0x03) << 4) + ((Source[1] & 0xf0) >> 4)];
+ *Destination++ = EncodingTable[((Source[1] & 0x0f) << 2) + ((Source[2] & 0xc0) >> 6)];
+ *Destination++ = EncodingTable[( Source[2] & 0x3f)];
+ Left -= 3;
+ Source += 3;
+ }
+
+ //
+ // Handle the remainder, and add padding '=' characters as necessary.
+ //
+ switch (Left) {
+ case 0:
+
+ //
+ // No bytes Left, done.
+ //
+ break;
+ case 1:
+
+ //
+ // One more data byte, two pad characters
+ //
+ *Destination++ = EncodingTable[( Source[0] & 0xfc) >> 2];
+ *Destination++ = EncodingTable[((Source[0] & 0x03) << 4)];
+ *Destination++ = '=';
+ *Destination++ = '=';
+ break;
+ case 2:
+
+ //
+ // Two more data bytes, and one pad character
+ //
+ *Destination++ = EncodingTable[( Source[0] & 0xfc) >> 2];
+ *Destination++ = EncodingTable[((Source[0] & 0x03) << 4) + ((Source[1] & 0xf0) >> 4)];
+ *Destination++ = EncodingTable[((Source[1] & 0x0f) << 2)];
+ *Destination++ = '=';
+ break;
+ }
+ //
+ // Add terminating NULL
+ //
+ *Destination = '\0';
+ return RETURN_SUCCESS;
+}
+
+/**
+ Decode Base64 ASCII encoded data to 8-bit binary representation, based on
+ RFC4648.
+
+ Decoding occurs according to "Table 1: The Base 64 Alphabet" in RFC4648.
+
+ Whitespace is ignored at all positions:
+ - 0x09 ('\t') horizontal tab
+ - 0x0A ('\n') new line
+ - 0x0B ('\v') vertical tab
+ - 0x0C ('\f') form feed
+ - 0x0D ('\r') carriage return
+ - 0x20 (' ') space
+
+ The minimum amount of required padding (with ASCII 0x3D, '=') is tolerated
+ and enforced at the end of the Base64 ASCII encoded data, and only there.
+
+ Other characters outside of the encoding alphabet cause the function to
+ reject the Base64 ASCII encoded data.
+
+ @param[in] Source Array of CHAR8 elements containing the Base64
+ ASCII encoding. May be NULL if SourceSize is
+ zero.
+
+ @param[in] SourceSize Number of CHAR8 elements in Source.
+
+ @param[out] Destination Array of UINT8 elements receiving the decoded
+ 8-bit binary representation. Allocated by the
+ caller. May be NULL if DestinationSize is
+ zero on input. If NULL, decoding is
+ performed, but the 8-bit binary
+ representation is not stored. If non-NULL and
+ the function returns an error, the contents
+ of Destination are indeterminate.
+
+ @param[in,out] DestinationSize On input, the number of UINT8 elements that
+ the caller allocated for Destination. On
+ output, if the function returns
+ RETURN_SUCCESS or RETURN_BUFFER_TOO_SMALL,
+ the number of UINT8 elements that are
+ required for decoding the Base64 ASCII
+ representation. If the function returns a
+ value different from both RETURN_SUCCESS and
+ RETURN_BUFFER_TOO_SMALL, then DestinationSize
+ is indeterminate on output.
+
+ @retval RETURN_SUCCESS SourceSize CHAR8 elements at Source have
+ been decoded to on-output DestinationSize
+ UINT8 elements at Destination. Note that
+ RETURN_SUCCESS covers the case when
+ DestinationSize is zero on input, and
+ Source decodes to zero bytes (due to
+ containing at most ignored whitespace).
+
+ @retval RETURN_BUFFER_TOO_SMALL The input value of DestinationSize is not
+ large enough for decoding SourceSize CHAR8
+ elements at Source. The required number of
+ UINT8 elements has been stored to
+ DestinationSize.
+
+ @retval RETURN_INVALID_PARAMETER DestinationSize is NULL.
+
+ @retval RETURN_INVALID_PARAMETER Source is NULL, but SourceSize is not zero.
+
+ @retval RETURN_INVALID_PARAMETER Destination is NULL, but DestinationSize is
+ not zero on input.
+
+ @retval RETURN_INVALID_PARAMETER Source is non-NULL, and (Source +
+ SourceSize) would wrap around MAX_ADDRESS.
+
+ @retval RETURN_INVALID_PARAMETER Destination is non-NULL, and (Destination +
+ DestinationSize) would wrap around
+ MAX_ADDRESS, as specified on input.
+
+ @retval RETURN_INVALID_PARAMETER None of Source and Destination are NULL,
+ and CHAR8[SourceSize] at Source overlaps
+ UINT8[DestinationSize] at Destination, as
+ specified on input.
+
+ @retval RETURN_INVALID_PARAMETER Invalid CHAR8 element encountered in
+ Source.
+**/
+RETURN_STATUS
+EFIAPI
+Base64Decode (
+ IN CONST CHAR8 *Source OPTIONAL,
+ IN UINTN SourceSize,
+ OUT UINT8 *Destination OPTIONAL,
+ IN OUT UINTN *DestinationSize
+ )
+{
+ BOOLEAN PaddingMode;
+ UINTN SixBitGroupsConsumed;
+ UINT32 Accumulator;
+ UINTN OriginalDestinationSize;
+ UINTN SourceIndex;
+ CHAR8 SourceChar;
+ UINT32 Base64Value;
+ UINT8 DestinationOctet;
+
+ if (DestinationSize == NULL) {
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Check Source array validity.
+ //
+ if (Source == NULL) {
+ if (SourceSize > 0) {
+ //
+ // At least one CHAR8 element at NULL Source.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+ } else if (SourceSize > MAX_ADDRESS - (UINTN)Source) {
+ //
+ // Non-NULL Source, but it wraps around.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Check Destination array validity.
+ //
+ if (Destination == NULL) {
+ if (*DestinationSize > 0) {
+ //
+ // At least one UINT8 element at NULL Destination.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+ } else if (*DestinationSize > MAX_ADDRESS - (UINTN)Destination) {
+ //
+ // Non-NULL Destination, but it wraps around.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Check for overlap.
+ //
+ if (Source != NULL && Destination != NULL) {
+ //
+ // Both arrays have been provided, and we know from earlier that each array
+ // is valid in itself.
+ //
+ if ((UINTN)Source + SourceSize <= (UINTN)Destination) {
+ //
+ // Source array precedes Destination array, OK.
+ //
+ } else if ((UINTN)Destination + *DestinationSize <= (UINTN)Source) {
+ //
+ // Destination array precedes Source array, OK.
+ //
+ } else {
+ //
+ // Overlap.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+ }
+
+ //
+ // Decoding loop setup.
+ //
+ PaddingMode = FALSE;
+ SixBitGroupsConsumed = 0;
+ Accumulator = 0;
+ OriginalDestinationSize = *DestinationSize;
+ *DestinationSize = 0;
+
+ //
+ // Decoding loop.
+ //
+ for (SourceIndex = 0; SourceIndex < SourceSize; SourceIndex++) {
+ SourceChar = Source[SourceIndex];
+
+ //
+ // Whitespace is ignored at all positions (regardless of padding mode).
+ //
+ if (SourceChar == '\t' || SourceChar == '\n' || SourceChar == '\v' ||
+ SourceChar == '\f' || SourceChar == '\r' || SourceChar == ' ') {
+ continue;
+ }
+
+ //
+ // If we're in padding mode, accept another padding character, as long as
+ // that padding character completes the quantum. This completes case (2)
+ // from RFC4648, Chapter 4. "Base 64 Encoding":
+ //
+ // (2) The final quantum of encoding input is exactly 8 bits; here, the
+ // final unit of encoded output will be two characters followed by two
+ // "=" padding characters.
+ //
+ if (PaddingMode) {
+ if (SourceChar == '=' && SixBitGroupsConsumed == 3) {
+ SixBitGroupsConsumed = 0;
+ continue;
+ }
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // When not in padding mode, decode Base64Value based on RFC4648, "Table 1:
+ // The Base 64 Alphabet".
+ //
+ if ('A' <= SourceChar && SourceChar <= 'Z') {
+ Base64Value = SourceChar - 'A';
+ } else if ('a' <= SourceChar && SourceChar <= 'z') {
+ Base64Value = 26 + (SourceChar - 'a');
+ } else if ('0' <= SourceChar && SourceChar <= '9') {
+ Base64Value = 52 + (SourceChar - '0');
+ } else if (SourceChar == '+') {
+ Base64Value = 62;
+ } else if (SourceChar == '/') {
+ Base64Value = 63;
+ } else if (SourceChar == '=') {
+ //
+ // Enter padding mode.
+ //
+ PaddingMode = TRUE;
+
+ if (SixBitGroupsConsumed == 2) {
+ //
+ // If we have consumed two 6-bit groups from the current quantum before
+ // encountering the first padding character, then this is case (2) from
+ // RFC4648, Chapter 4. "Base 64 Encoding". Bump SixBitGroupsConsumed,
+ // and we'll enforce another padding character.
+ //
+ SixBitGroupsConsumed = 3;
+ } else if (SixBitGroupsConsumed == 3) {
+ //
+ // If we have consumed three 6-bit groups from the current quantum
+ // before encountering the first padding character, then this is case
+ // (3) from RFC4648, Chapter 4. "Base 64 Encoding". The quantum is now
+ // complete.
+ //
+ SixBitGroupsConsumed = 0;
+ } else {
+ //
+ // Padding characters are not allowed at the first two positions of a
+ // quantum.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Wherever in a quantum we enter padding mode, we enforce the padding
+ // bits pending in the accumulator -- from the last 6-bit group just
+ // preceding the padding character -- to be zero. Refer to RFC4648,
+ // Chapter 3.5. "Canonical Encoding".
+ //
+ if (Accumulator != 0) {
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Advance to the next source character.
+ //
+ continue;
+ } else {
+ //
+ // Other characters outside of the encoding alphabet are rejected.
+ //
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Feed the bits of the current 6-bit group of the quantum to the
+ // accumulator.
+ //
+ Accumulator = (Accumulator << 6) | Base64Value;
+ SixBitGroupsConsumed++;
+ switch (SixBitGroupsConsumed) {
+ case 1:
+ //
+ // No octet to spill after consuming the first 6-bit group of the
+ // quantum; advance to the next source character.
+ //
+ continue;
+ case 2:
+ //
+ // 12 bits accumulated (6 pending + 6 new); prepare for spilling an
+ // octet. 4 bits remain pending.
+ //
+ DestinationOctet = (UINT8)(Accumulator >> 4);
+ Accumulator &= 0xF;
+ break;
+ case 3:
+ //
+ // 10 bits accumulated (4 pending + 6 new); prepare for spilling an
+ // octet. 2 bits remain pending.
+ //
+ DestinationOctet = (UINT8)(Accumulator >> 2);
+ Accumulator &= 0x3;
+ break;
+ default:
+ ASSERT (SixBitGroupsConsumed == 4);
+ //
+ // 8 bits accumulated (2 pending + 6 new); prepare for spilling an octet.
+ // The quantum is complete, 0 bits remain pending.
+ //
+ DestinationOctet = (UINT8)Accumulator;
+ Accumulator = 0;
+ SixBitGroupsConsumed = 0;
+ break;
+ }
+
+ //
+ // Store the decoded octet if there's room left. Increment
+ // (*DestinationSize) unconditionally.
+ //
+ if (*DestinationSize < OriginalDestinationSize) {
+ ASSERT (Destination != NULL);
+ Destination[*DestinationSize] = DestinationOctet;
+ }
+ (*DestinationSize)++;
+
+ //
+ // Advance to the next source character.
+ //
+ }
+
+ //
+ // If Source terminates mid-quantum, then Source is invalid.
+ //
+ if (SixBitGroupsConsumed != 0) {
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ //
+ // Done.
+ //
+ if (*DestinationSize <= OriginalDestinationSize) {
+ return RETURN_SUCCESS;
+ }
+ return RETURN_BUFFER_TOO_SMALL;
+}
+
+/**
+ Converts an 8-bit value to an 8-bit BCD value.
+
+ Converts the 8-bit value specified by Value to BCD. The BCD value is
+ returned.
+
+ If Value >= 100, then ASSERT().
+
+ @param Value The 8-bit value to convert to BCD. Range 0..99.
+
+ @return The BCD value.
+
+**/
+UINT8
+EFIAPI
+DecimalToBcd8 (
+ IN UINT8 Value
+ )
+{
+ ASSERT (Value < 100);
+ return (UINT8) (((Value / 10) << 4) | (Value % 10));
+}
+
+/**
+ Converts an 8-bit BCD value to an 8-bit value.
+
+ Converts the 8-bit BCD value specified by Value to an 8-bit value. The 8-bit
+ value is returned.
+
+ If Value >= 0xA0, then ASSERT().
+ If (Value & 0x0F) >= 0x0A, then ASSERT().
+
+ @param Value The 8-bit BCD value to convert to an 8-bit value.
+
+ @return The 8-bit value is returned.
+
+**/
+UINT8
+EFIAPI
+BcdToDecimal8 (
+ IN UINT8 Value
+ )
+{
+ ASSERT (Value < 0xa0);
+ ASSERT ((Value & 0xf) < 0xa);
+ return (UINT8) ((Value >> 4) * 10 + (Value & 0xf));
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes16.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes16.c
new file mode 100644
index 0000000..52e7f71
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes16.c
@@ -0,0 +1,33 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Switches the endianess of a 16-bit integer.
+
+ This function swaps the bytes in a 16-bit unsigned value to switch the value
+ from little endian to big endian or vice versa. The byte swapped value is
+ returned.
+
+ @param Value A 16-bit unsigned value.
+
+ @return The byte swapped Value.
+
+**/
+UINT16
+EFIAPI
+SwapBytes16 (
+ IN UINT16 Value
+ )
+{
+ return (UINT16) ((Value<< 8) | (Value>> 8));
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes32.c
new file mode 100644
index 0000000..5109ad5
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes32.c
@@ -0,0 +1,39 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Switches the endianess of a 32-bit integer.
+
+ This function swaps the bytes in a 32-bit unsigned value to switch the value
+ from little endian to big endian or vice versa. The byte swapped value is
+ returned.
+
+ @param Value A 32-bit unsigned value.
+
+ @return The byte swapped Value.
+
+**/
+UINT32
+EFIAPI
+SwapBytes32 (
+ IN UINT32 Value
+ )
+{
+ UINT32 LowerBytes;
+ UINT32 HigherBytes;
+
+ LowerBytes = (UINT32) SwapBytes16 ((UINT16) Value);
+ HigherBytes = (UINT32) SwapBytes16 ((UINT16) (Value >> 16));
+
+ return (LowerBytes << 16 | HigherBytes);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes64.c
new file mode 100644
index 0000000..500f76d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwapBytes64.c
@@ -0,0 +1,33 @@
+/** @file
+ Math worker functions.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Switches the endianess of a 64-bit integer.
+
+ This function swaps the bytes in a 64-bit unsigned value to switch the value
+ from little endian to big endian or vice versa. The byte swapped value is
+ returned.
+
+ @param Value A 64-bit unsigned value.
+
+ @return The byte swapped Value.
+
+**/
+UINT64
+EFIAPI
+SwapBytes64 (
+ IN UINT64 Value
+ )
+{
+ return InternalMathSwapBytes64 (Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwitchStack.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwitchStack.c
new file mode 100644
index 0000000..cb9f69f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/SwitchStack.c
@@ -0,0 +1,70 @@
+/** @file
+ Switch Stack functions.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Transfers control to a function starting with a new stack.
+
+ Transfers control to the function specified by EntryPoint using the
+ new stack specified by NewStack and passing in the parameters specified
+ by Context1 and Context2. Context1 and Context2 are optional and may
+ be NULL. The function EntryPoint must never return. This function
+ supports a variable number of arguments following the NewStack parameter.
+ These additional arguments are ignored on IA-32, x64, and EBC.
+ IPF CPUs expect one additional parameter of type VOID * that specifies
+ the new backing store pointer.
+
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ @param EntryPoint A pointer to function to call with the new stack.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function.
+ @param ... This variable argument list is ignored for IA32, x64, and EBC.
+ For IPF, this variable argument list is expected to contain
+ a single parameter of type VOID * that specifies the new backing
+ store pointer.
+
+
+**/
+VOID
+EFIAPI
+SwitchStack (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack,
+ ...
+ )
+{
+ VA_LIST Marker;
+
+ ASSERT (EntryPoint != NULL);
+ ASSERT (NewStack != NULL);
+
+ //
+ // New stack must be aligned with CPU_STACK_ALIGNMENT
+ //
+ ASSERT (((UINTN)NewStack & (CPU_STACK_ALIGNMENT - 1)) == 0);
+
+ VA_START (Marker, NewStack);
+
+ InternalSwitchStack (EntryPoint, Context1, Context2, NewStack, Marker);
+
+ VA_END (Marker);
+
+ //
+ // InternalSwitchStack () will never return
+ //
+ ASSERT (FALSE);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/Unaligned.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Unaligned.c
new file mode 100644
index 0000000..a419cb8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/Unaligned.c
@@ -0,0 +1,216 @@
+/** @file
+ Unaligned access functions of BaseLib.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+
+/**
+ Reads a 16-bit value from memory that may be unaligned.
+
+ This function returns the 16-bit value pointed to by Buffer. The function
+ guarantees that the read operation does not produce an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 16-bit value that may be unaligned.
+
+ @return The 16-bit value read from Buffer.
+
+**/
+UINT16
+EFIAPI
+ReadUnaligned16 (
+ IN CONST UINT16 *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer;
+}
+
+/**
+ Writes a 16-bit value to memory that may be unaligned.
+
+ This function writes the 16-bit value specified by Value to Buffer. Value is
+ returned. The function guarantees that the write operation does not produce
+ an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 16-bit value that may be unaligned.
+ @param Value 16-bit value to write to Buffer.
+
+ @return The 16-bit value to write to Buffer.
+
+**/
+UINT16
+EFIAPI
+WriteUnaligned16 (
+ OUT UINT16 *Buffer,
+ IN UINT16 Value
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer = Value;
+}
+
+/**
+ Reads a 24-bit value from memory that may be unaligned.
+
+ This function returns the 24-bit value pointed to by Buffer. The function
+ guarantees that the read operation does not produce an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 24-bit value that may be unaligned.
+
+ @return The 24-bit value read from Buffer.
+
+**/
+UINT32
+EFIAPI
+ReadUnaligned24 (
+ IN CONST UINT32 *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer & 0xffffff;
+}
+
+/**
+ Writes a 24-bit value to memory that may be unaligned.
+
+ This function writes the 24-bit value specified by Value to Buffer. Value is
+ returned. The function guarantees that the write operation does not produce
+ an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 24-bit value that may be unaligned.
+ @param Value 24-bit value to write to Buffer.
+
+ @return The 24-bit value to write to Buffer.
+
+**/
+UINT32
+EFIAPI
+WriteUnaligned24 (
+ OUT UINT32 *Buffer,
+ IN UINT32 Value
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ *Buffer = BitFieldWrite32 (*Buffer, 0, 23, Value);
+ return Value;
+}
+
+/**
+ Reads a 32-bit value from memory that may be unaligned.
+
+ This function returns the 32-bit value pointed to by Buffer. The function
+ guarantees that the read operation does not produce an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 32-bit value that may be unaligned.
+
+ @return The 32-bit value read from Buffer.
+
+**/
+UINT32
+EFIAPI
+ReadUnaligned32 (
+ IN CONST UINT32 *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer;
+}
+
+/**
+ Writes a 32-bit value to memory that may be unaligned.
+
+ This function writes the 32-bit value specified by Value to Buffer. Value is
+ returned. The function guarantees that the write operation does not produce
+ an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 32-bit value that may be unaligned.
+ @param Value The 32-bit value to write to Buffer.
+
+ @return The 32-bit value to write to Buffer.
+
+**/
+UINT32
+EFIAPI
+WriteUnaligned32 (
+ OUT UINT32 *Buffer,
+ IN UINT32 Value
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer = Value;
+}
+
+/**
+ Reads a 64-bit value from memory that may be unaligned.
+
+ This function returns the 64-bit value pointed to by Buffer. The function
+ guarantees that the read operation does not produce an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 64-bit value that may be unaligned.
+
+ @return The 64-bit value read from Buffer.
+
+**/
+UINT64
+EFIAPI
+ReadUnaligned64 (
+ IN CONST UINT64 *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer;
+}
+
+/**
+ Writes a 64-bit value to memory that may be unaligned.
+
+ This function writes the 64-bit value specified by Value to Buffer. Value is
+ returned. The function guarantees that the write operation does not produce
+ an alignment fault.
+
+ If the Buffer is NULL, then ASSERT().
+
+ @param Buffer A pointer to a 64-bit value that may be unaligned.
+ @param Value The 64-bit value to write to Buffer.
+
+ @return The 64-bit value to write to Buffer.
+
+**/
+UINT64
+EFIAPI
+WriteUnaligned64 (
+ OUT UINT64 *Buffer,
+ IN UINT64 Value
+ )
+{
+ ASSERT (Buffer != NULL);
+
+ return *Buffer = Value;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.c
new file mode 100644
index 0000000..79eec7c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.c
@@ -0,0 +1,140 @@
+/** @file
+ Common Unit Test Host functions.
+
+ Copyright (c) 2020, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UnitTestHost.h"
+
+///
+/// Module global variable for simple system emulation of interrupt state
+///
+STATIC BOOLEAN mUnitTestHostBaseLibInterruptState;
+
+/**
+ Enables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibEnableInterrupts (
+ VOID
+ )
+{
+ mUnitTestHostBaseLibInterruptState = TRUE;
+}
+
+/**
+ Disables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibDisableInterrupts (
+ VOID
+ )
+{
+ mUnitTestHostBaseLibInterruptState = FALSE;
+}
+
+/**
+ Enables CPU interrupts for the smallest window required to capture any
+ pending interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibEnableDisableInterrupts (
+ VOID
+ )
+{
+ mUnitTestHostBaseLibInterruptState = FALSE;
+}
+
+/**
+ Set the current CPU interrupt state.
+
+ Sets the current CPU interrupt state to the state specified by
+ InterruptState. If InterruptState is TRUE, then interrupts are enabled. If
+ InterruptState is FALSE, then interrupts are disabled. InterruptState is
+ returned.
+
+ @param InterruptState TRUE if interrupts should enabled. FALSE if
+ interrupts should be disabled.
+
+ @return InterruptState
+
+**/
+BOOLEAN
+EFIAPI
+UnitTestHostBaseLibGetInterruptState (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibInterruptState;
+}
+
+/**
+ Enables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+EnableInterrupts (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.Common->EnableInterrupts ();
+}
+
+/**
+ Disables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+DisableInterrupts (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.Common->DisableInterrupts ();
+}
+
+/**
+ Enables CPU interrupts for the smallest window required to capture any
+ pending interrupts.
+
+**/
+VOID
+EFIAPI
+EnableDisableInterrupts (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.Common->EnableDisableInterrupts ();
+}
+
+/**
+ Set the current CPU interrupt state.
+
+ Sets the current CPU interrupt state to the state specified by
+ InterruptState. If InterruptState is TRUE, then interrupts are enabled. If
+ InterruptState is FALSE, then interrupts are disabled. InterruptState is
+ returned.
+
+ @param InterruptState TRUE if interrupts should enabled. FALSE if
+ interrupts should be disabled.
+
+ @return InterruptState
+
+**/
+BOOLEAN
+EFIAPI
+GetInterruptState (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.Common->GetInterruptState ();
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.h b/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.h
new file mode 100644
index 0000000..42bc6b7
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/UnitTestHost.h
@@ -0,0 +1,66 @@
+/** @file
+ Unit Test Host functions.
+
+ Copyright (c) 2020, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __UNIT_TEST_HOST_H__
+#define __UNIT_TEST_HOST_H__
+
+#include "BaseLibInternals.h"
+#include <Library/UnitTestHostBaseLib.h>
+
+/**
+ Enables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibEnableInterrupts (
+ VOID
+ );
+
+/**
+ Disables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibDisableInterrupts (
+ VOID
+ );
+
+/**
+ Enables CPU interrupts for the smallest window required to capture any
+ pending interrupts.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibEnableDisableInterrupts (
+ VOID
+ );
+
+/**
+ Set the current CPU interrupt state.
+
+ Sets the current CPU interrupt state to the state specified by
+ InterruptState. If InterruptState is TRUE, then interrupts are enabled. If
+ InterruptState is FALSE, then interrupts are disabled. InterruptState is
+ returned.
+
+ @param InterruptState TRUE if interrupts should enabled. FALSE if
+ interrupts should be disabled.
+
+ @return InterruptState
+
+**/
+BOOLEAN
+EFIAPI
+UnitTestHostBaseLibGetInterruptState (
+ VOID
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.c
new file mode 100644
index 0000000..c626ef8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.c
@@ -0,0 +1,33 @@
+/** @file
+ CpuBreakpoint function.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+/**
+ Microsoft Visual Studio 7.1 Function Prototypes for I/O Intrinsics.
+**/
+
+void __debugbreak (VOID);
+
+#pragma intrinsic(__debugbreak)
+
+/**
+ Generates a breakpoint on the CPU.
+
+ Generates a breakpoint on the CPU. The breakpoint must be implemented such
+ that code can resume normal execution after the breakpoint.
+
+**/
+VOID
+EFIAPI
+CpuBreakpoint (
+ VOID
+ )
+{
+ __debugbreak ();
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.nasm
new file mode 100644
index 0000000..5bdbe32
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuBreakpoint.nasm
@@ -0,0 +1,31 @@
+;------------------------------------------------------------------------------ ;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; CpuBreakpoint.Asm
+;
+; Abstract:
+;
+; CpuBreakpoint function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; CpuBreakpoint (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(CpuBreakpoint)
+ASM_PFX(CpuBreakpoint):
+ int 3
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuId.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuId.nasm
new file mode 100644
index 0000000..bb83017
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuId.nasm
@@ -0,0 +1,58 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; CpuId.Asm
+;
+; Abstract:
+;
+; AsmCpuid function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmCpuid (
+; IN UINT32 RegisterInEax,
+; OUT UINT32 *RegisterOutEax OPTIONAL,
+; OUT UINT32 *RegisterOutEbx OPTIONAL,
+; OUT UINT32 *RegisterOutEcx OPTIONAL,
+; OUT UINT32 *RegisterOutEdx OPTIONAL
+; )
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmCpuid)
+ASM_PFX(AsmCpuid):
+ push rbx
+ mov eax, ecx
+ push rax ; save Index on stack
+ push rdx
+ cpuid
+ test r9, r9
+ jz .0
+ mov [r9], ecx
+.0:
+ pop rcx
+ jrcxz .1
+ mov [rcx], eax
+.1:
+ mov rcx, r8
+ jrcxz .2
+ mov [rcx], ebx
+.2:
+ mov rcx, [rsp + 0x38]
+ jrcxz .3
+ mov [rcx], edx
+.3:
+ pop rax ; restore Index to rax as return value
+ pop rbx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuIdEx.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuIdEx.nasm
new file mode 100644
index 0000000..fd5caa3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuIdEx.nasm
@@ -0,0 +1,60 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; CpuIdEx.Asm
+;
+; Abstract:
+;
+; AsmCpuidEx function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT32
+; EFIAPI
+; AsmCpuidEx (
+; IN UINT32 RegisterInEax,
+; IN UINT32 RegisterInEcx,
+; OUT UINT32 *RegisterOutEax OPTIONAL,
+; OUT UINT32 *RegisterOutEbx OPTIONAL,
+; OUT UINT32 *RegisterOutEcx OPTIONAL,
+; OUT UINT32 *RegisterOutEdx OPTIONAL
+; )
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmCpuidEx)
+ASM_PFX(AsmCpuidEx):
+ push rbx
+ mov eax, ecx
+ mov ecx, edx
+ push rax ; save Index on stack
+ cpuid
+ mov r10, [rsp + 0x38]
+ test r10, r10
+ jz .0
+ mov [r10], ecx
+.0:
+ mov rcx, r8
+ jrcxz .1
+ mov [rcx], eax
+.1:
+ mov rcx, r9
+ jrcxz .2
+ mov [rcx], ebx
+.2:
+ mov rcx, [rsp + 0x40]
+ jrcxz .3
+ mov [rcx], edx
+.3:
+ pop rax ; restore Index to rax as return value
+ pop rbx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuPause.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuPause.nasm
new file mode 100644
index 0000000..ca35197
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/CpuPause.nasm
@@ -0,0 +1,31 @@
+;------------------------------------------------------------------------------ ;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; CpuPause.Asm
+;
+; Abstract:
+;
+; CpuPause function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; CpuPause (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(CpuPause)
+ASM_PFX(CpuPause):
+ pause
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableCache.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableCache.nasm
new file mode 100644
index 0000000..93f5f75
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableCache.nasm
@@ -0,0 +1,37 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; DisableCache.Asm
+;
+; Abstract:
+;
+; Set the CD bit of CR0 to 1, clear the NW bit of CR0 to 0, and flush all caches with a
+; WBINVD instruction.
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmDisableCache (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmDisableCache)
+ASM_PFX(AsmDisableCache):
+ mov rax, cr0
+ bts rax, 30
+ btr rax, 29
+ mov cr0, rax
+ wbinvd
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableInterrupts.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableInterrupts.nasm
new file mode 100644
index 0000000..43c7e5d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisableInterrupts.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; DisableInterrupts.Asm
+;
+; Abstract:
+;
+; DisableInterrupts function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; DisableInterrupts (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(DisableInterrupts)
+ASM_PFX(DisableInterrupts):
+ cli
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisablePaging64.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisablePaging64.nasm
new file mode 100644
index 0000000..c76ed1a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/DisablePaging64.nasm
@@ -0,0 +1,78 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; DisablePaging64.Asm
+;
+; Abstract:
+;
+; AsmDisablePaging64 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86DisablePaging64 (
+; IN UINT16 Cs,
+; IN UINT32 EntryPoint,
+; IN UINT32 Context1, OPTIONAL
+; IN UINT32 Context2, OPTIONAL
+; IN UINT32 NewStack
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86DisablePaging64)
+ASM_PFX(InternalX86DisablePaging64):
+ cli
+ lea rsi, [.0] ; rsi <- The start address of transition code
+ mov edi, [rsp + 0x28] ; rdi <- New stack
+ lea rax, [mTransitionEnd] ; rax <- end of transition code
+ sub rax, rsi ; rax <- The size of transition piece code
+ add rax, 4 ; Round RAX up to the next 4 byte boundary
+ and al, 0xfc
+ sub rdi, rax ; rdi <- Use stack to hold transition code
+ mov r10d, edi ; r10 <- The start address of transicition code below 4G
+ push rcx ; save rcx to stack
+ mov rcx, rax ; rcx <- The size of transition piece code
+ rep movsb ; copy transition code to top of new stack which must be below 4GB
+ pop rcx ; restore rcx
+
+ mov esi, r8d
+ mov edi, r9d
+ mov eax, r10d ; eax <- start of the transition code on the stack
+ sub eax, 4 ; eax <- One slot below transition code on the stack
+ push rcx ; push Cs to stack
+ push r10 ; push address of tansition code on stack
+ DB 0x48 ; prefix to composite "retq" with next "retf"
+ retf ; Use far return to load CS register from stack
+
+; Start of transition code
+.0:
+ mov esp, eax ; set up new stack
+ mov rax, cr0
+ btr eax, 31 ; Clear CR0.PG
+ mov cr0, rax ; disable paging and caches
+
+ mov ebx, edx ; save EntryPoint to rbx, for rdmsr will overwrite rdx
+ mov ecx, 0xc0000080
+ rdmsr
+ and ah, ~ 1 ; clear LME
+ wrmsr
+ mov rax, cr4
+ and al, ~ (1 << 5) ; clear PAE
+ mov cr4, rax
+ push rdi ; push Context2
+ push rsi ; push Context1
+ call rbx ; transfer control to EntryPoint
+ hlt ; no one should get here
+
+mTransitionEnd:
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableCache.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableCache.nasm
new file mode 100644
index 0000000..b6fae3c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableCache.nasm
@@ -0,0 +1,37 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; EnableCache.Asm
+;
+; Abstract:
+;
+; Flush all caches with a WBINVD instruction, clear the CD bit of CR0 to 0, and clear
+; the NW bit of CR0 to 0
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmEnableCache (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmEnableCache)
+ASM_PFX(AsmEnableCache):
+ wbinvd
+ mov rax, cr0
+ btr rax, 29
+ btr rax, 30
+ mov cr0, rax
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableDisableInterrupts.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableDisableInterrupts.nasm
new file mode 100644
index 0000000..3c7e9e7
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableDisableInterrupts.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; EnableDisableInterrupts.Asm
+;
+; Abstract:
+;
+; EnableDisableInterrupts function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; EnableDisableInterrupts (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(EnableDisableInterrupts)
+ASM_PFX(EnableDisableInterrupts):
+ sti
+ cli
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableInterrupts.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableInterrupts.nasm
new file mode 100644
index 0000000..6057afd
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/EnableInterrupts.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; EnableInterrupts.Asm
+;
+; Abstract:
+;
+; EnableInterrupts function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; EnableInterrupts (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(EnableInterrupts)
+ASM_PFX(EnableInterrupts):
+ sti
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FlushCacheLine.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FlushCacheLine.nasm
new file mode 100644
index 0000000..1effabe
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FlushCacheLine.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; FlushCacheLine.Asm
+;
+; Abstract:
+;
+; AsmFlushCacheLine function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID *
+; EFIAPI
+; AsmFlushCacheLine (
+; IN VOID *LinearAddress
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmFlushCacheLine)
+ASM_PFX(AsmFlushCacheLine):
+ clflush [rcx]
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxRestore.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxRestore.nasm
new file mode 100644
index 0000000..261981e
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxRestore.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; FxRestore.Asm
+;
+; Abstract:
+;
+; AsmFxRestore function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86FxRestore (
+; IN CONST IA32_FX_BUFFER *Buffer
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86FxRestore)
+ASM_PFX(InternalX86FxRestore):
+ fxrstor [rcx]
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxSave.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxSave.nasm
new file mode 100644
index 0000000..fafe24d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/FxSave.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; FxSave.Asm
+;
+; Abstract:
+;
+; AsmFxSave function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86FxSave (
+; OUT IA32_FX_BUFFER *Buffer
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86FxSave)
+ASM_PFX(InternalX86FxSave):
+ fxsave [rcx]
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInline.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInline.c
new file mode 100644
index 0000000..40a208f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInline.c
@@ -0,0 +1,562 @@
+/** @file
+ GCC inline implementation of BaseLib processor specific functions.
+
+ Copyright (c) 2006 - 2020, Intel Corporation. All rights reserved.<BR>
+ Portions copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+
+
+
+/**
+ Used to serialize load and store operations.
+
+ All loads and stores that proceed calls to this function are guaranteed to be
+ globally visible when this function returns.
+
+**/
+VOID
+EFIAPI
+MemoryFence (
+ VOID
+ )
+{
+ // This is a little bit of overkill and it is more about the compiler that it is
+ // actually processor synchronization. This is like the _ReadWriteBarrier
+ // Microsoft specific intrinsic
+ __asm__ __volatile__ ("":::"memory");
+}
+
+
+/**
+ Requests CPU to pause for a short period of time.
+
+ Requests CPU to pause for a short period of time. Typically used in MP
+ systems to prevent memory starvation while waiting for a spin lock.
+
+**/
+VOID
+EFIAPI
+CpuPause (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("pause");
+}
+
+
+/**
+ Generates a breakpoint on the CPU.
+
+ Generates a breakpoint on the CPU. The breakpoint must be implemented such
+ that code can resume normal execution after the breakpoint.
+
+**/
+VOID
+EFIAPI
+CpuBreakpoint (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("int $3");
+}
+
+
+/**
+ Reads the current value of the EFLAGS register.
+
+ Reads and returns the current value of the EFLAGS register. This function is
+ only available on IA-32 and X64. This returns a 32-bit value on IA-32 and a
+ 64-bit value on X64.
+
+ @return EFLAGS on IA-32 or RFLAGS on X64.
+
+**/
+UINTN
+EFIAPI
+AsmReadEflags (
+ VOID
+ )
+{
+ UINTN Eflags;
+
+ __asm__ __volatile__ (
+ "pushfq \n\t"
+ "pop %0 "
+ : "=r" (Eflags) // %0
+ );
+
+ return Eflags;
+}
+
+/**
+ Save the current floating point/SSE/SSE2 context to a buffer.
+
+ Saves the current floating point/SSE/SSE2 state to the buffer specified by
+ Buffer. Buffer must be aligned on a 16-byte boundary. This function is only
+ available on IA-32 and X64.
+
+ @param Buffer The pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+InternalX86FxSave (
+ OUT IA32_FX_BUFFER *Buffer
+ )
+{
+ __asm__ __volatile__ (
+ "fxsave %0"
+ :
+ : "m" (*Buffer) // %0
+ );
+}
+
+
+/**
+ Restores the current floating point/SSE/SSE2 context from a buffer.
+
+ Restores the current floating point/SSE/SSE2 state from the buffer specified
+ by Buffer. Buffer must be aligned on a 16-byte boundary. This function is
+ only available on IA-32 and X64.
+
+ @param Buffer The pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+InternalX86FxRestore (
+ IN CONST IA32_FX_BUFFER *Buffer
+ )
+{
+ __asm__ __volatile__ (
+ "fxrstor %0"
+ :
+ : "m" (*Buffer) // %0
+ );
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #0 (MM0).
+
+ Reads and returns the current value of MM0. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM0.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm0 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm0, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #1 (MM1).
+
+ Reads and returns the current value of MM1. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM1.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm1 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm1, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #2 (MM2).
+
+ Reads and returns the current value of MM2. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM2.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm2 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm2, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #3 (MM3).
+
+ Reads and returns the current value of MM3. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM3.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm3 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm3, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #4 (MM4).
+
+ Reads and returns the current value of MM4. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM4.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm4 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm4, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #5 (MM5).
+
+ Reads and returns the current value of MM5. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM5.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm5 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm5, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #6 (MM6).
+
+ Reads and returns the current value of MM6. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM6.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm6 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm6, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of 64-bit MMX Register #7 (MM7).
+
+ Reads and returns the current value of MM7. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of MM7.
+
+**/
+UINT64
+EFIAPI
+AsmReadMm7 (
+ VOID
+ )
+{
+ UINT64 Data;
+
+ __asm__ __volatile__ (
+ "movd %%mm7, %0 \n\t"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #0 (MM0).
+
+ Writes the current value of MM0. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM0.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm0 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm0" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #1 (MM1).
+
+ Writes the current value of MM1. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM1.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm1 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm1" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #2 (MM2).
+
+ Writes the current value of MM2. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM2.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm2 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm2" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #3 (MM3).
+
+ Writes the current value of MM3. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM3.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm3 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm3" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #4 (MM4).
+
+ Writes the current value of MM4. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM4.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm4 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm4" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #5 (MM5).
+
+ Writes the current value of MM5. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM5.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm5 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm5" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #6 (MM6).
+
+ Writes the current value of MM6. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM6.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm6 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm6" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Writes the current value of 64-bit MMX Register #7 (MM7).
+
+ Writes the current value of MM7. This function is only available on IA32 and
+ X64.
+
+ @param Value The 64-bit value to write to MM7.
+
+**/
+VOID
+EFIAPI
+AsmWriteMm7 (
+ IN UINT64 Value
+ )
+{
+ __asm__ __volatile__ (
+ "movd %0, %%mm7" // %0
+ :
+ : "m" (Value)
+ );
+}
+
+
+/**
+ Reads the current value of Time Stamp Counter (TSC).
+
+ Reads and returns the current value of TSC. This function is only available
+ on IA-32 and X64.
+
+ @return The current value of TSC
+
+**/
+UINT64
+EFIAPI
+AsmReadTsc (
+ VOID
+ )
+{
+ UINT32 LowData;
+ UINT32 HiData;
+
+ __asm__ __volatile__ (
+ "rdtsc"
+ : "=a" (LowData),
+ "=d" (HiData)
+ );
+
+ return (((UINT64)HiData) << 32) | LowData;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInlinePriv.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInlinePriv.c
new file mode 100644
index 0000000..98be19b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/GccInlinePriv.c
@@ -0,0 +1,1234 @@
+/** @file
+ GCC inline implementation of BaseLib processor specific functions that use
+ privlidged instructions.
+
+ Copyright (c) 2006 - 2020, Intel Corporation. All rights reserved.<BR>
+ Portions copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Enables CPU interrupts.
+
+ Enables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+EnableInterrupts (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("sti"::: "memory");
+}
+
+
+/**
+ Disables CPU interrupts.
+
+ Disables CPU interrupts.
+
+**/
+VOID
+EFIAPI
+DisableInterrupts (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("cli"::: "memory");
+}
+
+/**
+ Returns a 64-bit Machine Specific Register(MSR).
+
+ Reads and returns the 64-bit MSR specified by Index. No parameter checking is
+ performed on Index, and some Index values may cause CPU exceptions. The
+ caller must either guarantee that Index is valid, or the caller must set up
+ exception handlers to catch the exceptions. This function is only available
+ on IA-32 and X64.
+
+ @param Index The 32-bit MSR index to read.
+
+ @return The value of the MSR identified by Index.
+
+**/
+UINT64
+EFIAPI
+AsmReadMsr64 (
+ IN UINT32 Index
+ )
+{
+ UINT32 LowData;
+ UINT32 HighData;
+
+ __asm__ __volatile__ (
+ "rdmsr"
+ : "=a" (LowData), // %0
+ "=d" (HighData) // %1
+ : "c" (Index) // %2
+ );
+
+ return (((UINT64)HighData) << 32) | LowData;
+}
+
+/**
+ Writes a 64-bit value to a Machine Specific Register(MSR), and returns the
+ value.
+
+ Writes the 64-bit value specified by Value to the MSR specified by Index. The
+ 64-bit value written to the MSR is returned. No parameter checking is
+ performed on Index or Value, and some of these may cause CPU exceptions. The
+ caller must either guarantee that Index and Value are valid, or the caller
+ must establish proper exception handlers. This function is only available on
+ IA-32 and X64.
+
+ @param Index The 32-bit MSR index to write.
+ @param Value The 64-bit value to write to the MSR.
+
+ @return Value
+
+**/
+UINT64
+EFIAPI
+AsmWriteMsr64 (
+ IN UINT32 Index,
+ IN UINT64 Value
+ )
+{
+ UINT32 LowData;
+ UINT32 HighData;
+
+ LowData = (UINT32)(Value);
+ HighData = (UINT32)(Value >> 32);
+
+ __asm__ __volatile__ (
+ "wrmsr"
+ :
+ : "c" (Index),
+ "a" (LowData),
+ "d" (HighData)
+ );
+
+ return Value;
+}
+
+/**
+ Reads the current value of the Control Register 0 (CR0).
+
+ Reads and returns the current value of CR0. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of the Control Register 0 (CR0).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr0 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%cr0,%0"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of the Control Register 2 (CR2).
+
+ Reads and returns the current value of CR2. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of the Control Register 2 (CR2).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr2 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%cr2, %0"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+/**
+ Reads the current value of the Control Register 3 (CR3).
+
+ Reads and returns the current value of CR3. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of the Control Register 3 (CR3).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr3 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%cr3, %0"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of the Control Register 4 (CR4).
+
+ Reads and returns the current value of CR4. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of the Control Register 4 (CR4).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr4 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%cr4, %0"
+ : "=r" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Writes a value to Control Register 0 (CR0).
+
+ Writes and returns a new value to CR0. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Cr0 The value to write to CR0.
+
+ @return The value written to CR0.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr0 (
+ UINTN Cr0
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%cr0"
+ :
+ : "r" (Cr0)
+ );
+ return Cr0;
+}
+
+
+/**
+ Writes a value to Control Register 2 (CR2).
+
+ Writes and returns a new value to CR2. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Cr2 The value to write to CR2.
+
+ @return The value written to CR2.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr2 (
+ UINTN Cr2
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%cr2"
+ :
+ : "r" (Cr2)
+ );
+ return Cr2;
+}
+
+
+/**
+ Writes a value to Control Register 3 (CR3).
+
+ Writes and returns a new value to CR3. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Cr3 The value to write to CR3.
+
+ @return The value written to CR3.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr3 (
+ UINTN Cr3
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%cr3"
+ :
+ : "r" (Cr3)
+ );
+ return Cr3;
+}
+
+
+/**
+ Writes a value to Control Register 4 (CR4).
+
+ Writes and returns a new value to CR4. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Cr4 The value to write to CR4.
+
+ @return The value written to CR4.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr4 (
+ UINTN Cr4
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%cr4"
+ :
+ : "r" (Cr4)
+ );
+ return Cr4;
+}
+
+
+/**
+ Reads the current value of Debug Register 0 (DR0).
+
+ Reads and returns the current value of DR0. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr0 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr0, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 1 (DR1).
+
+ Reads and returns the current value of DR1. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr1 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr1, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 2 (DR2).
+
+ Reads and returns the current value of DR2. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr2 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr2, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 3 (DR3).
+
+ Reads and returns the current value of DR3. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr3 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr3, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 4 (DR4).
+
+ Reads and returns the current value of DR4. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr4 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr4, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 5 (DR5).
+
+ Reads and returns the current value of DR5. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr5 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr5, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 6 (DR6).
+
+ Reads and returns the current value of DR6. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr6 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr6, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Debug Register 7 (DR7).
+
+ Reads and returns the current value of DR7. This function is only available
+ on IA-32 and X64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ X64.
+
+ @return The value of Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr7 (
+ VOID
+ )
+{
+ UINTN Data;
+
+ __asm__ __volatile__ (
+ "mov %%dr7, %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Writes a value to Debug Register 0 (DR0).
+
+ Writes and returns a new value to DR0. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr0 The value to write to Dr0.
+
+ @return The value written to Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr0 (
+ UINTN Dr0
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr0"
+ :
+ : "r" (Dr0)
+ );
+ return Dr0;
+}
+
+
+/**
+ Writes a value to Debug Register 1 (DR1).
+
+ Writes and returns a new value to DR1. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr1 The value to write to Dr1.
+
+ @return The value written to Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr1 (
+ UINTN Dr1
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr1"
+ :
+ : "r" (Dr1)
+ );
+ return Dr1;
+}
+
+
+/**
+ Writes a value to Debug Register 2 (DR2).
+
+ Writes and returns a new value to DR2. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr2 The value to write to Dr2.
+
+ @return The value written to Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr2 (
+ UINTN Dr2
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr2"
+ :
+ : "r" (Dr2)
+ );
+ return Dr2;
+}
+
+
+/**
+ Writes a value to Debug Register 3 (DR3).
+
+ Writes and returns a new value to DR3. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr3 The value to write to Dr3.
+
+ @return The value written to Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr3 (
+ UINTN Dr3
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr3"
+ :
+ : "r" (Dr3)
+ );
+ return Dr3;
+}
+
+
+/**
+ Writes a value to Debug Register 4 (DR4).
+
+ Writes and returns a new value to DR4. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr4 The value to write to Dr4.
+
+ @return The value written to Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr4 (
+ UINTN Dr4
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr4"
+ :
+ : "r" (Dr4)
+ );
+ return Dr4;
+}
+
+
+/**
+ Writes a value to Debug Register 5 (DR5).
+
+ Writes and returns a new value to DR5. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr5 The value to write to Dr5.
+
+ @return The value written to Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr5 (
+ UINTN Dr5
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr5"
+ :
+ : "r" (Dr5)
+ );
+ return Dr5;
+}
+
+
+/**
+ Writes a value to Debug Register 6 (DR6).
+
+ Writes and returns a new value to DR6. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr6 The value to write to Dr6.
+
+ @return The value written to Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr6 (
+ UINTN Dr6
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr6"
+ :
+ : "r" (Dr6)
+ );
+ return Dr6;
+}
+
+
+/**
+ Writes a value to Debug Register 7 (DR7).
+
+ Writes and returns a new value to DR7. This function is only available on
+ IA-32 and X64. This writes a 32-bit value on IA-32 and a 64-bit value on X64.
+
+ @param Dr7 The value to write to Dr7.
+
+ @return The value written to Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr7 (
+ UINTN Dr7
+ )
+{
+ __asm__ __volatile__ (
+ "mov %0, %%dr7"
+ :
+ : "r" (Dr7)
+ );
+ return Dr7;
+}
+
+
+/**
+ Reads the current value of Code Segment Register (CS).
+
+ Reads and returns the current value of CS. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of CS.
+
+**/
+UINT16
+EFIAPI
+AsmReadCs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%cs, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Data Segment Register (DS).
+
+ Reads and returns the current value of DS. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of DS.
+
+**/
+UINT16
+EFIAPI
+AsmReadDs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%ds, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Extra Segment Register (ES).
+
+ Reads and returns the current value of ES. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of ES.
+
+**/
+UINT16
+EFIAPI
+AsmReadEs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%es, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of FS Data Segment Register (FS).
+
+ Reads and returns the current value of FS. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of FS.
+
+**/
+UINT16
+EFIAPI
+AsmReadFs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%fs, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of GS Data Segment Register (GS).
+
+ Reads and returns the current value of GS. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of GS.
+
+**/
+UINT16
+EFIAPI
+AsmReadGs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%gs, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Stack Segment Register (SS).
+
+ Reads and returns the current value of SS. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of SS.
+
+**/
+UINT16
+EFIAPI
+AsmReadSs (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "mov %%ds, %0"
+ :"=a" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current value of Task Register (TR).
+
+ Reads and returns the current value of TR. This function is only available on
+ IA-32 and X64.
+
+ @return The current value of TR.
+
+**/
+UINT16
+EFIAPI
+AsmReadTr (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "str %0"
+ : "=r" (Data)
+ );
+
+ return Data;
+}
+
+
+/**
+ Reads the current Global Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current GDTR descriptor and returns it in Gdtr. This
+ function is only available on IA-32 and X64.
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86ReadGdtr (
+ OUT IA32_DESCRIPTOR *Gdtr
+ )
+{
+ __asm__ __volatile__ (
+ "sgdt %0"
+ : "=m" (*Gdtr)
+ );
+}
+
+
+/**
+ Writes the current Global Descriptor Table Register (GDTR) descriptor.
+
+ Writes and the current GDTR descriptor specified by Gdtr. This function is
+ only available on IA-32 and X64.
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86WriteGdtr (
+ IN CONST IA32_DESCRIPTOR *Gdtr
+ )
+{
+ __asm__ __volatile__ (
+ "lgdt %0"
+ :
+ : "m" (*Gdtr)
+ );
+
+}
+
+
+/**
+ Reads the current Interrupt Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current IDTR descriptor and returns it in Idtr. This
+ function is only available on IA-32 and X64.
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86ReadIdtr (
+ OUT IA32_DESCRIPTOR *Idtr
+ )
+{
+ __asm__ __volatile__ (
+ "sidt %0"
+ : "=m" (*Idtr)
+ );
+}
+
+
+/**
+ Writes the current Interrupt Descriptor Table Register(GDTR) descriptor.
+
+ Writes the current IDTR descriptor and returns it in Idtr. This function is
+ only available on IA-32 and X64.
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+InternalX86WriteIdtr (
+ IN CONST IA32_DESCRIPTOR *Idtr
+ )
+{
+ __asm__ __volatile__ (
+ "lidt %0"
+ :
+ : "m" (*Idtr)
+ );
+}
+
+
+/**
+ Reads the current Local Descriptor Table Register(LDTR) selector.
+
+ Reads and returns the current 16-bit LDTR descriptor value. This function is
+ only available on IA-32 and X64.
+
+ @return The current selector of LDT.
+
+**/
+UINT16
+EFIAPI
+AsmReadLdtr (
+ VOID
+ )
+{
+ UINT16 Data;
+
+ __asm__ __volatile__ (
+ "sldt %0"
+ : "=g" (Data) // %0
+ );
+
+ return Data;
+}
+
+
+/**
+ Writes the current Local Descriptor Table Register (GDTR) selector.
+
+ Writes and the current LDTR descriptor specified by Ldtr. This function is
+ only available on IA-32 and X64.
+
+ @param Ldtr 16-bit LDTR selector value.
+
+**/
+VOID
+EFIAPI
+AsmWriteLdtr (
+ IN UINT16 Ldtr
+ )
+{
+ __asm__ __volatile__ (
+ "lldtw %0"
+ :
+ : "g" (Ldtr) // %0
+ );
+}
+
+/**
+ Reads the current value of a Performance Counter (PMC).
+
+ Reads and returns the current value of performance counter specified by
+ Index. This function is only available on IA-32 and X64.
+
+ @param Index The 32-bit Performance Counter index to read.
+
+ @return The value of the PMC specified by Index.
+
+**/
+UINT64
+EFIAPI
+AsmReadPmc (
+ IN UINT32 Index
+ )
+{
+ UINT32 LowData;
+ UINT32 HiData;
+
+ __asm__ __volatile__ (
+ "rdpmc"
+ : "=a" (LowData),
+ "=d" (HiData)
+ : "c" (Index)
+ );
+
+ return (((UINT64)HiData) << 32) | LowData;
+}
+
+/**
+ Sets up a monitor buffer that is used by AsmMwait().
+
+ Executes a MONITOR instruction with the register state specified by Eax, Ecx
+ and Edx. Returns Eax. This function is only available on IA-32 and X64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+ @param Edx The value to load into EDX or RDX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+AsmMonitor (
+ IN UINTN Eax,
+ IN UINTN Ecx,
+ IN UINTN Edx
+ )
+{
+ __asm__ __volatile__ (
+ "monitor"
+ :
+ : "a" (Eax),
+ "c" (Ecx),
+ "d" (Edx)
+ );
+
+ return Eax;
+}
+
+/**
+ Executes an MWAIT instruction.
+
+ Executes an MWAIT instruction with the register state specified by Eax and
+ Ecx. Returns Eax. This function is only available on IA-32 and X64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+AsmMwait (
+ IN UINTN Eax,
+ IN UINTN Ecx
+ )
+{
+ __asm__ __volatile__ (
+ "mwait"
+ :
+ : "a" (Eax),
+ "c" (Ecx)
+ );
+
+ return Eax;
+}
+
+/**
+ Executes a WBINVD instruction.
+
+ Executes a WBINVD instruction. This function is only available on IA-32 and
+ X64.
+
+**/
+VOID
+EFIAPI
+AsmWbinvd (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("wbinvd":::"memory");
+}
+
+/**
+ Executes a INVD instruction.
+
+ Executes a INVD instruction. This function is only available on IA-32 and
+ X64.
+
+**/
+VOID
+EFIAPI
+AsmInvd (
+ VOID
+ )
+{
+ __asm__ __volatile__ ("invd":::"memory");
+
+}
+
+
+/**
+ Flushes a cache line from all the instruction and data caches within the
+ coherency domain of the CPU.
+
+ Flushed the cache line specified by LinearAddress, and returns LinearAddress.
+ This function is only available on IA-32 and X64.
+
+ @param LinearAddress The address of the cache line to flush. If the CPU is
+ in a physical addressing mode, then LinearAddress is a
+ physical address. If the CPU is in a virtual
+ addressing mode, then LinearAddress is a virtual
+ address.
+
+ @return LinearAddress
+**/
+VOID *
+EFIAPI
+AsmFlushCacheLine (
+ IN VOID *LinearAddress
+ )
+{
+ __asm__ __volatile__ (
+ "clflush (%0)"
+ :
+ : "r" (LinearAddress)
+ : "memory"
+ );
+
+ return LinearAddress;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Invd.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Invd.nasm
new file mode 100644
index 0000000..5580f64
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Invd.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Invd.Asm
+;
+; Abstract:
+;
+; AsmInvd function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmInvd (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmInvd)
+ASM_PFX(AsmInvd):
+ invd
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Lfence.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Lfence.nasm
new file mode 100644
index 0000000..25fd074
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Lfence.nasm
@@ -0,0 +1,31 @@
+;------------------------------------------------------------------------------ ;
+; Copyright (c) 2018, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Lfence.nasm
+;
+; Abstract:
+;
+; Performs a serializing operation on all load-from-memory instructions that
+; were issued prior to the call of this function.
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmLfence (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmLfence)
+ASM_PFX(AsmLfence):
+ lfence
+ ret
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/LongJump.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/LongJump.nasm
new file mode 100644
index 0000000..59f7092
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/LongJump.nasm
@@ -0,0 +1,77 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; LongJump.Asm
+;
+; Abstract:
+;
+; Implementation of _LongJump() on x64.
+;
+;------------------------------------------------------------------------------
+
+%include "Nasm.inc"
+
+ DEFAULT REL
+ SECTION .text
+
+extern ASM_PFX(PcdGet32 (PcdControlFlowEnforcementPropertyMask))
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalLongJump (
+; IN BASE_LIBRARY_JUMP_BUFFER *JumpBuffer,
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalLongJump)
+ASM_PFX(InternalLongJump):
+
+ mov eax, [ASM_PFX(PcdGet32 (PcdControlFlowEnforcementPropertyMask))]
+ test eax, eax
+ jz CetDone
+ mov rax, cr4
+ bt eax, 23 ; check if CET is enabled
+ jnc CetDone
+
+ push rdx ; save rdx
+
+ mov rdx, [rcx + 0xF8] ; rdx = target SSP
+ READSSP_RAX
+ sub rdx, rax ; rdx = delta
+ mov rax, rdx ; rax = delta
+
+ shr rax, 3 ; rax = delta/sizeof(UINT64)
+ INCSSP_RAX
+
+ pop rdx ; restore rdx
+CetDone:
+
+ mov rbx, [rcx]
+ mov rsp, [rcx + 8]
+ mov rbp, [rcx + 0x10]
+ mov rdi, [rcx + 0x18]
+ mov rsi, [rcx + 0x20]
+ mov r12, [rcx + 0x28]
+ mov r13, [rcx + 0x30]
+ mov r14, [rcx + 0x38]
+ mov r15, [rcx + 0x40]
+ ; load non-volatile fp registers
+ ldmxcsr [rcx + 0x50]
+ movdqu xmm6, [rcx + 0x58]
+ movdqu xmm7, [rcx + 0x68]
+ movdqu xmm8, [rcx + 0x78]
+ movdqu xmm9, [rcx + 0x88]
+ movdqu xmm10, [rcx + 0x98]
+ movdqu xmm11, [rcx + 0xA8]
+ movdqu xmm12, [rcx + 0xB8]
+ movdqu xmm13, [rcx + 0xC8]
+ movdqu xmm14, [rcx + 0xD8]
+ movdqu xmm15, [rcx + 0xE8]
+ mov rax, rdx ; set return value
+ jmp qword [rcx + 0x48]
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Monitor.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Monitor.nasm
new file mode 100644
index 0000000..e1ccb83
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Monitor.nasm
@@ -0,0 +1,37 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Monitor.Asm
+;
+; Abstract:
+;
+; AsmMonitor function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmMonitor (
+; IN UINTN Eax,
+; IN UINTN Ecx,
+; IN UINTN Edx
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmMonitor)
+ASM_PFX(AsmMonitor):
+ mov eax, ecx
+ mov ecx, edx
+ mov edx, r8d
+ DB 0xf, 1, 0xc8 ; monitor
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Mwait.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Mwait.nasm
new file mode 100644
index 0000000..83fc895
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Mwait.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Mwait.Asm
+;
+; Abstract:
+;
+; AsmMwait function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmMwait (
+; IN UINTN Eax,
+; IN UINTN Ecx
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmMwait)
+ASM_PFX(AsmMwait):
+ mov eax, ecx
+ mov ecx, edx
+ DB 0xf, 1, 0xc9 ; mwait
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Non-existing.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Non-existing.c
new file mode 100644
index 0000000..e00cb7e
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Non-existing.c
@@ -0,0 +1,147 @@
+/** @file
+ Non-existing BaseLib functions on x64
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+
+/**
+ Enables the 32-bit paging mode on the CPU.
+
+ Enables the 32-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode. This function is
+ only available on IA-32. After the 32-bit paging mode is enabled, control is
+ transferred to the function specified by EntryPoint using the new stack
+ specified by NewStack and passing in the parameters specified by Context1 and
+ Context2. Context1 and Context2 are optional and may be NULL. The function
+ EntryPoint must never return.
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit protected mode with flat descriptors. This
+ means all descriptors must have a base of 0 and a limit of 4GB.
+ 3) CR0 and CR4 must be compatible with 32-bit protected mode with flat
+ descriptors.
+ 4) CR3 must point to valid page tables that will be used once the transition
+ is complete, and those page tables must guarantee that the pages for this
+ function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is enabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is enabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is enabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+InternalX86EnablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ //
+ // This function cannot work on x64 platform
+ //
+ ASSERT (FALSE);
+}
+
+/**
+ Disables the 32-bit paging mode on the CPU.
+
+ Disables the 32-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 32-paged protected
+ mode. This function is only available on IA-32. After the 32-bit paging mode
+ is disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be NULL. The function EntryPoint must never return.
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit paged mode.
+ 3) CR0, CR3, and CR4 must be compatible with 32-bit paged mode.
+ 4) CR3 must point to valid page tables that guarantee that the pages for
+ this function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is disabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is disabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is
+ disabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+InternalX86DisablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ //
+ // This function cannot work on x64 platform
+ //
+ ASSERT (FALSE);
+}
+
+
+/**
+ Enables the 64-bit paging mode on the CPU.
+
+ Enables the 64-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode with flat
+ descriptors. This function is only available on IA-32. After the 64-bit
+ paging mode is enabled, control is transferred to the function specified by
+ EntryPoint using the new stack specified by NewStack and passing in the
+ parameters specified by Context1 and Context2. Context1 and Context2 are
+ optional and may be 0. The function EntryPoint must never return.
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for long mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is enabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is enabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is enabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+InternalX86EnablePaging64 (
+ IN UINT16 Cs,
+ IN UINT64 EntryPoint,
+ IN UINT64 Context1, OPTIONAL
+ IN UINT64 Context2, OPTIONAL
+ IN UINT64 NewStack
+ )
+{
+ //
+ // This function cannot work on x64 platform.
+ //
+ ASSERT (FALSE);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/RdRand.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/RdRand.nasm
new file mode 100644
index 0000000..7e7fe99
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/RdRand.nasm
@@ -0,0 +1,77 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; RdRand.nasm
+;
+; Abstract:
+;
+; Generates random number through CPU RdRand instruction under 64-bit platform.
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; Generates a 16 bit random number through RDRAND instruction.
+; Return TRUE if Rand generated successfully, or FALSE if not.
+;
+; BOOLEAN EFIAPI InternalX86RdRand16 (UINT16 *Rand);
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86RdRand16)
+ASM_PFX(InternalX86RdRand16):
+ ; rdrand ax ; generate a 16 bit RN into eax,
+ ; CF=1 if RN generated ok, otherwise CF=0
+ db 0xf, 0xc7, 0xf0 ; rdrand r16: "0f c7 /6 ModRM:r/m(w)"
+ jc rn16_ok ; jmp if CF=1
+ xor rax, rax ; reg=0 if CF=0
+ ret ; return with failure status
+rn16_ok:
+ mov [rcx], ax
+ mov rax, 1
+ ret
+
+;------------------------------------------------------------------------------
+; Generates a 32 bit random number through RDRAND instruction.
+; Return TRUE if Rand generated successfully, or FALSE if not.
+;
+; BOOLEAN EFIAPI InternalX86RdRand32 (UINT32 *Rand);
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86RdRand32)
+ASM_PFX(InternalX86RdRand32):
+ ; rdrand eax ; generate a 32 bit RN into eax,
+ ; CF=1 if RN generated ok, otherwise CF=0
+ db 0xf, 0xc7, 0xf0 ; rdrand r32: "0f c7 /6 ModRM:r/m(w)"
+ jc rn32_ok ; jmp if CF=1
+ xor rax, rax ; reg=0 if CF=0
+ ret ; return with failure status
+rn32_ok:
+ mov [rcx], eax
+ mov rax, 1
+ ret
+
+;------------------------------------------------------------------------------
+; Generates a 64 bit random number through one RDRAND instruction.
+; Return TRUE if Rand generated successfully, or FALSE if not.
+;
+; BOOLEAN EFIAPI InternalX86RdRand64 (UINT64 *Random);
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86RdRand64)
+ASM_PFX(InternalX86RdRand64):
+ ; rdrand rax ; generate a 64 bit RN into rax,
+ ; CF=1 if RN generated ok, otherwise CF=0
+ db 0x48, 0xf, 0xc7, 0xf0 ; rdrand r64: "REX.W + 0f c7 /6 ModRM:r/m(w)"
+ jc rn64_ok ; jmp if CF=1
+ xor rax, rax ; reg=0 if CF=0
+ ret ; return with failure status
+rn64_ok:
+ mov [rcx], rax
+ mov rax, 1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr0.nasm
new file mode 100644
index 0000000..aaa6f81
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr0.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadCr0.Asm
+;
+; Abstract:
+;
+; AsmReadCr0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadCr0 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadCr0)
+ASM_PFX(AsmReadCr0):
+ mov rax, cr0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr2.nasm
new file mode 100644
index 0000000..74c4778
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr2.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadCr2.Asm
+;
+; Abstract:
+;
+; AsmReadCr2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadCr2 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadCr2)
+ASM_PFX(AsmReadCr2):
+ mov rax, cr2
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr3.nasm
new file mode 100644
index 0000000..ea8173f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr3.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadCr3.Asm
+;
+; Abstract:
+;
+; AsmReadCr3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadCr3 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadCr3)
+ASM_PFX(AsmReadCr3):
+ mov rax, cr3
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr4.nasm
new file mode 100644
index 0000000..70c2650
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCr4.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadCr4.Asm
+;
+; Abstract:
+;
+; AsmReadCr4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadCr4 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadCr4)
+ASM_PFX(AsmReadCr4):
+ mov rax, cr4
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCs.nasm
new file mode 100644
index 0000000..ec069b8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadCs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadCs.Asm
+;
+; Abstract:
+;
+; AsmReadCs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadCs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadCs)
+ASM_PFX(AsmReadCs):
+ mov eax, cs
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr0.nasm
new file mode 100644
index 0000000..7973e52
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr0.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr0.Asm
+;
+; Abstract:
+;
+; AsmReadDr0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr0 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr0)
+ASM_PFX(AsmReadDr0):
+ mov rax, dr0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr1.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr1.nasm
new file mode 100644
index 0000000..1a4b159
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr1.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr1.Asm
+;
+; Abstract:
+;
+; AsmReadDr1 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr1 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr1)
+ASM_PFX(AsmReadDr1):
+ mov rax, dr1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr2.nasm
new file mode 100644
index 0000000..d1e403d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr2.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr2.Asm
+;
+; Abstract:
+;
+; AsmReadDr2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr2 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr2)
+ASM_PFX(AsmReadDr2):
+ mov rax, dr2
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr3.nasm
new file mode 100644
index 0000000..96a9c5b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr3.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr3.Asm
+;
+; Abstract:
+;
+; AsmReadDr3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr3 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr3)
+ASM_PFX(AsmReadDr3):
+ mov rax, dr3
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr4.nasm
new file mode 100644
index 0000000..82c0a9a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr4.nasm
@@ -0,0 +1,36 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr4.Asm
+;
+; Abstract:
+;
+; AsmReadDr4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr4 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr4)
+ASM_PFX(AsmReadDr4):
+ ;
+ ; There's no obvious reason to access this register, since it's aliased to
+ ; DR7 when DE=0 or an exception generated when DE=1
+ ;
+ DB 0xf, 0x21, 0xe0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr5.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr5.nasm
new file mode 100644
index 0000000..c309c66
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr5.nasm
@@ -0,0 +1,36 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr5.Asm
+;
+; Abstract:
+;
+; AsmReadDr5 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr5 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr5)
+ASM_PFX(AsmReadDr5):
+ ;
+ ; There's no obvious reason to access this register, since it's aliased to
+ ; DR7 when DE=0 or an exception generated when DE=1
+ ;
+ DB 0xf, 0x21, 0xe8
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr6.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr6.nasm
new file mode 100644
index 0000000..7bdc103
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr6.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr6.Asm
+;
+; Abstract:
+;
+; AsmReadDr6 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr6 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr6)
+ASM_PFX(AsmReadDr6):
+ mov rax, dr6
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr7.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr7.nasm
new file mode 100644
index 0000000..219d2e4
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDr7.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDr7.Asm
+;
+; Abstract:
+;
+; AsmReadDr7 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadDr7 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDr7)
+ASM_PFX(AsmReadDr7):
+ mov rax, dr7
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDs.nasm
new file mode 100644
index 0000000..597450d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadDs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadDs.Asm
+;
+; Abstract:
+;
+; AsmReadDs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadDs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadDs)
+ASM_PFX(AsmReadDs):
+ mov eax, ds
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEflags.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEflags.nasm
new file mode 100644
index 0000000..e0a5ea0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEflags.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadEflags.Asm
+;
+; Abstract:
+;
+; AsmReadEflags function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmReadEflags (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadEflags)
+ASM_PFX(AsmReadEflags):
+ pushfq
+ pop rax
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEs.nasm
new file mode 100644
index 0000000..9633945
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadEs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadEs.Asm
+;
+; Abstract:
+;
+; AsmReadEs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadEs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadEs)
+ASM_PFX(AsmReadEs):
+ mov eax, es
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadFs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadFs.nasm
new file mode 100644
index 0000000..9d032ff
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadFs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadFs.Asm
+;
+; Abstract:
+;
+; AsmReadFs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadFs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadFs)
+ASM_PFX(AsmReadFs):
+ mov eax, fs
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGdtr.nasm
new file mode 100644
index 0000000..1712c11
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGdtr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadGdtr.Asm
+;
+; Abstract:
+;
+; AsmReadGdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86ReadGdtr (
+; OUT IA32_DESCRIPTOR *Gdtr
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86ReadGdtr)
+ASM_PFX(InternalX86ReadGdtr):
+ sgdt [rcx]
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGs.nasm
new file mode 100644
index 0000000..953fe9c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadGs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadGs.Asm
+;
+; Abstract:
+;
+; AsmReadGs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadGs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadGs)
+ASM_PFX(AsmReadGs):
+ mov eax, gs
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadIdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadIdtr.nasm
new file mode 100644
index 0000000..086ab70
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadIdtr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadIdtr.Asm
+;
+; Abstract:
+;
+; AsmReadIdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86ReadIdtr (
+; OUT IA32_DESCRIPTOR *Idtr
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86ReadIdtr)
+ASM_PFX(InternalX86ReadIdtr):
+ sidt [rcx]
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadLdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadLdtr.nasm
new file mode 100644
index 0000000..9339161
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadLdtr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadLdtr.Asm
+;
+; Abstract:
+;
+; AsmReadLdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadLdtr (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadLdtr)
+ASM_PFX(AsmReadLdtr):
+ sldt eax
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm0.nasm
new file mode 100644
index 0000000..615721b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm0.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm0.Asm
+;
+; Abstract:
+;
+; AsmReadMm0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm0 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm0)
+ASM_PFX(AsmReadMm0):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xc0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm1.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm1.nasm
new file mode 100644
index 0000000..7b27393
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm1.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm1.Asm
+;
+; Abstract:
+;
+; AsmReadMm1 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm1 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm1)
+ASM_PFX(AsmReadMm1):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xc8
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm2.nasm
new file mode 100644
index 0000000..c654b91
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm2.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm2.Asm
+;
+; Abstract:
+;
+; AsmReadMm2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm2 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm2)
+ASM_PFX(AsmReadMm2):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xd0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm3.nasm
new file mode 100644
index 0000000..88d51c0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm3.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm3.Asm
+;
+; Abstract:
+;
+; AsmReadMm3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm3 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm3)
+ASM_PFX(AsmReadMm3):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xd8
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm4.nasm
new file mode 100644
index 0000000..4252d20
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm4.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm4.Asm
+;
+; Abstract:
+;
+; AsmReadMm4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm4 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm4)
+ASM_PFX(AsmReadMm4):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xe0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm5.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm5.nasm
new file mode 100644
index 0000000..d8f530d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm5.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm5.Asm
+;
+; Abstract:
+;
+; AsmReadMm5 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm5 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm5)
+ASM_PFX(AsmReadMm5):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xe8
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm6.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm6.nasm
new file mode 100644
index 0000000..6f6883c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm6.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm6.Asm
+;
+; Abstract:
+;
+; AsmReadMm6 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm6 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm6)
+ASM_PFX(AsmReadMm6):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xf0
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm7.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm7.nasm
new file mode 100644
index 0000000..573f15d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMm7.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMm7.Asm
+;
+; Abstract:
+;
+; AsmReadMm7 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMm7 (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMm7)
+ASM_PFX(AsmReadMm7):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x7e, 0xf8
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.c
new file mode 100644
index 0000000..5ee7ca5
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.c
@@ -0,0 +1,33 @@
+/** @file
+ CpuBreakpoint function.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+/**
+ Microsoft Visual Studio 7.1 Function Prototypes for I/O Intrinsics.
+**/
+
+unsigned __int64 __readmsr (int register);
+
+#pragma intrinsic(__readmsr)
+
+/**
+ Read data to MSR.
+
+ @param Index Register index of MSR.
+
+ @return Value read from MSR.
+
+**/
+UINT64
+EFIAPI
+AsmReadMsr64 (
+ IN UINT32 Index
+ )
+{
+ return __readmsr (Index);
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.nasm
new file mode 100644
index 0000000..df69255
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadMsr64.nasm
@@ -0,0 +1,34 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadMsr64.Asm
+;
+; Abstract:
+;
+; AsmReadMsr64 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadMsr64 (
+; IN UINT32 Index
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadMsr64)
+ASM_PFX(AsmReadMsr64):
+ rdmsr ; edx & eax are zero extended
+ shl rdx, 0x20
+ or rax, rdx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadPmc.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadPmc.nasm
new file mode 100644
index 0000000..1785a09
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadPmc.nasm
@@ -0,0 +1,34 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadPmc.Asm
+;
+; Abstract:
+;
+; AsmReadPmc function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadPmc (
+; IN UINT32 PmcIndex
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadPmc)
+ASM_PFX(AsmReadPmc):
+ rdpmc
+ shl rdx, 0x20
+ or rax, rdx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadSs.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadSs.nasm
new file mode 100644
index 0000000..5fbe698
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadSs.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadSs.Asm
+;
+; Abstract:
+;
+; AsmReadSs function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadSs (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadSs)
+ASM_PFX(AsmReadSs):
+ mov eax, ss
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTr.nasm
new file mode 100644
index 0000000..492ef6c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadTr.Asm
+;
+; Abstract:
+;
+; AsmReadTr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT16
+; EFIAPI
+; AsmReadTr (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadTr)
+ASM_PFX(AsmReadTr):
+ str eax
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTsc.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTsc.nasm
new file mode 100644
index 0000000..45672d6
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/ReadTsc.nasm
@@ -0,0 +1,34 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; ReadTsc.Asm
+;
+; Abstract:
+;
+; AsmReadTsc function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmReadTsc (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmReadTsc)
+ASM_PFX(AsmReadTsc):
+ rdtsc
+ shl rdx, 0x20
+ or rax, rdx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SetJump.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SetJump.nasm
new file mode 100644
index 0000000..5a68396
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SetJump.nasm
@@ -0,0 +1,81 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; SetJump.Asm
+;
+; Abstract:
+;
+; Implementation of SetJump() on x64.
+;
+;------------------------------------------------------------------------------
+
+%include "Nasm.inc"
+
+ DEFAULT REL
+ SECTION .text
+
+extern ASM_PFX(InternalAssertJumpBuffer)
+extern ASM_PFX(PcdGet32 (PcdControlFlowEnforcementPropertyMask))
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; SetJump (
+; OUT BASE_LIBRARY_JUMP_BUFFER *JumpBuffer
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(SetJump)
+ASM_PFX(SetJump):
+ push rcx
+ add rsp, -0x20
+ call ASM_PFX(InternalAssertJumpBuffer)
+ add rsp, 0x20
+ pop rcx
+ pop rdx
+
+ xor rax, rax
+ mov [rcx + 0xF8], rax ; save 0 to SSP
+
+ mov eax, [ASM_PFX(PcdGet32 (PcdControlFlowEnforcementPropertyMask))]
+ test eax, eax
+ jz CetDone
+ mov rax, cr4
+ bt eax, 23 ; check if CET is enabled
+ jnc CetDone
+
+ mov rax, 1
+ INCSSP_RAX ; to read original SSP
+ READSSP_RAX
+ mov [rcx + 0xF8], rax ; save SSP
+
+CetDone:
+
+ mov [rcx], rbx
+ mov [rcx + 8], rsp
+ mov [rcx + 0x10], rbp
+ mov [rcx + 0x18], rdi
+ mov [rcx + 0x20], rsi
+ mov [rcx + 0x28], r12
+ mov [rcx + 0x30], r13
+ mov [rcx + 0x38], r14
+ mov [rcx + 0x40], r15
+ mov [rcx + 0x48], rdx
+ ; save non-volatile fp registers
+ stmxcsr [rcx + 0x50]
+ movdqu [rcx + 0x58], xmm6
+ movdqu [rcx + 0x68], xmm7
+ movdqu [rcx + 0x78], xmm8
+ movdqu [rcx + 0x88], xmm9
+ movdqu [rcx + 0x98], xmm10
+ movdqu [rcx + 0xA8], xmm11
+ movdqu [rcx + 0xB8], xmm12
+ movdqu [rcx + 0xC8], xmm13
+ movdqu [rcx + 0xD8], xmm14
+ movdqu [rcx + 0xE8], xmm15
+ xor rax, rax
+ jmp rdx
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SwitchStack.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SwitchStack.nasm
new file mode 100644
index 0000000..7be666d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/SwitchStack.nasm
@@ -0,0 +1,45 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; SwitchStack.Asm
+;
+; Abstract:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; Routine Description:
+;
+; Routine for switching stacks with 2 parameters
+;
+; Arguments:
+;
+; (rcx) EntryPoint - Entry point with new stack.
+; (rdx) Context1 - Parameter1 for entry point.
+; (r8) Context2 - Parameter2 for entry point.
+; (r9) NewStack - The pointer to new stack.
+;
+; Returns:
+;
+; None
+;
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalSwitchStack)
+ASM_PFX(InternalSwitchStack):
+ mov rax, rcx
+ mov rcx, rdx
+ mov rdx, r8
+ ;
+ ; Reserve space for register parameters (rcx, rdx, r8 & r9) on the stack,
+ ; in case the callee wishes to spill them.
+ ;
+ lea rsp, [r9 - 0x20]
+ call rax
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Thunk16.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Thunk16.nasm
new file mode 100644
index 0000000..e83b31c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Thunk16.nasm
@@ -0,0 +1,319 @@
+
+#include "BaseLibInternals.h"
+
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Thunk.asm
+;
+; Abstract:
+;
+; Real mode thunk
+;
+;------------------------------------------------------------------------------
+
+global ASM_PFX(m16Size)
+global ASM_PFX(mThunk16Attr)
+global ASM_PFX(m16Gdt)
+global ASM_PFX(m16GdtrBase)
+global ASM_PFX(mTransition)
+global ASM_PFX(m16Start)
+
+struc IA32_REGS
+
+ ._EDI: resd 1
+ ._ESI: resd 1
+ ._EBP: resd 1
+ ._ESP: resd 1
+ ._EBX: resd 1
+ ._EDX: resd 1
+ ._ECX: resd 1
+ ._EAX: resd 1
+ ._DS: resw 1
+ ._ES: resw 1
+ ._FS: resw 1
+ ._GS: resw 1
+ ._EFLAGS: resq 1
+ ._EIP: resd 1
+ ._CS: resw 1
+ ._SS: resw 1
+ .size:
+
+endstruc
+
+SECTION .data
+
+;
+; These are global constant to convey information to C code.
+;
+ASM_PFX(m16Size) DW ASM_PFX(InternalAsmThunk16) - ASM_PFX(m16Start)
+ASM_PFX(mThunk16Attr) DW _BackFromUserCode.ThunkAttrEnd - 4 - ASM_PFX(m16Start)
+ASM_PFX(m16Gdt) DW _NullSeg - ASM_PFX(m16Start)
+ASM_PFX(m16GdtrBase) DW _16GdtrBase - ASM_PFX(m16Start)
+ASM_PFX(mTransition) DW _EntryPoint - ASM_PFX(m16Start)
+
+SECTION .text
+
+ASM_PFX(m16Start):
+
+SavedGdt:
+ dw 0
+ dq 0
+
+;------------------------------------------------------------------------------
+; _BackFromUserCode() takes control in real mode after 'retf' has been executed
+; by user code. It will be shadowed to somewhere in memory below 1MB.
+;------------------------------------------------------------------------------
+_BackFromUserCode:
+ ;
+ ; The order of saved registers on the stack matches the order they appears
+ ; in IA32_REGS structure. This facilitates wrapper function to extract them
+ ; into that structure.
+ ;
+BITS 16
+ push ss
+ push cs
+ ;
+ ; Note: We can't use o32 on the next instruction because of a bug
+ ; in NASM 2.09.04 through 2.10rc1.
+ ;
+ call dword .Base ; push eip
+.Base:
+ push dword 0 ; reserved high order 32 bits of EFlags
+ pushfd
+ cli ; disable interrupts
+ push gs
+ push fs
+ push es
+ push ds
+ pushad
+ mov edx, strict dword 0
+.ThunkAttrEnd:
+ test dl, THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15
+ jz .1
+ mov ax, 2401h
+ int 15h
+ cli ; disable interrupts
+ jnc .2
+.1:
+ test dl, THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL
+ jz .2
+ in al, 92h
+ or al, 2
+ out 92h, al ; deactivate A20M#
+.2:
+ xor eax, eax
+ mov ax, ss
+ lea ebp, [esp + IA32_REGS.size]
+ mov [bp - IA32_REGS.size + IA32_REGS._ESP], ebp
+ mov ebx, [bp - IA32_REGS.size + IA32_REGS._EIP]
+ shl eax, 4 ; shl eax, 4
+ add ebp, eax ; add ebp, eax
+ mov eax, cs
+ shl eax, 4
+ lea eax, [eax + ebx + (.X64JmpEnd - .Base)]
+ mov [cs:bx + (.X64JmpEnd - 6 - .Base)], eax
+ mov eax, strict dword 0
+.SavedCr4End:
+ mov cr4, eax
+o32 lgdt [cs:bx + (SavedGdt - .Base)]
+ mov ecx, 0c0000080h
+ rdmsr
+ or ah, 1
+ wrmsr
+ mov eax, strict dword 0
+.SavedCr0End:
+ mov cr0, eax
+ jmp 0:strict dword 0
+.X64JmpEnd:
+BITS 64
+ nop
+ mov rsp, strict qword 0
+.SavedSpEnd:
+ nop
+ ret
+
+_EntryPoint:
+ DD _ToUserCode - ASM_PFX(m16Start)
+ DW CODE16
+_16Gdtr:
+ DW GDT_SIZE - 1
+_16GdtrBase:
+ DQ 0
+_16Idtr:
+ DW (1 << 10) - 1
+ DD 0
+
+;------------------------------------------------------------------------------
+; _ToUserCode() takes control in real mode before passing control to user code.
+; It will be shadowed to somewhere in memory below 1MB.
+;------------------------------------------------------------------------------
+_ToUserCode:
+BITS 16
+ mov ss, dx ; set new segment selectors
+ mov ds, dx
+ mov es, dx
+ mov fs, dx
+ mov gs, dx
+ mov ecx, 0c0000080h
+ mov cr0, eax ; real mode starts at next instruction
+ rdmsr
+ and ah, ~1
+ wrmsr
+ mov cr4, ebp
+ mov ss, si ; set up 16-bit stack segment
+ mov esp, ebx ; set up 16-bit stack pointer
+ call dword .Base ; push eip
+.Base:
+ pop ebp ; ebp <- address of .Base
+ push word [dword esp + IA32_REGS.size + 2]
+ lea ax, [bp + (.RealMode - .Base)]
+ push ax
+ retf ; execution begins at next instruction
+.RealMode:
+
+o32 lidt [cs:bp + (_16Idtr - .Base)]
+
+ popad
+ pop ds
+ pop es
+ pop fs
+ pop gs
+ popfd
+ lea esp, [esp + 4] ; skip high order 32 bits of EFlags
+
+o32 retf ; transfer control to user code
+
+ALIGN 8
+
+CODE16 equ _16Code - $
+DATA16 equ _16Data - $
+DATA32 equ _32Data - $
+
+_NullSeg DQ 0
+_16Code:
+ DW -1
+ DW 0
+ DB 0
+ DB 9bh
+ DB 8fh ; 16-bit segment, 4GB limit
+ DB 0
+_16Data:
+ DW -1
+ DW 0
+ DB 0
+ DB 93h
+ DB 8fh ; 16-bit segment, 4GB limit
+ DB 0
+_32Data:
+ DW -1
+ DW 0
+ DB 0
+ DB 93h
+ DB 0cfh ; 16-bit segment, 4GB limit
+ DB 0
+
+GDT_SIZE equ $ - _NullSeg
+
+;------------------------------------------------------------------------------
+; IA32_REGISTER_SET *
+; EFIAPI
+; InternalAsmThunk16 (
+; IN IA32_REGISTER_SET *RegisterSet,
+; IN OUT VOID *Transition
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalAsmThunk16)
+ASM_PFX(InternalAsmThunk16):
+BITS 64
+ push rbp
+ push rbx
+ push rsi
+ push rdi
+
+ mov ebx, ds
+ push rbx ; Save ds segment register on the stack
+ mov ebx, es
+ push rbx ; Save es segment register on the stack
+ mov ebx, ss
+ push rbx ; Save ss segment register on the stack
+
+ push fs
+ push gs
+ mov rsi, rcx
+ movzx r8d, word [rsi + IA32_REGS._SS]
+ mov edi, [rsi + IA32_REGS._ESP]
+ lea rdi, [edi - (IA32_REGS.size + 4)]
+ imul eax, r8d, 16 ; eax <- r8d(stack segment) * 16
+ mov ebx, edi ; ebx <- stack for 16-bit code
+ push IA32_REGS.size / 4
+ add edi, eax ; edi <- linear address of 16-bit stack
+ pop rcx
+ rep movsd ; copy RegSet
+ lea ecx, [rdx + (_BackFromUserCode.SavedCr4End - ASM_PFX(m16Start))]
+ mov eax, edx ; eax <- transition code address
+ and edx, 0fh
+ shl eax, 12 ; segment address in high order 16 bits
+ lea ax, [rdx + (_BackFromUserCode - ASM_PFX(m16Start))] ; offset address
+ stosd ; [edi] <- return address of user code
+
+ sgdt [rsp + 60h] ; save GDT stack in argument space
+ movzx r10, word [rsp + 60h] ; r10 <- GDT limit
+ lea r11, [rcx + (ASM_PFX(InternalAsmThunk16) - _BackFromUserCode.SavedCr4End) + 0xf]
+ and r11, ~0xf ; r11 <- 16-byte aligned shadowed GDT table in real mode buffer
+
+ mov [rcx + (SavedGdt - _BackFromUserCode.SavedCr4End)], r10w ; save the limit of shadowed GDT table
+ mov [rcx + (SavedGdt - _BackFromUserCode.SavedCr4End) + 2], r11 ; save the base address of shadowed GDT table
+
+ mov rsi, [rsp + 62h] ; rsi <- the original GDT base address
+ xchg rcx, r10 ; save rcx to r10 and initialize rcx to be the limit of GDT table
+ inc rcx ; rcx <- the size of memory to copy
+ xchg rdi, r11 ; save rdi to r11 and initialize rdi to the base address of shadowed GDT table
+ rep movsb ; perform memory copy to shadow GDT table
+ mov rcx, r10 ; restore the orignal rcx before memory copy
+ mov rdi, r11 ; restore the original rdi before memory copy
+
+ sidt [rsp + 50h] ; save IDT stack in argument space
+ mov rax, cr0
+ mov [rcx + (_BackFromUserCode.SavedCr0End - 4 - _BackFromUserCode.SavedCr4End)], eax
+ and eax, 7ffffffeh ; clear PE, PG bits
+ mov rbp, cr4
+ mov [rcx - 4], ebp ; save CR4 in _BackFromUserCode.SavedCr4End - 4
+ and ebp, ~30h ; clear PAE, PSE bits
+ mov esi, r8d ; esi <- 16-bit stack segment
+ push DATA32
+ pop rdx ; rdx <- 32-bit data segment selector
+ lgdt [rcx + (_16Gdtr - _BackFromUserCode.SavedCr4End)]
+ mov ss, edx
+ pushfq
+ lea edx, [rdx + DATA16 - DATA32]
+ lea r8, [REL .RetFromRealMode]
+ push r8
+ mov r8d, cs
+ mov [rcx + (_BackFromUserCode.X64JmpEnd - 2 - _BackFromUserCode.SavedCr4End)], r8w
+ mov [rcx + (_BackFromUserCode.SavedSpEnd - 8 - _BackFromUserCode.SavedCr4End)], rsp
+ jmp dword far [rcx + (_EntryPoint - _BackFromUserCode.SavedCr4End)]
+.RetFromRealMode:
+ popfq
+ lgdt [rsp + 60h] ; restore protected mode GDTR
+ lidt [rsp + 50h] ; restore protected mode IDTR
+ lea eax, [rbp - IA32_REGS.size]
+ pop gs
+ pop fs
+ pop rbx
+ mov ss, ebx
+ pop rbx
+ mov es, ebx
+ pop rbx
+ mov ds, ebx
+
+ pop rdi
+ pop rsi
+ pop rbx
+ pop rbp
+
+ ret
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/VmgExit.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/VmgExit.nasm
new file mode 100644
index 0000000..26f0345
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/VmgExit.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (C) 2020, Advanced Micro Devices, Inc. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; VmgExit.Asm
+;
+; Abstract:
+;
+; AsmVmgExit function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmVmgExit (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmVmgExit)
+ASM_PFX(AsmVmgExit):
+ rep vmmcall
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Wbinvd.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Wbinvd.nasm
new file mode 100644
index 0000000..90427fe
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/Wbinvd.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; Wbinvd.Asm
+;
+; Abstract:
+;
+; AsmWbinvd function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWbinvd (
+; VOID
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWbinvd)
+ASM_PFX(AsmWbinvd):
+ wbinvd
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr0.nasm
new file mode 100644
index 0000000..d351396
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr0.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteCr0.Asm
+;
+; Abstract:
+;
+; AsmWriteCr0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteCr0 (
+; UINTN Cr0
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteCr0)
+ASM_PFX(AsmWriteCr0):
+ mov cr0, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr2.nasm
new file mode 100644
index 0000000..2b6bce0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr2.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteCr2.Asm
+;
+; Abstract:
+;
+; AsmWriteCr2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteCr2 (
+; UINTN Cr2
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteCr2)
+ASM_PFX(AsmWriteCr2):
+ mov cr2, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr3.nasm
new file mode 100644
index 0000000..fb0b5ba
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr3.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteCr3.Asm
+;
+; Abstract:
+;
+; AsmWriteCr3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteCr3 (
+; UINTN Cr3
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteCr3)
+ASM_PFX(AsmWriteCr3):
+ mov cr3, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr4.nasm
new file mode 100644
index 0000000..483a996
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteCr4.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteCr4.Asm
+;
+; Abstract:
+;
+; AsmWriteCr4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteCr4 (
+; UINTN Cr4
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteCr4)
+ASM_PFX(AsmWriteCr4):
+ mov cr4, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr0.nasm
new file mode 100644
index 0000000..3c88154
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr0.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr0.Asm
+;
+; Abstract:
+;
+; AsmWriteDr0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr0 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr0)
+ASM_PFX(AsmWriteDr0):
+ mov dr0, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr1.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr1.nasm
new file mode 100644
index 0000000..6fcbbfc
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr1.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr1.Asm
+;
+; Abstract:
+;
+; AsmWriteDr1 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr1 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr1)
+ASM_PFX(AsmWriteDr1):
+ mov dr1, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr2.nasm
new file mode 100644
index 0000000..a8e0bfc
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr2.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr2.Asm
+;
+; Abstract:
+;
+; AsmWriteDr2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr2 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr2)
+ASM_PFX(AsmWriteDr2):
+ mov dr2, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr3.nasm
new file mode 100644
index 0000000..ac46ab8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr3.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr3.Asm
+;
+; Abstract:
+;
+; AsmWriteDr3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr3 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr3)
+ASM_PFX(AsmWriteDr3):
+ mov dr3, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr4.nasm
new file mode 100644
index 0000000..c4b12c9
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr4.nasm
@@ -0,0 +1,37 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr4.Asm
+;
+; Abstract:
+;
+; AsmWriteDr4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr4 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr4)
+ASM_PFX(AsmWriteDr4):
+ ;
+ ; There's no obvious reason to access this register, since it's aliased to
+ ; DR6 when DE=0 or an exception generated when DE=1
+ ;
+ DB 0xf, 0x23, 0xe1
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr5.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr5.nasm
new file mode 100644
index 0000000..986a4a9
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr5.nasm
@@ -0,0 +1,37 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr5.Asm
+;
+; Abstract:
+;
+; AsmWriteDr5 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr5 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr5)
+ASM_PFX(AsmWriteDr5):
+ ;
+ ; There's no obvious reason to access this register, since it's aliased to
+ ; DR7 when DE=0 or an exception generated when DE=1
+ ;
+ DB 0xf, 0x23, 0xe9
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr6.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr6.nasm
new file mode 100644
index 0000000..196993d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr6.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr6.Asm
+;
+; Abstract:
+;
+; AsmWriteDr6 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr6 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr6)
+ASM_PFX(AsmWriteDr6):
+ mov dr6, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr7.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr7.nasm
new file mode 100644
index 0000000..1b3c181
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteDr7.nasm
@@ -0,0 +1,33 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteDr7.Asm
+;
+; Abstract:
+;
+; AsmWriteDr7 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINTN
+; EFIAPI
+; AsmWriteDr7 (
+; IN UINTN Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteDr7)
+ASM_PFX(AsmWriteDr7):
+ mov dr7, rcx
+ mov rax, rcx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteGdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteGdtr.nasm
new file mode 100644
index 0000000..0a26ba0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteGdtr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteGdtr.Asm
+;
+; Abstract:
+;
+; AsmWriteGdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86WriteGdtr (
+; IN CONST IA32_DESCRIPTOR *Idtr
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86WriteGdtr)
+ASM_PFX(InternalX86WriteGdtr):
+ lgdt [rcx]
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteIdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteIdtr.nasm
new file mode 100644
index 0000000..c6155c0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteIdtr.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteIdtr.Asm
+;
+; Abstract:
+;
+; AsmWriteIdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; InternalX86WriteIdtr (
+; IN CONST IA32_DESCRIPTOR *Idtr
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(InternalX86WriteIdtr)
+ASM_PFX(InternalX86WriteIdtr):
+ pushfq
+ cli
+ lidt [rcx]
+ popfq
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteLdtr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteLdtr.nasm
new file mode 100644
index 0000000..55881db
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteLdtr.nasm
@@ -0,0 +1,32 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteLdtr.Asm
+;
+; Abstract:
+;
+; AsmWriteLdtr function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteLdtr (
+; IN UINT16 Ldtr
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteLdtr)
+ASM_PFX(AsmWriteLdtr):
+ lldt cx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm0.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm0.nasm
new file mode 100644
index 0000000..3f03529
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm0.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm0.Asm
+;
+; Abstract:
+;
+; AsmWriteMm0 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm0 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm0)
+ASM_PFX(AsmWriteMm0):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xc1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm1.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm1.nasm
new file mode 100644
index 0000000..f552d40
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm1.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm1.Asm
+;
+; Abstract:
+;
+; AsmWriteMm1 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm1 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm1)
+ASM_PFX(AsmWriteMm1):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xc9
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm2.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm2.nasm
new file mode 100644
index 0000000..1bd176c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm2.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm2.Asm
+;
+; Abstract:
+;
+; AsmWriteMm2 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm2 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm2)
+ASM_PFX(AsmWriteMm2):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xd1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm3.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm3.nasm
new file mode 100644
index 0000000..403f140
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm3.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm3.Asm
+;
+; Abstract:
+;
+; AsmWriteMm3 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm3 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm3)
+ASM_PFX(AsmWriteMm3):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xd9
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm4.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm4.nasm
new file mode 100644
index 0000000..d99709d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm4.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm4.Asm
+;
+; Abstract:
+;
+; AsmWriteMm4 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm4 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm4)
+ASM_PFX(AsmWriteMm4):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xe1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm5.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm5.nasm
new file mode 100644
index 0000000..0467ac4
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm5.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm5.Asm
+;
+; Abstract:
+;
+; AsmWriteMm5 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm5 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm5)
+ASM_PFX(AsmWriteMm5):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xe9
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm6.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm6.nasm
new file mode 100644
index 0000000..6d2e5eb
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm6.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm6.Asm
+;
+; Abstract:
+;
+; AsmWriteMm6 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm6 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm6)
+ASM_PFX(AsmWriteMm6):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xf1
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm7.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm7.nasm
new file mode 100644
index 0000000..de72adf
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMm7.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMm7.Asm
+;
+; Abstract:
+;
+; AsmWriteMm7 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; AsmWriteMm7 (
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMm7)
+ASM_PFX(AsmWriteMm7):
+ ;
+ ; 64-bit MASM doesn't support MMX instructions, so use opcode here
+ ;
+ DB 0x48, 0xf, 0x6e, 0xf9
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.c
new file mode 100644
index 0000000..98c5458
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.c
@@ -0,0 +1,36 @@
+/** @file
+ CpuBreakpoint function.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+/**
+ Microsoft Visual Studio 7.1 Function Prototypes for I/O Intrinsics.
+**/
+
+void __writemsr (unsigned long Register, unsigned __int64 Value);
+
+#pragma intrinsic(__writemsr)
+
+/**
+ Write data to MSR.
+
+ @param Index The register index of MSR.
+ @param Value Data wants to be written.
+
+ @return Value written to MSR.
+
+**/
+UINT64
+EFIAPI
+AsmWriteMsr64 (
+ IN UINT32 Index,
+ IN UINT64 Value
+ )
+{
+ __writemsr (Index, Value);
+ return Value;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.nasm
new file mode 100644
index 0000000..11224d3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteMsr64.nasm
@@ -0,0 +1,35 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteMsr64.Asm
+;
+; Abstract:
+;
+; AsmWriteMsr64 function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmWriteMsr64 (
+; IN UINT32 Index,
+; IN UINT64 Value
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteMsr64)
+ASM_PFX(AsmWriteMsr64):
+ mov rax, rdx ; meanwhile, rax <- return value
+ shr rdx, 0x20 ; edx:eax contains the value to write
+ wrmsr
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteTr.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteTr.nasm
new file mode 100644
index 0000000..4e364bc
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/WriteTr.nasm
@@ -0,0 +1,31 @@
+;------------------------------------------------------------------------------ ;
+; Copyright (c) 2017, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; WriteTr.nasm
+;
+; Abstract:
+;
+; Write TR register
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; AsmWriteTr (
+; UINT16 Selector
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmWriteTr)
+ASM_PFX(AsmWriteTr):
+ mov eax, ecx
+ ltr ax
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/XGetBv.nasm b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/XGetBv.nasm
new file mode 100644
index 0000000..09f3be8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X64/XGetBv.nasm
@@ -0,0 +1,34 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (C) 2020, Advanced Micro Devices, Inc. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Module Name:
+;
+; XGetBv.Asm
+;
+; Abstract:
+;
+; AsmXgetBv function
+;
+; Notes:
+;
+;------------------------------------------------------------------------------
+
+ DEFAULT REL
+ SECTION .text
+
+;------------------------------------------------------------------------------
+; UINT64
+; EFIAPI
+; AsmXGetBv (
+; IN UINT32 Index
+; );
+;------------------------------------------------------------------------------
+global ASM_PFX(AsmXGetBv)
+ASM_PFX(AsmXGetBv):
+ xgetbv
+ shl rdx, 32
+ or rax, rdx
+ ret
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging32.c
new file mode 100644
index 0000000..b7378c0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging32.c
@@ -0,0 +1,60 @@
+/** @file
+ IA-32/x64 AsmDisablePaging32()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Disables the 32-bit paging mode on the CPU.
+
+ Disables the 32-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 32-paged protected
+ mode. This function is only available on IA-32. After the 32-bit paging mode
+ is disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be NULL. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit paged mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit paged mode.
+ 3) CR0, CR3, and CR4 must be compatible with 32-bit paged mode.
+ 4) CR3 must point to valid page tables that guarantee that the pages for
+ this function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is disabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is disabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is
+ disabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+AsmDisablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ ASSERT (EntryPoint != NULL);
+ ASSERT (NewStack != NULL);
+ InternalX86DisablePaging32 (EntryPoint, Context1, Context2, NewStack);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging64.c
new file mode 100644
index 0000000..867a8eb
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86DisablePaging64.c
@@ -0,0 +1,57 @@
+/** @file
+ IA-32/x64 AsmDisablePaging64()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Disables the 64-bit paging mode on the CPU.
+
+ Disables the 64-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 64-paging mode.
+ This function is only available on x64. After the 64-bit paging mode is
+ disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 64-bit paged mode, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for 32-bit protected mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is disabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is disabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is disabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+AsmDisablePaging64 (
+ IN UINT16 Cs,
+ IN UINT32 EntryPoint,
+ IN UINT32 Context1, OPTIONAL
+ IN UINT32 Context2, OPTIONAL
+ IN UINT32 NewStack
+ )
+{
+ ASSERT (EntryPoint != 0);
+ ASSERT (NewStack != 0);
+ InternalX86DisablePaging64 (Cs, EntryPoint, Context1, Context2, NewStack);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging32.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging32.c
new file mode 100644
index 0000000..32a0054
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging32.c
@@ -0,0 +1,63 @@
+/** @file
+ IA-32/x64 AsmEnablePaging32()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Enables the 32-bit paging mode on the CPU.
+
+ Enables the 32-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode. This function is
+ only available on IA-32. After the 32-bit paging mode is enabled, control is
+ transferred to the function specified by EntryPoint using the new stack
+ specified by NewStack and passing in the parameters specified by Context1 and
+ Context2. Context1 and Context2 are optional and may be NULL. The function
+ EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit protected mode with flat descriptors. This
+ means all descriptors must have a base of 0 and a limit of 4GB.
+ 3) CR0 and CR4 must be compatible with 32-bit protected mode with flat
+ descriptors.
+ 4) CR3 must point to valid page tables that will be used once the transition
+ is complete, and those page tables must guarantee that the pages for this
+ function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is enabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is enabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is enabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+AsmEnablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ ASSERT (EntryPoint != NULL);
+ ASSERT (NewStack != NULL);
+ InternalX86EnablePaging32 (EntryPoint, Context1, Context2, NewStack);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging64.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging64.c
new file mode 100644
index 0000000..1323e68
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86EnablePaging64.c
@@ -0,0 +1,59 @@
+/** @file
+ IA-32/x64 AsmEnablePaging64()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Enables the 64-bit paging mode on the CPU.
+
+ Enables the 64-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode with flat
+ descriptors. This function is only available on IA-32. After the 64-bit
+ paging mode is enabled, control is transferred to the function specified by
+ EntryPoint using the new stack specified by NewStack and passing in the
+ parameters specified by Context1 and Context2. Context1 and Context2 are
+ optional and may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode with flat
+ descriptors, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for long mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is enabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is enabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is enabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+AsmEnablePaging64 (
+ IN UINT16 Cs,
+ IN UINT64 EntryPoint,
+ IN UINT64 Context1, OPTIONAL
+ IN UINT64 Context2, OPTIONAL
+ IN UINT64 NewStack
+ )
+{
+ ASSERT (EntryPoint != 0);
+ ASSERT (NewStack != 0);
+ InternalX86EnablePaging64 (Cs, EntryPoint, Context1, Context2, NewStack);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxRestore.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxRestore.c
new file mode 100644
index 0000000..c4fa668
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxRestore.c
@@ -0,0 +1,43 @@
+/** @file
+ IA-32/x64 AsmFxRestore()
+
+ Copyright (c) 2006 - 2012, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Restores the current floating point/SSE/SSE2 context from a buffer.
+
+ Restores the current floating point/SSE/SSE2 state from the buffer specified
+ by Buffer. Buffer must be aligned on a 16-byte boundary. This function is
+ only available on IA-32 and x64.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-byte boundary, then ASSERT().
+ If Buffer was not saved with AsmFxSave(), then ASSERT().
+
+ @param Buffer A pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+AsmFxRestore (
+ IN CONST IA32_FX_BUFFER *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+ ASSERT (0 == ((UINTN)Buffer & 0xf));
+
+ //
+ // Check the flag recorded by AsmFxSave()
+ //
+ ASSERT (0xAA5555AA == *(UINT32 *) (&Buffer->Buffer[sizeof (Buffer->Buffer) - 4]));
+
+ InternalX86FxRestore (Buffer);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxSave.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxSave.c
new file mode 100644
index 0000000..2621a08
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86FxSave.c
@@ -0,0 +1,42 @@
+/** @file
+ IA-32/x64 AsmFxSave()
+
+ Copyright (c) 2006 - 2012, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Save the current floating point/SSE/SSE2 context to a buffer.
+
+ Saves the current floating point/SSE/SSE2 state to the buffer specified by
+ Buffer. Buffer must be aligned on a 16-byte boundary. This function is only
+ available on IA-32 and x64.
+
+ If Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-byte boundary, then ASSERT().
+
+ @param Buffer A pointer to a buffer to save the floating point/SSE/SSE2 context.
+
+**/
+VOID
+EFIAPI
+AsmFxSave (
+ OUT IA32_FX_BUFFER *Buffer
+ )
+{
+ ASSERT (Buffer != NULL);
+ ASSERT (0 == ((UINTN)Buffer & 0xf));
+
+ InternalX86FxSave (Buffer);
+
+ //
+ // Mark one flag at end of Buffer, it will be check by AsmFxRestor()
+ //
+ *(UINT32 *) (&Buffer->Buffer[sizeof (Buffer->Buffer) - 4]) = 0xAA5555AA;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86GetInterruptState.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86GetInterruptState.c
new file mode 100644
index 0000000..4363a7f
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86GetInterruptState.c
@@ -0,0 +1,35 @@
+/** @file
+ IA-32/x64 GetInterruptState()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+
+/**
+ Retrieves the current CPU interrupt state.
+
+ Returns TRUE is interrupts are currently enabled. Otherwise
+ returns FALSE.
+
+ @retval TRUE CPU interrupts are enabled.
+ @retval FALSE CPU interrupts are disabled.
+
+**/
+BOOLEAN
+EFIAPI
+GetInterruptState (
+ VOID
+ )
+{
+ IA32_EFLAGS32 EFlags;
+
+ EFlags.UintN = AsmReadEflags ();
+ return (BOOLEAN)(1 == EFlags.Bits.IF);
+}
+
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86MemoryFence.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86MemoryFence.c
new file mode 100644
index 0000000..399b36b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86MemoryFence.c
@@ -0,0 +1,26 @@
+/** @file
+ IA-32/x64 MemoryFence().
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+/**
+ Used to serialize load and store operations.
+
+ All loads and stores that proceed calls to this function are guaranteed to be
+ globally visible when this function returns.
+
+**/
+VOID
+EFIAPI
+MemoryFence (
+ VOID
+ )
+{
+ return;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Msr.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Msr.c
new file mode 100644
index 0000000..ea51ca9
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Msr.c
@@ -0,0 +1,654 @@
+/** @file
+ IA-32/x64 MSR functions.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+
+/**
+ Returns the lower 32-bits of a Machine Specific Register(MSR).
+
+ Reads and returns the lower 32-bits of the MSR specified by Index.
+ No parameter checking is performed on Index, and some Index values may cause
+ CPU exceptions. The caller must either guarantee that Index is valid, or the
+ caller must set up exception handlers to catch the exceptions. This function
+ is only available on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to read.
+
+ @return The lower 32 bits of the MSR identified by Index.
+
+**/
+UINT32
+EFIAPI
+AsmReadMsr32 (
+ IN UINT32 Index
+ )
+{
+ return (UINT32)AsmReadMsr64 (Index);
+}
+
+/**
+ Writes a 32-bit value to a Machine Specific Register(MSR), and returns the value.
+ The upper 32-bits of the MSR are set to zero.
+
+ Writes the 32-bit value specified by Value to the MSR specified by Index. The
+ upper 32-bits of the MSR write are set to zero. The 32-bit value written to
+ the MSR is returned. No parameter checking is performed on Index or Value,
+ and some of these may cause CPU exceptions. The caller must either guarantee
+ that Index and Value are valid, or the caller must establish proper exception
+ handlers. This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param Value The 32-bit value to write to the MSR.
+
+ @return Value
+
+**/
+UINT32
+EFIAPI
+AsmWriteMsr32 (
+ IN UINT32 Index,
+ IN UINT32 Value
+ )
+{
+ return (UINT32)AsmWriteMsr64 (Index, Value);
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise OR on the lower 32-bits, and
+ writes the result back to the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise OR
+ between the lower 32-bits of the read result and the value specified by
+ OrData, and writes the result to the 64-bit MSR specified by Index. The lower
+ 32-bits of the value written to the MSR is returned. No parameter checking is
+ performed on Index or OrData, and some of these may cause CPU exceptions. The
+ caller must either guarantee that Index and OrData are valid, or the caller
+ must establish proper exception handlers. This function is only available on
+ IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param OrData The value to OR with the read value from the MSR.
+
+ @return The lower 32-bit value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrOr32 (
+ IN UINT32 Index,
+ IN UINT32 OrData
+ )
+{
+ return (UINT32)AsmMsrOr64 (Index, OrData);
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise AND on the lower 32-bits, and writes
+ the result back to the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between the
+ lower 32-bits of the read result and the value specified by AndData, and
+ writes the result to the 64-bit MSR specified by Index. The lower 32-bits of
+ the value written to the MSR is returned. No parameter checking is performed
+ on Index or AndData, and some of these may cause CPU exceptions. The caller
+ must either guarantee that Index and AndData are valid, or the caller must
+ establish proper exception handlers. This function is only available on IA-32
+ and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param AndData The value to AND with the read value from the MSR.
+
+ @return The lower 32-bit value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrAnd32 (
+ IN UINT32 Index,
+ IN UINT32 AndData
+ )
+{
+ return (UINT32)AsmMsrAnd64 (Index, AndData);
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise AND followed by a bitwise OR
+ on the lower 32-bits, and writes the result back to the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between the
+ lower 32-bits of the read result and the value specified by AndData
+ preserving the upper 32-bits, performs a bitwise OR between the
+ result of the AND operation and the value specified by OrData, and writes the
+ result to the 64-bit MSR specified by Address. The lower 32-bits of the value
+ written to the MSR is returned. No parameter checking is performed on Index,
+ AndData, or OrData, and some of these may cause CPU exceptions. The caller
+ must either guarantee that Index, AndData, and OrData are valid, or the
+ caller must establish proper exception handlers. This function is only
+ available on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param AndData The value to AND with the read value from the MSR.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The lower 32-bit value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrAndThenOr32 (
+ IN UINT32 Index,
+ IN UINT32 AndData,
+ IN UINT32 OrData
+ )
+{
+ return (UINT32)AsmMsrAndThenOr64 (Index, AndData, OrData);
+}
+
+/**
+ Reads a bit field of an MSR.
+
+ Reads the bit field in the lower 32-bits of a 64-bit MSR. The bit field is
+ specified by the StartBit and the EndBit. The value of the bit field is
+ returned. The caller must either guarantee that Index is valid, or the caller
+ must set up exception handlers to catch the exceptions. This function is only
+ available on IA-32 and x64.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to read.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+
+ @return The bit field read from the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrBitFieldRead32 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ return BitFieldRead32 (AsmReadMsr32 (Index), StartBit, EndBit);
+}
+
+/**
+ Writes a bit field to an MSR.
+
+ Writes Value to a bit field in the lower 32-bits of a 64-bit MSR. The bit
+ field is specified by the StartBit and the EndBit. All other bits in the
+ destination MSR are preserved. The lower 32-bits of the MSR written is
+ returned. The caller must either guarantee that Index and the data written
+ is valid, or the caller must set up exception handlers to catch the exceptions.
+ This function is only available on IA-32 and x64.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param Value The new value of the bit field.
+
+ @return The lower 32-bit of the value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrBitFieldWrite32 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 Value
+ )
+{
+ ASSERT (EndBit < sizeof (Value) * 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)AsmMsrBitFieldWrite64 (Index, StartBit, EndBit, Value);
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise OR, and writes the
+ result back to the bit field in the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise OR
+ between the read result and the value specified by OrData, and writes the
+ result to the 64-bit MSR specified by Index. The lower 32-bits of the value
+ written to the MSR are returned. Extra left bits in OrData are stripped. The
+ caller must either guarantee that Index and the data written is valid, or
+ the caller must set up exception handlers to catch the exceptions. This
+ function is only available on IA-32 and x64.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param OrData The value to OR with the read value from the MSR.
+
+ @return The lower 32-bit of the value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrBitFieldOr32 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 OrData
+ )
+{
+ ASSERT (EndBit < sizeof (OrData) * 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)AsmMsrBitFieldOr64 (Index, StartBit, EndBit, OrData);
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise AND, and writes the
+ result back to the bit field in the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between the
+ read result and the value specified by AndData, and writes the result to the
+ 64-bit MSR specified by Index. The lower 32-bits of the value written to the
+ MSR are returned. Extra left bits in AndData are stripped. The caller must
+ either guarantee that Index and the data written is valid, or the caller must
+ set up exception handlers to catch the exceptions. This function is only
+ available on IA-32 and x64.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param AndData The value to AND with the read value from the MSR.
+
+ @return The lower 32-bit of the value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrBitFieldAnd32 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 AndData
+ )
+{
+ ASSERT (EndBit < sizeof (AndData) * 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)AsmMsrBitFieldAnd64 (Index, StartBit, EndBit, AndData);
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise AND followed by a
+ bitwise OR, and writes the result back to the bit field in the
+ 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND followed by a
+ bitwise OR between the read result and the value specified by
+ AndData, and writes the result to the 64-bit MSR specified by Index. The
+ lower 32-bits of the value written to the MSR are returned. Extra left bits
+ in both AndData and OrData are stripped. The caller must either guarantee
+ that Index and the data written is valid, or the caller must set up exception
+ handlers to catch the exceptions. This function is only available on IA-32
+ and x64.
+
+ If StartBit is greater than 31, then ASSERT().
+ If EndBit is greater than 31, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..31.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..31.
+ @param AndData The value to AND with the read value from the MSR.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The lower 32-bit of the value written to the MSR.
+
+**/
+UINT32
+EFIAPI
+AsmMsrBitFieldAndThenOr32 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT32 AndData,
+ IN UINT32 OrData
+ )
+{
+ ASSERT (EndBit < sizeof (AndData) * 8);
+ ASSERT (StartBit <= EndBit);
+ return (UINT32)AsmMsrBitFieldAndThenOr64 (
+ Index,
+ StartBit,
+ EndBit,
+ AndData,
+ OrData
+ );
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise OR, and writes the result
+ back to the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise OR
+ between the read result and the value specified by OrData, and writes the
+ result to the 64-bit MSR specified by Index. The value written to the MSR is
+ returned. No parameter checking is performed on Index or OrData, and some of
+ these may cause CPU exceptions. The caller must either guarantee that Index
+ and OrData are valid, or the caller must establish proper exception handlers.
+ This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param OrData The value to OR with the read value from the MSR.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrOr64 (
+ IN UINT32 Index,
+ IN UINT64 OrData
+ )
+{
+ return AsmWriteMsr64 (Index, AsmReadMsr64 (Index) | OrData);
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise AND, and writes the result back to the
+ 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between the
+ read result and the value specified by OrData, and writes the result to the
+ 64-bit MSR specified by Index. The value written to the MSR is returned. No
+ parameter checking is performed on Index or OrData, and some of these may
+ cause CPU exceptions. The caller must either guarantee that Index and OrData
+ are valid, or the caller must establish proper exception handlers. This
+ function is only available on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param AndData The value to AND with the read value from the MSR.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrAnd64 (
+ IN UINT32 Index,
+ IN UINT64 AndData
+ )
+{
+ return AsmWriteMsr64 (Index, AsmReadMsr64 (Index) & AndData);
+}
+
+/**
+ Reads a 64-bit MSR, performs a bitwise AND followed by a bitwise
+ OR, and writes the result back to the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between read
+ result and the value specified by AndData, performs a bitwise OR
+ between the result of the AND operation and the value specified by OrData,
+ and writes the result to the 64-bit MSR specified by Index. The value written
+ to the MSR is returned. No parameter checking is performed on Index, AndData,
+ or OrData, and some of these may cause CPU exceptions. The caller must either
+ guarantee that Index, AndData, and OrData are valid, or the caller must
+ establish proper exception handlers. This function is only available on IA-32
+ and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param AndData The value to AND with the read value from the MSR.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrAndThenOr64 (
+ IN UINT32 Index,
+ IN UINT64 AndData,
+ IN UINT64 OrData
+ )
+{
+ return AsmWriteMsr64 (Index, (AsmReadMsr64 (Index) & AndData) | OrData);
+}
+
+/**
+ Reads a bit field of an MSR.
+
+ Reads the bit field in the 64-bit MSR. The bit field is specified by the
+ StartBit and the EndBit. The value of the bit field is returned. The caller
+ must either guarantee that Index is valid, or the caller must set up
+ exception handlers to catch the exceptions. This function is only available
+ on IA-32 and x64.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to read.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+
+ @return The value read from the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrBitFieldRead64 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit
+ )
+{
+ return BitFieldRead64 (AsmReadMsr64 (Index), StartBit, EndBit);
+}
+
+/**
+ Writes a bit field to an MSR.
+
+ Writes Value to a bit field in a 64-bit MSR. The bit field is specified by
+ the StartBit and the EndBit. All other bits in the destination MSR are
+ preserved. The MSR written is returned. The caller must either guarantee
+ that Index and the data written is valid, or the caller must set up exception
+ handlers to catch the exceptions. This function is only available on IA-32 and x64.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If Value is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param Value The new value of the bit field.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrBitFieldWrite64 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 Value
+ )
+{
+ return AsmWriteMsr64 (
+ Index,
+ BitFieldWrite64 (AsmReadMsr64 (Index), StartBit, EndBit, Value)
+ );
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise OR, and
+ writes the result back to the bit field in the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise OR
+ between the read result and the value specified by OrData, and writes the
+ result to the 64-bit MSR specified by Index. The value written to the MSR is
+ returned. Extra left bits in OrData are stripped. The caller must either
+ guarantee that Index and the data written is valid, or the caller must set up
+ exception handlers to catch the exceptions. This function is only available
+ on IA-32 and x64.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param OrData The value to OR with the read value from the bit field.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrBitFieldOr64 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 OrData
+ )
+{
+ return AsmWriteMsr64 (
+ Index,
+ BitFieldOr64 (AsmReadMsr64 (Index), StartBit, EndBit, OrData)
+ );
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise AND, and writes the
+ result back to the bit field in the 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND between the
+ read result and the value specified by AndData, and writes the result to the
+ 64-bit MSR specified by Index. The value written to the MSR is returned.
+ Extra left bits in AndData are stripped. The caller must either guarantee
+ that Index and the data written is valid, or the caller must set up exception
+ handlers to catch the exceptions. This function is only available on IA-32
+ and x64.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param AndData The value to AND with the read value from the bit field.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrBitFieldAnd64 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 AndData
+ )
+{
+ return AsmWriteMsr64 (
+ Index,
+ BitFieldAnd64 (AsmReadMsr64 (Index), StartBit, EndBit, AndData)
+ );
+}
+
+/**
+ Reads a bit field in a 64-bit MSR, performs a bitwise AND followed by a
+ bitwise OR, and writes the result back to the bit field in the
+ 64-bit MSR.
+
+ Reads the 64-bit MSR specified by Index, performs a bitwise AND followed by
+ a bitwise OR between the read result and the value specified by
+ AndData, and writes the result to the 64-bit MSR specified by Index. The
+ value written to the MSR is returned. Extra left bits in both AndData and
+ OrData are stripped. The caller must either guarantee that Index and the data
+ written is valid, or the caller must set up exception handlers to catch the
+ exceptions. This function is only available on IA-32 and x64.
+
+ If StartBit is greater than 63, then ASSERT().
+ If EndBit is greater than 63, then ASSERT().
+ If EndBit is less than StartBit, then ASSERT().
+ If AndData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+ If OrData is larger than the bitmask value range specified by StartBit and EndBit, then ASSERT().
+
+ @param Index The 32-bit MSR index to write.
+ @param StartBit The ordinal of the least significant bit in the bit field.
+ Range 0..63.
+ @param EndBit The ordinal of the most significant bit in the bit field.
+ Range 0..63.
+ @param AndData The value to AND with the read value from the bit field.
+ @param OrData The value to OR with the result of the AND operation.
+
+ @return The value written back to the MSR.
+
+**/
+UINT64
+EFIAPI
+AsmMsrBitFieldAndThenOr64 (
+ IN UINT32 Index,
+ IN UINTN StartBit,
+ IN UINTN EndBit,
+ IN UINT64 AndData,
+ IN UINT64 OrData
+ )
+{
+ return AsmWriteMsr64 (
+ Index,
+ BitFieldAndThenOr64 (
+ AsmReadMsr64 (Index),
+ StartBit,
+ EndBit,
+ AndData,
+ OrData
+ )
+ );
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86PatchInstruction.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86PatchInstruction.c
new file mode 100644
index 0000000..fc70a35
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86PatchInstruction.c
@@ -0,0 +1,83 @@
+/** @file
+ IA-32/x64 PatchInstructionX86()
+
+ Copyright (C) 2018, Intel Corporation. All rights reserved.<BR>
+ Copyright (C) 2018, Red Hat, Inc.
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Patch the immediate operand of an IA32 or X64 instruction such that the byte,
+ word, dword or qword operand is encoded at the end of the instruction's
+ binary representation.
+
+ This function should be used to update object code that was compiled with
+ NASM from assembly source code. Example:
+
+ NASM source code:
+
+ mov eax, strict dword 0 ; the imm32 zero operand will be patched
+ ASM_PFX(gPatchCr3):
+ mov cr3, eax
+
+ C source code:
+
+ X86_ASSEMBLY_PATCH_LABEL gPatchCr3;
+ PatchInstructionX86 (gPatchCr3, AsmReadCr3 (), 4);
+
+ @param[out] InstructionEnd Pointer right past the instruction to patch. The
+ immediate operand to patch is expected to
+ comprise the trailing bytes of the instruction.
+ If InstructionEnd is closer to address 0 than
+ ValueSize permits, then ASSERT().
+
+ @param[in] PatchValue The constant to write to the immediate operand.
+ The caller is responsible for ensuring that
+ PatchValue can be represented in the byte, word,
+ dword or qword operand (as indicated through
+ ValueSize); otherwise ASSERT().
+
+ @param[in] ValueSize The size of the operand in bytes; must be 1, 2,
+ 4, or 8. ASSERT() otherwise.
+**/
+VOID
+EFIAPI
+PatchInstructionX86 (
+ OUT X86_ASSEMBLY_PATCH_LABEL *InstructionEnd,
+ IN UINT64 PatchValue,
+ IN UINTN ValueSize
+ )
+{
+ //
+ // The equality ((UINTN)InstructionEnd == ValueSize) would assume a zero-size
+ // instruction at address 0; forbid it.
+ //
+ ASSERT ((UINTN)InstructionEnd > ValueSize);
+
+ switch (ValueSize) {
+ case 1:
+ ASSERT (PatchValue <= MAX_UINT8);
+ *((UINT8 *)(UINTN)InstructionEnd - 1) = (UINT8)PatchValue;
+ break;
+
+ case 2:
+ ASSERT (PatchValue <= MAX_UINT16);
+ WriteUnaligned16 ((UINT16 *)(UINTN)InstructionEnd - 1, (UINT16)PatchValue);
+ break;
+
+ case 4:
+ ASSERT (PatchValue <= MAX_UINT32);
+ WriteUnaligned32 ((UINT32 *)(UINTN)InstructionEnd - 1, (UINT32)PatchValue);
+ break;
+
+ case 8:
+ WriteUnaligned64 ((UINT64 *)(UINTN)InstructionEnd - 1, PatchValue);
+ break;
+
+ default:
+ ASSERT (FALSE);
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86RdRand.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86RdRand.c
new file mode 100644
index 0000000..dcbd969
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86RdRand.c
@@ -0,0 +1,73 @@
+/** @file
+ IA-32/x64 AsmRdRandxx()
+ Generates random number through CPU RdRand instruction.
+
+ Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "BaseLibInternals.h"
+
+/**
+ Generates a 16-bit random number through RDRAND instruction.
+
+ if Rand is NULL, then ASSERT().
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+ **/
+BOOLEAN
+EFIAPI
+AsmRdRand16 (
+ OUT UINT16 *Rand
+ )
+{
+ ASSERT (Rand != NULL);
+ return InternalX86RdRand16 (Rand);
+}
+
+/**
+ Generates a 32-bit random number through RDRAND instruction.
+
+ if Rand is NULL, then ASSERT().
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+**/
+BOOLEAN
+EFIAPI
+AsmRdRand32 (
+ OUT UINT32 *Rand
+ )
+{
+ ASSERT (Rand != NULL);
+ return InternalX86RdRand32 (Rand);
+}
+
+/**
+ Generates a 64-bit random number through RDRAND instruction.
+
+ if Rand is NULL, then ASSERT().
+
+ @param[out] Rand Buffer pointer to store the random result.
+
+ @retval TRUE RDRAND call was successful.
+ @retval FALSE Failed attempts to call RDRAND.
+
+**/
+BOOLEAN
+EFIAPI
+AsmRdRand64 (
+ OUT UINT64 *Rand
+ )
+{
+ ASSERT (Rand != NULL);
+ return InternalX86RdRand64 (Rand);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadGdtr.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadGdtr.c
new file mode 100644
index 0000000..ca7c5de
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadGdtr.c
@@ -0,0 +1,33 @@
+/** @file
+ IA-32/x64 AsmReadGdtr()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Reads the current Global Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current GDTR descriptor and returns it in Gdtr. This
+ function is only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmReadGdtr (
+ OUT IA32_DESCRIPTOR *Gdtr
+ )
+{
+ ASSERT (Gdtr != NULL);
+ InternalX86ReadGdtr (Gdtr);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadIdtr.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadIdtr.c
new file mode 100644
index 0000000..f9133f9
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86ReadIdtr.c
@@ -0,0 +1,33 @@
+/** @file
+ IA-32/x64 AsmReadIdtr()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Reads the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Reads and returns the current IDTR descriptor and returns it in Idtr. This
+ function is only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmReadIdtr (
+ OUT IA32_DESCRIPTOR *Idtr
+ )
+{
+ ASSERT (Idtr != NULL);
+ InternalX86ReadIdtr (Idtr);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86SpeculationBarrier.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86SpeculationBarrier.c
new file mode 100644
index 0000000..b28fd8d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86SpeculationBarrier.c
@@ -0,0 +1,30 @@
+/** @file
+ SpeculationBarrier() function for IA32 and x64.
+
+ Copyright (C) 2018 - 2019, Intel Corporation. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Library/BaseLib.h>
+
+/**
+ Uses as a barrier to stop speculative execution.
+
+ Ensures that no later instruction will execute speculatively, until all prior
+ instructions have completed.
+
+**/
+VOID
+EFIAPI
+SpeculationBarrier (
+ VOID
+ )
+{
+ if (PcdGet8 (PcdSpeculationBarrierType) == 0x01) {
+ AsmLfence ();
+ } else if (PcdGet8 (PcdSpeculationBarrierType) == 0x02) {
+ AsmCpuid (0x01, NULL, NULL, NULL, NULL);
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Thunk.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Thunk.c
new file mode 100644
index 0000000..5c8a039
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86Thunk.c
@@ -0,0 +1,262 @@
+/** @file
+ Real Mode Thunk Functions for IA32 and x64.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "BaseLibInternals.h"
+
+extern CONST UINT8 m16Start;
+extern CONST UINT16 m16Size;
+extern CONST UINT16 mThunk16Attr;
+extern CONST UINT16 m16Gdt;
+extern CONST UINT16 m16GdtrBase;
+extern CONST UINT16 mTransition;
+
+/**
+ Invokes 16-bit code in big real mode and returns the updated register set.
+
+ This function transfers control to the 16-bit code specified by CS:EIP using
+ the stack specified by SS:ESP in RegisterSet. The updated registers are saved
+ on the real mode stack and the starting address of the save area is returned.
+
+ @param RegisterSet Values of registers before invocation of 16-bit code.
+ @param Transition The pointer to the transition code under 1MB.
+
+ @return The pointer to a IA32_REGISTER_SET structure containing the updated
+ register values.
+
+**/
+IA32_REGISTER_SET *
+EFIAPI
+InternalAsmThunk16 (
+ IN IA32_REGISTER_SET *RegisterSet,
+ IN OUT VOID *Transition
+ );
+
+/**
+ Retrieves the properties for 16-bit thunk functions.
+
+ Computes the size of the buffer and stack below 1MB required to use the
+ AsmPrepareThunk16(), AsmThunk16() and AsmPrepareAndThunk16() functions. This
+ buffer size is returned in RealModeBufferSize, and the stack size is returned
+ in ExtraStackSize. If parameters are passed to the 16-bit real mode code,
+ then the actual minimum stack size is ExtraStackSize plus the maximum number
+ of bytes that need to be passed to the 16-bit real mode code.
+
+ If RealModeBufferSize is NULL, then ASSERT().
+ If ExtraStackSize is NULL, then ASSERT().
+
+ @param RealModeBufferSize A pointer to the size of the buffer below 1MB
+ required to use the 16-bit thunk functions.
+ @param ExtraStackSize A pointer to the extra size of stack below 1MB
+ that the 16-bit thunk functions require for
+ temporary storage in the transition to and from
+ 16-bit real mode.
+
+**/
+VOID
+EFIAPI
+AsmGetThunk16Properties (
+ OUT UINT32 *RealModeBufferSize,
+ OUT UINT32 *ExtraStackSize
+ )
+{
+ ASSERT (RealModeBufferSize != NULL);
+ ASSERT (ExtraStackSize != NULL);
+
+ *RealModeBufferSize = m16Size;
+
+ //
+ // Extra 4 bytes for return address, and another 4 bytes for mode transition
+ //
+ *ExtraStackSize = sizeof (IA32_DWORD_REGS) + 8;
+}
+
+/**
+ Prepares all structures a code required to use AsmThunk16().
+
+ Prepares all structures and code required to use AsmThunk16().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ If ThunkContext is NULL, then ASSERT().
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmPrepareThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ IA32_SEGMENT_DESCRIPTOR *RealModeGdt;
+
+ ASSERT (ThunkContext != NULL);
+ ASSERT ((UINTN)ThunkContext->RealModeBuffer < 0x100000);
+ ASSERT (ThunkContext->RealModeBufferSize >= m16Size);
+ ASSERT ((UINTN)ThunkContext->RealModeBuffer + m16Size <= 0x100000);
+
+ CopyMem (ThunkContext->RealModeBuffer, &m16Start, m16Size);
+
+ //
+ // Point RealModeGdt to the GDT to be used in transition
+ //
+ // RealModeGdt[0]: Reserved as NULL descriptor
+ // RealModeGdt[1]: Code Segment
+ // RealModeGdt[2]: Data Segment
+ // RealModeGdt[3]: Call Gate
+ //
+ RealModeGdt = (IA32_SEGMENT_DESCRIPTOR*)(
+ (UINTN)ThunkContext->RealModeBuffer + m16Gdt);
+
+ //
+ // Update Code & Data Segment Descriptor
+ //
+ RealModeGdt[1].Bits.BaseLow =
+ (UINT32)(UINTN)ThunkContext->RealModeBuffer & ~0xf;
+ RealModeGdt[1].Bits.BaseMid =
+ (UINT32)(UINTN)ThunkContext->RealModeBuffer >> 16;
+
+ //
+ // Update transition code entry point offset
+ //
+ *(UINT32*)((UINTN)ThunkContext->RealModeBuffer + mTransition) +=
+ (UINT32)(UINTN)ThunkContext->RealModeBuffer & 0xf;
+
+ //
+ // Update Segment Limits for both Code and Data Segment Descriptors
+ //
+ if ((ThunkContext->ThunkAttributes & THUNK_ATTRIBUTE_BIG_REAL_MODE) == 0) {
+ //
+ // Set segment limits to 64KB
+ //
+ RealModeGdt[1].Bits.LimitHigh = 0;
+ RealModeGdt[1].Bits.G = 0;
+ RealModeGdt[2].Bits.LimitHigh = 0;
+ RealModeGdt[2].Bits.G = 0;
+ }
+
+ //
+ // Update GDTBASE for this thunk context
+ //
+ *(VOID**)((UINTN)ThunkContext->RealModeBuffer + m16GdtrBase) = RealModeGdt;
+
+ //
+ // Update Thunk Attributes
+ //
+ *(UINT32*)((UINTN)ThunkContext->RealModeBuffer + mThunk16Attr) =
+ ThunkContext->ThunkAttributes;
+}
+
+/**
+ Transfers control to a 16-bit real mode entry point and returns the results.
+
+ Transfers control to a 16-bit real mode entry point and returns the results.
+ AsmPrepareThunk16() must be called with ThunkContext before this function is used.
+ This function must be called with interrupts disabled.
+
+ The register state from the RealModeState field of ThunkContext is restored just prior
+ to calling the 16-bit real mode entry point. This includes the EFLAGS field of RealModeState,
+ which is used to set the interrupt state when a 16-bit real mode entry point is called.
+ Control is transferred to the 16-bit real mode entry point specified by the CS and Eip fields of RealModeState.
+ The stack is initialized to the SS and ESP fields of RealModeState. Any parameters passed to
+ the 16-bit real mode code must be populated by the caller at SS:ESP prior to calling this function.
+ The 16-bit real mode entry point is invoked with a 16-bit CALL FAR instruction,
+ so when accessing stack contents, the 16-bit real mode code must account for the 16-bit segment
+ and 16-bit offset of the return address that were pushed onto the stack. The 16-bit real mode entry
+ point must exit with a RETF instruction. The register state is captured into RealModeState immediately
+ after the RETF instruction is executed.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ or any of the 16-bit real mode code makes a SW interrupt, then the caller is responsible for making sure
+ the IDT at address 0 is initialized to handle any HW or SW interrupts that may occur while in 16-bit real mode.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ then the caller is responsible for making sure the 8259 PIC is in a state compatible with 16-bit real mode.
+ This includes the base vectors, the interrupt masks, and the edge/level trigger mode.
+
+ If THUNK_ATTRIBUTE_BIG_REAL_MODE is set in the ThunkAttributes field of ThunkContext, then the user code
+ is invoked in big real mode. Otherwise, the user code is invoked in 16-bit real mode with 64KB segment limits.
+
+ If neither THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 nor THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then it is assumed that the user code did not enable the A20 mask, and no attempt is made to
+ disable the A20 mask.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is set and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is clear in
+ ThunkAttributes, then attempt to use the INT 15 service to disable the A20 mask. If this INT 15 call fails,
+ then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is clear and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is set in
+ ThunkAttributes, then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If ThunkContext is NULL, then ASSERT().
+ If AsmPrepareThunk16() was not previously called with ThunkContext, then ASSERT().
+ If both THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then ASSERT().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ IA32_REGISTER_SET *UpdatedRegs;
+
+ ASSERT (ThunkContext != NULL);
+ ASSERT ((UINTN)ThunkContext->RealModeBuffer < 0x100000);
+ ASSERT (ThunkContext->RealModeBufferSize >= m16Size);
+ ASSERT ((UINTN)ThunkContext->RealModeBuffer + m16Size <= 0x100000);
+ ASSERT (((ThunkContext->ThunkAttributes & (THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 | THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL)) != \
+ (THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 | THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL)));
+
+ UpdatedRegs = InternalAsmThunk16 (
+ ThunkContext->RealModeState,
+ ThunkContext->RealModeBuffer
+ );
+
+ CopyMem (ThunkContext->RealModeState, UpdatedRegs, sizeof (*UpdatedRegs));
+}
+
+/**
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results.
+
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results. If the
+ caller only need to perform a single 16-bit real mode thunk, then this
+ service should be used. If the caller intends to make more than one 16-bit
+ real mode thunk, then it is more efficient if AsmPrepareThunk16() is called
+ once and AsmThunk16() can be called for each 16-bit real mode thunk.
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ See AsmPrepareThunk16() and AsmThunk16() for the detailed description and ASSERT() conditions.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmPrepareAndThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ AsmPrepareThunk16 (ThunkContext);
+ AsmThunk16 (ThunkContext);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86UnitTestHost.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86UnitTestHost.c
new file mode 100644
index 0000000..d0e4284
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86UnitTestHost.c
@@ -0,0 +1,2977 @@
+/** @file
+ IA32/X64 specific Unit Test Host functions.
+
+ Copyright (c) 2020, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UnitTestHost.h"
+
+///
+/// Defines for mUnitTestHostBaseLibSegment indexes
+///
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_CS 0
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_DS 1
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_ES 2
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_FS 3
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_GS 4
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_SS 5
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_TR 6
+#define UNIT_TEST_HOST_BASE_LIB_SEGMENT_LDTR 7
+
+///
+/// Module global variables for simple system emulation of MSRs, CRx, DRx,
+/// GDTR, IDTR, and Segment Selectors.
+///
+STATIC UINT64 mUnitTestHostBaseLibMsr[2][0x1000];
+STATIC UINTN mUnitTestHostBaseLibCr[5];
+STATIC UINTN mUnitTestHostBaseLibDr[8];
+STATIC UINT16 mUnitTestHostBaseLibSegment[8];
+STATIC IA32_DESCRIPTOR mUnitTestHostBaseLibGdtr;
+STATIC IA32_DESCRIPTOR mUnitTestHostBaseLibIdtr;
+
+/**
+ Retrieves CPUID information.
+
+ Executes the CPUID instruction with EAX set to the value specified by Index.
+ This function always returns Index.
+ If Eax is not NULL, then the value of EAX after CPUID is returned in Eax.
+ If Ebx is not NULL, then the value of EBX after CPUID is returned in Ebx.
+ If Ecx is not NULL, then the value of ECX after CPUID is returned in Ecx.
+ If Edx is not NULL, then the value of EDX after CPUID is returned in Edx.
+ This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit value to load into EAX prior to invoking the CPUID
+ instruction.
+ @param Eax The pointer to the 32-bit EAX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Ebx The pointer to the 32-bit EBX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Ecx The pointer to the 32-bit ECX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Edx The pointer to the 32-bit EDX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+
+ @return Index.
+
+**/
+UINT32
+EFIAPI
+UnitTestHostBaseLibAsmCpuid (
+ IN UINT32 Index,
+ OUT UINT32 *Eax, OPTIONAL
+ OUT UINT32 *Ebx, OPTIONAL
+ OUT UINT32 *Ecx, OPTIONAL
+ OUT UINT32 *Edx OPTIONAL
+ )
+{
+ if (Eax != NULL) {
+ *Eax = 0;
+ }
+ if (Ebx != NULL) {
+ *Ebx = 0;
+ }
+ if (Ecx != NULL) {
+ *Ecx = 0;
+ }
+ if (Edx != NULL) {
+ *Edx = 0;
+ }
+ return Index;
+}
+
+/**
+ Retrieves CPUID information using an extended leaf identifier.
+
+ Executes the CPUID instruction with EAX set to the value specified by Index
+ and ECX set to the value specified by SubIndex. This function always returns
+ Index. This function is only available on IA-32 and x64.
+
+ If Eax is not NULL, then the value of EAX after CPUID is returned in Eax.
+ If Ebx is not NULL, then the value of EBX after CPUID is returned in Ebx.
+ If Ecx is not NULL, then the value of ECX after CPUID is returned in Ecx.
+ If Edx is not NULL, then the value of EDX after CPUID is returned in Edx.
+
+ @param Index The 32-bit value to load into EAX prior to invoking the
+ CPUID instruction.
+ @param SubIndex The 32-bit value to load into ECX prior to invoking the
+ CPUID instruction.
+ @param Eax The pointer to the 32-bit EAX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Ebx The pointer to the 32-bit EBX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Ecx The pointer to the 32-bit ECX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Edx The pointer to the 32-bit EDX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+
+ @return Index.
+
+**/
+UINT32
+EFIAPI
+UnitTestHostBaseLibAsmCpuidEx (
+ IN UINT32 Index,
+ IN UINT32 SubIndex,
+ OUT UINT32 *Eax, OPTIONAL
+ OUT UINT32 *Ebx, OPTIONAL
+ OUT UINT32 *Ecx, OPTIONAL
+ OUT UINT32 *Edx OPTIONAL
+ )
+{
+ if (Eax != NULL) {
+ *Eax = 0;
+ }
+ if (Ebx != NULL) {
+ *Ebx = 0;
+ }
+ if (Ecx != NULL) {
+ *Ecx = 0;
+ }
+ if (Edx != NULL) {
+ *Edx = 0;
+ }
+ return Index;
+}
+
+/**
+ Set CD bit and clear NW bit of CR0 followed by a WBINVD.
+
+ Disables the caches by setting the CD bit of CR0 to 1, clearing the NW bit of CR0 to 0,
+ and executing a WBINVD instruction. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmDisableCache (
+ VOID
+ )
+{
+}
+
+/**
+ Perform a WBINVD and clear both the CD and NW bits of CR0.
+
+ Enables the caches by executing a WBINVD instruction and then clear both the CD and NW
+ bits of CR0 to 0. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmEnableCache (
+ VOID
+ )
+{
+}
+
+/**
+ Returns a 64-bit Machine Specific Register(MSR).
+
+ Reads and returns the 64-bit MSR specified by Index. No parameter checking is
+ performed on Index, and some Index values may cause CPU exceptions. The
+ caller must either guarantee that Index is valid, or the caller must set up
+ exception handlers to catch the exceptions. This function is only available
+ on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to read.
+
+ @return The value of the MSR identified by Index.
+
+**/
+UINT64
+EFIAPI
+UnitTestHostBaseLibAsmReadMsr64 (
+ IN UINT32 Index
+ )
+{
+ if (Index < 0x1000) {
+ return mUnitTestHostBaseLibMsr[0][Index];
+ }
+ if (Index >= 0xC0000000 && Index < 0xC0001000) {
+ return mUnitTestHostBaseLibMsr[1][Index];
+ }
+ return 0;
+}
+
+/**
+ Writes a 64-bit value to a Machine Specific Register(MSR), and returns the
+ value.
+
+ Writes the 64-bit value specified by Value to the MSR specified by Index. The
+ 64-bit value written to the MSR is returned. No parameter checking is
+ performed on Index or Value, and some of these may cause CPU exceptions. The
+ caller must either guarantee that Index and Value are valid, or the caller
+ must establish proper exception handlers. This function is only available on
+ IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param Value The 64-bit value to write to the MSR.
+
+ @return Value
+
+**/
+UINT64
+EFIAPI
+UnitTestHostBaseLibAsmWriteMsr64 (
+ IN UINT32 Index,
+ IN UINT64 Value
+ )
+{
+ if (Index < 0x1000) {
+ mUnitTestHostBaseLibMsr[0][Index] = Value;
+ }
+ if (Index >= 0xC0000000 && Index < 0xC0001000) {
+ mUnitTestHostBaseLibMsr[1][Index - 0xC00000000] = Value;
+ }
+ return Value;
+}
+
+/**
+ Reads the current value of the Control Register 0 (CR0).
+
+ Reads and returns the current value of CR0. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 0 (CR0).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadCr0 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibCr[0];
+}
+
+/**
+ Reads the current value of the Control Register 2 (CR2).
+
+ Reads and returns the current value of CR2. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 2 (CR2).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadCr2 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibCr[2];
+}
+
+/**
+ Reads the current value of the Control Register 3 (CR3).
+
+ Reads and returns the current value of CR3. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 3 (CR3).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadCr3 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibCr[3];
+}
+
+/**
+ Reads the current value of the Control Register 4 (CR4).
+
+ Reads and returns the current value of CR4. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 4 (CR4).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadCr4 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibCr[4];
+}
+
+/**
+ Writes a value to Control Register 0 (CR0).
+
+ Writes and returns a new value to CR0. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr0 The value to write to CR0.
+
+ @return The value written to CR0.
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteCr0 (
+ UINTN Cr0
+ )
+{
+ mUnitTestHostBaseLibCr[0] = Cr0;
+ return Cr0;
+}
+
+/**
+ Writes a value to Control Register 2 (CR2).
+
+ Writes and returns a new value to CR2. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr2 The value to write to CR2.
+
+ @return The value written to CR2.
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteCr2 (
+ UINTN Cr2
+ )
+{
+ mUnitTestHostBaseLibCr[2] = Cr2;
+ return Cr2;
+}
+
+/**
+ Writes a value to Control Register 3 (CR3).
+
+ Writes and returns a new value to CR3. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr3 The value to write to CR3.
+
+ @return The value written to CR3.
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteCr3 (
+ UINTN Cr3
+ )
+{
+ mUnitTestHostBaseLibCr[3] = Cr3;
+ return Cr3;
+}
+
+/**
+ Writes a value to Control Register 4 (CR4).
+
+ Writes and returns a new value to CR4. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr4 The value to write to CR4.
+
+ @return The value written to CR4.
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteCr4 (
+ UINTN Cr4
+ )
+{
+ mUnitTestHostBaseLibCr[4] = Cr4;
+ return Cr4;
+}
+
+/**
+ Reads the current value of Debug Register 0 (DR0).
+
+ Reads and returns the current value of DR0. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr0 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[0];
+}
+
+/**
+ Reads the current value of Debug Register 1 (DR1).
+
+ Reads and returns the current value of DR1. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr1 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[1];
+}
+
+/**
+ Reads the current value of Debug Register 2 (DR2).
+
+ Reads and returns the current value of DR2. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr2 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[2];
+}
+
+/**
+ Reads the current value of Debug Register 3 (DR3).
+
+ Reads and returns the current value of DR3. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr3 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[3];
+}
+
+/**
+ Reads the current value of Debug Register 4 (DR4).
+
+ Reads and returns the current value of DR4. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr4 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[4];
+}
+
+/**
+ Reads the current value of Debug Register 5 (DR5).
+
+ Reads and returns the current value of DR5. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr5 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[5];
+}
+
+/**
+ Reads the current value of Debug Register 6 (DR6).
+
+ Reads and returns the current value of DR6. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr6 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[6];
+}
+
+/**
+ Reads the current value of Debug Register 7 (DR7).
+
+ Reads and returns the current value of DR7. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmReadDr7 (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibDr[7];
+}
+
+/**
+ Writes a value to Debug Register 0 (DR0).
+
+ Writes and returns a new value to DR0. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr0 The value to write to Dr0.
+
+ @return The value written to Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr0 (
+ UINTN Dr0
+ )
+{
+ mUnitTestHostBaseLibDr[0] = Dr0;
+ return Dr0;
+}
+
+/**
+ Writes a value to Debug Register 1 (DR1).
+
+ Writes and returns a new value to DR1. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr1 The value to write to Dr1.
+
+ @return The value written to Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr1 (
+ UINTN Dr1
+ )
+{
+ mUnitTestHostBaseLibDr[1] = Dr1;
+ return Dr1;
+}
+
+/**
+ Writes a value to Debug Register 2 (DR2).
+
+ Writes and returns a new value to DR2. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr2 The value to write to Dr2.
+
+ @return The value written to Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr2 (
+ UINTN Dr2
+ )
+{
+ mUnitTestHostBaseLibDr[2] = Dr2;
+ return Dr2;
+}
+
+/**
+ Writes a value to Debug Register 3 (DR3).
+
+ Writes and returns a new value to DR3. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr3 The value to write to Dr3.
+
+ @return The value written to Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr3 (
+ UINTN Dr3
+ )
+{
+ mUnitTestHostBaseLibDr[3] = Dr3;
+ return Dr3;
+}
+
+/**
+ Writes a value to Debug Register 4 (DR4).
+
+ Writes and returns a new value to DR4. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr4 The value to write to Dr4.
+
+ @return The value written to Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr4 (
+ UINTN Dr4
+ )
+{
+ mUnitTestHostBaseLibDr[4] = Dr4;
+ return Dr4;
+}
+
+/**
+ Writes a value to Debug Register 5 (DR5).
+
+ Writes and returns a new value to DR5. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr5 The value to write to Dr5.
+
+ @return The value written to Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr5 (
+ UINTN Dr5
+ )
+{
+ mUnitTestHostBaseLibDr[5] = Dr5;
+ return Dr5;
+}
+
+/**
+ Writes a value to Debug Register 6 (DR6).
+
+ Writes and returns a new value to DR6. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr6 The value to write to Dr6.
+
+ @return The value written to Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr6 (
+ UINTN Dr6
+ )
+{
+ mUnitTestHostBaseLibDr[6] = Dr6;
+ return Dr6;
+}
+
+/**
+ Writes a value to Debug Register 7 (DR7).
+
+ Writes and returns a new value to DR7. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr7 The value to write to Dr7.
+
+ @return The value written to Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmWriteDr7 (
+ UINTN Dr7
+ )
+{
+ mUnitTestHostBaseLibDr[7] = Dr7;
+ return Dr7;
+}
+
+/**
+ Reads the current value of Code Segment Register (CS).
+
+ Reads and returns the current value of CS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of CS.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadCs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_CS];
+}
+
+/**
+ Reads the current value of Data Segment Register (DS).
+
+ Reads and returns the current value of DS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of DS.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadDs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_DS];
+}
+
+/**
+ Reads the current value of Extra Segment Register (ES).
+
+ Reads and returns the current value of ES. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of ES.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadEs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_ES];
+}
+
+/**
+ Reads the current value of FS Data Segment Register (FS).
+
+ Reads and returns the current value of FS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of FS.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadFs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_FS];
+}
+
+/**
+ Reads the current value of GS Data Segment Register (GS).
+
+ Reads and returns the current value of GS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of GS.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadGs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_GS];
+}
+
+/**
+ Reads the current value of Stack Segment Register (SS).
+
+ Reads and returns the current value of SS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of SS.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadSs (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_SS];
+}
+
+/**
+ Reads the current value of Task Register (TR).
+
+ Reads and returns the current value of TR. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of TR.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadTr (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_TR];
+}
+
+/**
+ Reads the current Global Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current GDTR descriptor and returns it in Gdtr. This
+ function is only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmReadGdtr (
+ OUT IA32_DESCRIPTOR *Gdtr
+ )
+{
+ Gdtr = &mUnitTestHostBaseLibGdtr;
+}
+
+/**
+ Writes the current Global Descriptor Table Register (GDTR) descriptor.
+
+ Writes and the current GDTR descriptor specified by Gdtr. This function is
+ only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmWriteGdtr (
+ IN CONST IA32_DESCRIPTOR *Gdtr
+ )
+{
+ CopyMem (&mUnitTestHostBaseLibGdtr, Gdtr, sizeof (IA32_DESCRIPTOR));
+}
+
+/**
+ Reads the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Reads and returns the current IDTR descriptor and returns it in Idtr. This
+ function is only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmReadIdtr (
+ OUT IA32_DESCRIPTOR *Idtr
+ )
+{
+ Idtr = &mUnitTestHostBaseLibIdtr;
+}
+
+/**
+ Writes the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Writes the current IDTR descriptor and returns it in Idtr. This function is
+ only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmWriteIdtr (
+ IN CONST IA32_DESCRIPTOR *Idtr
+ )
+{
+ CopyMem (&mUnitTestHostBaseLibIdtr, Idtr, sizeof (IA32_DESCRIPTOR));
+}
+
+/**
+ Reads the current Local Descriptor Table Register(LDTR) selector.
+
+ Reads and returns the current 16-bit LDTR descriptor value. This function is
+ only available on IA-32 and x64.
+
+ @return The current selector of LDT.
+
+**/
+UINT16
+EFIAPI
+UnitTestHostBaseLibAsmReadLdtr (
+ VOID
+ )
+{
+ return mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_LDTR];
+}
+
+/**
+ Writes the current Local Descriptor Table Register (LDTR) selector.
+
+ Writes and the current LDTR descriptor specified by Ldtr. This function is
+ only available on IA-32 and x64.
+
+ @param Ldtr 16-bit LDTR selector value.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmWriteLdtr (
+ IN UINT16 Ldtr
+ )
+{
+ mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_LDTR] = Ldtr;
+}
+
+/**
+ Reads the current value of a Performance Counter (PMC).
+
+ Reads and returns the current value of performance counter specified by
+ Index. This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit Performance Counter index to read.
+
+ @return The value of the PMC specified by Index.
+
+**/
+UINT64
+EFIAPI
+UnitTestHostBaseLibAsmReadPmc (
+ IN UINT32 Index
+ )
+{
+ return 0;
+}
+
+/**
+ Sets up a monitor buffer that is used by AsmMwait().
+
+ Executes a MONITOR instruction with the register state specified by Eax, Ecx
+ and Edx. Returns Eax. This function is only available on IA-32 and x64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+ @param Edx The value to load into EDX or RDX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmMonitor (
+ IN UINTN Eax,
+ IN UINTN Ecx,
+ IN UINTN Edx
+ )
+{
+ return Eax;
+}
+
+/**
+ Executes an MWAIT instruction.
+
+ Executes an MWAIT instruction with the register state specified by Eax and
+ Ecx. Returns Eax. This function is only available on IA-32 and x64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+UnitTestHostBaseLibAsmMwait (
+ IN UINTN Eax,
+ IN UINTN Ecx
+ )
+{
+ return Eax;
+}
+
+/**
+ Executes a WBINVD instruction.
+
+ Executes a WBINVD instruction. This function is only available on IA-32 and
+ x64.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmWbinvd (
+ VOID
+ )
+{
+}
+
+/**
+ Executes a INVD instruction.
+
+ Executes a INVD instruction. This function is only available on IA-32 and
+ x64.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmInvd (
+ VOID
+ )
+{
+}
+
+/**
+ Flushes a cache line from all the instruction and data caches within the
+ coherency domain of the CPU.
+
+ Flushed the cache line specified by LinearAddress, and returns LinearAddress.
+ This function is only available on IA-32 and x64.
+
+ @param LinearAddress The address of the cache line to flush. If the CPU is
+ in a physical addressing mode, then LinearAddress is a
+ physical address. If the CPU is in a virtual
+ addressing mode, then LinearAddress is a virtual
+ address.
+
+ @return LinearAddress.
+**/
+VOID *
+EFIAPI
+UnitTestHostBaseLibAsmFlushCacheLine (
+ IN VOID *LinearAddress
+ )
+{
+ return LinearAddress;
+}
+
+/**
+ Enables the 32-bit paging mode on the CPU.
+
+ Enables the 32-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode. This function is
+ only available on IA-32. After the 32-bit paging mode is enabled, control is
+ transferred to the function specified by EntryPoint using the new stack
+ specified by NewStack and passing in the parameters specified by Context1 and
+ Context2. Context1 and Context2 are optional and may be NULL. The function
+ EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit protected mode with flat descriptors. This
+ means all descriptors must have a base of 0 and a limit of 4GB.
+ 3) CR0 and CR4 must be compatible with 32-bit protected mode with flat
+ descriptors.
+ 4) CR3 must point to valid page tables that will be used once the transition
+ is complete, and those page tables must guarantee that the pages for this
+ function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is enabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is enabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is enabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmEnablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ EntryPoint (Context1, Context2);
+}
+
+/**
+ Disables the 32-bit paging mode on the CPU.
+
+ Disables the 32-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 32-paged protected
+ mode. This function is only available on IA-32. After the 32-bit paging mode
+ is disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be NULL. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit paged mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit paged mode.
+ 3) CR0, CR3, and CR4 must be compatible with 32-bit paged mode.
+ 4) CR3 must point to valid page tables that guarantee that the pages for
+ this function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is disabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is disabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is
+ disabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmDisablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ EntryPoint (Context1, Context2);
+}
+
+/**
+ Enables the 64-bit paging mode on the CPU.
+
+ Enables the 64-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode with flat
+ descriptors. This function is only available on IA-32. After the 64-bit
+ paging mode is enabled, control is transferred to the function specified by
+ EntryPoint using the new stack specified by NewStack and passing in the
+ parameters specified by Context1 and Context2. Context1 and Context2 are
+ optional and may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode with flat
+ descriptors, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for long mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is enabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is enabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is enabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmEnablePaging64 (
+ IN UINT16 Cs,
+ IN UINT64 EntryPoint,
+ IN UINT64 Context1, OPTIONAL
+ IN UINT64 Context2, OPTIONAL
+ IN UINT64 NewStack
+ )
+{
+ SWITCH_STACK_ENTRY_POINT NewEntryPoint;
+
+ NewEntryPoint = (SWITCH_STACK_ENTRY_POINT)(UINTN)(EntryPoint);
+ NewEntryPoint ((VOID *)(UINTN)Context1, (VOID *)(UINTN)Context2);
+}
+
+/**
+ Disables the 64-bit paging mode on the CPU.
+
+ Disables the 64-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 64-paging mode.
+ This function is only available on x64. After the 64-bit paging mode is
+ disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 64-bit paged mode, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for 32-bit protected mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is disabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is disabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is disabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmDisablePaging64 (
+ IN UINT16 Cs,
+ IN UINT32 EntryPoint,
+ IN UINT32 Context1, OPTIONAL
+ IN UINT32 Context2, OPTIONAL
+ IN UINT32 NewStack
+ )
+{
+ SWITCH_STACK_ENTRY_POINT NewEntryPoint;
+
+ NewEntryPoint = (SWITCH_STACK_ENTRY_POINT)(UINTN)(EntryPoint);
+ NewEntryPoint ((VOID *)(UINTN)Context1, (VOID *)(UINTN)Context2);
+}
+
+/**
+ Retrieves the properties for 16-bit thunk functions.
+
+ Computes the size of the buffer and stack below 1MB required to use the
+ AsmPrepareThunk16(), AsmThunk16() and AsmPrepareAndThunk16() functions. This
+ buffer size is returned in RealModeBufferSize, and the stack size is returned
+ in ExtraStackSize. If parameters are passed to the 16-bit real mode code,
+ then the actual minimum stack size is ExtraStackSize plus the maximum number
+ of bytes that need to be passed to the 16-bit real mode code.
+
+ If RealModeBufferSize is NULL, then ASSERT().
+ If ExtraStackSize is NULL, then ASSERT().
+
+ @param RealModeBufferSize A pointer to the size of the buffer below 1MB
+ required to use the 16-bit thunk functions.
+ @param ExtraStackSize A pointer to the extra size of stack below 1MB
+ that the 16-bit thunk functions require for
+ temporary storage in the transition to and from
+ 16-bit real mode.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmGetThunk16Properties (
+ OUT UINT32 *RealModeBufferSize,
+ OUT UINT32 *ExtraStackSize
+ )
+{
+ *RealModeBufferSize = 0;
+ *ExtraStackSize = 0;
+}
+
+/**
+ Prepares all structures a code required to use AsmThunk16().
+
+ Prepares all structures and code required to use AsmThunk16().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ If ThunkContext is NULL, then ASSERT().
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmPrepareThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+}
+
+/**
+ Transfers control to a 16-bit real mode entry point and returns the results.
+
+ Transfers control to a 16-bit real mode entry point and returns the results.
+ AsmPrepareThunk16() must be called with ThunkContext before this function is used.
+ This function must be called with interrupts disabled.
+
+ The register state from the RealModeState field of ThunkContext is restored just prior
+ to calling the 16-bit real mode entry point. This includes the EFLAGS field of RealModeState,
+ which is used to set the interrupt state when a 16-bit real mode entry point is called.
+ Control is transferred to the 16-bit real mode entry point specified by the CS and Eip fields of RealModeState.
+ The stack is initialized to the SS and ESP fields of RealModeState. Any parameters passed to
+ the 16-bit real mode code must be populated by the caller at SS:ESP prior to calling this function.
+ The 16-bit real mode entry point is invoked with a 16-bit CALL FAR instruction,
+ so when accessing stack contents, the 16-bit real mode code must account for the 16-bit segment
+ and 16-bit offset of the return address that were pushed onto the stack. The 16-bit real mode entry
+ point must exit with a RETF instruction. The register state is captured into RealModeState immediately
+ after the RETF instruction is executed.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ or any of the 16-bit real mode code makes a SW interrupt, then the caller is responsible for making sure
+ the IDT at address 0 is initialized to handle any HW or SW interrupts that may occur while in 16-bit real mode.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ then the caller is responsible for making sure the 8259 PIC is in a state compatible with 16-bit real mode.
+ This includes the base vectors, the interrupt masks, and the edge/level trigger mode.
+
+ If THUNK_ATTRIBUTE_BIG_REAL_MODE is set in the ThunkAttributes field of ThunkContext, then the user code
+ is invoked in big real mode. Otherwise, the user code is invoked in 16-bit real mode with 64KB segment limits.
+
+ If neither THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 nor THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then it is assumed that the user code did not enable the A20 mask, and no attempt is made to
+ disable the A20 mask.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is set and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is clear in
+ ThunkAttributes, then attempt to use the INT 15 service to disable the A20 mask. If this INT 15 call fails,
+ then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is clear and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is set in
+ ThunkAttributes, then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If ThunkContext is NULL, then ASSERT().
+ If AsmPrepareThunk16() was not previously called with ThunkContext, then ASSERT().
+ If both THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then ASSERT().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer are mapped 1:1.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+}
+
+/**
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results.
+
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results. If the
+ caller only need to perform a single 16-bit real mode thunk, then this
+ service should be used. If the caller intends to make more than one 16-bit
+ real mode thunk, then it is more efficient if AsmPrepareThunk16() is called
+ once and AsmThunk16() can be called for each 16-bit real mode thunk.
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ See AsmPrepareThunk16() and AsmThunk16() for the detailed description and ASSERT() conditions.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmPrepareAndThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+}
+
+/**
+ Load given selector into TR register.
+
+ @param[in] Selector Task segment selector
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmWriteTr (
+ IN UINT16 Selector
+ )
+{
+ mUnitTestHostBaseLibSegment[UNIT_TEST_HOST_BASE_LIB_SEGMENT_TR] = Selector;
+}
+
+/**
+ Performs a serializing operation on all load-from-memory instructions that
+ were issued prior the AsmLfence function.
+
+ Executes a LFENCE instruction. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibAsmLfence (
+ VOID
+ )
+{
+}
+
+/**
+ Patch the immediate operand of an IA32 or X64 instruction such that the byte,
+ word, dword or qword operand is encoded at the end of the instruction's
+ binary representation.
+
+ This function should be used to update object code that was compiled with
+ NASM from assembly source code. Example:
+
+ NASM source code:
+
+ mov eax, strict dword 0 ; the imm32 zero operand will be patched
+ ASM_PFX(gPatchCr3):
+ mov cr3, eax
+
+ C source code:
+
+ X86_ASSEMBLY_PATCH_LABEL gPatchCr3;
+ PatchInstructionX86 (gPatchCr3, AsmReadCr3 (), 4);
+
+ @param[out] InstructionEnd Pointer right past the instruction to patch. The
+ immediate operand to patch is expected to
+ comprise the trailing bytes of the instruction.
+ If InstructionEnd is closer to address 0 than
+ ValueSize permits, then ASSERT().
+
+ @param[in] PatchValue The constant to write to the immediate operand.
+ The caller is responsible for ensuring that
+ PatchValue can be represented in the byte, word,
+ dword or qword operand (as indicated through
+ ValueSize); otherwise ASSERT().
+
+ @param[in] ValueSize The size of the operand in bytes; must be 1, 2,
+ 4, or 8. ASSERT() otherwise.
+**/
+VOID
+EFIAPI
+UnitTestHostBaseLibPatchInstructionX86 (
+ OUT X86_ASSEMBLY_PATCH_LABEL *InstructionEnd,
+ IN UINT64 PatchValue,
+ IN UINTN ValueSize
+ )
+{
+}
+
+/**
+ Retrieves CPUID information.
+
+ Executes the CPUID instruction with EAX set to the value specified by Index.
+ This function always returns Index.
+ If Eax is not NULL, then the value of EAX after CPUID is returned in Eax.
+ If Ebx is not NULL, then the value of EBX after CPUID is returned in Ebx.
+ If Ecx is not NULL, then the value of ECX after CPUID is returned in Ecx.
+ If Edx is not NULL, then the value of EDX after CPUID is returned in Edx.
+ This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit value to load into EAX prior to invoking the CPUID
+ instruction.
+ @param Eax The pointer to the 32-bit EAX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Ebx The pointer to the 32-bit EBX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Ecx The pointer to the 32-bit ECX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+ @param Edx The pointer to the 32-bit EDX value returned by the CPUID
+ instruction. This is an optional parameter that may be NULL.
+
+ @return Index.
+
+**/
+UINT32
+EFIAPI
+AsmCpuid (
+ IN UINT32 Index,
+ OUT UINT32 *Eax, OPTIONAL
+ OUT UINT32 *Ebx, OPTIONAL
+ OUT UINT32 *Ecx, OPTIONAL
+ OUT UINT32 *Edx OPTIONAL
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmCpuid (Index, Eax, Ebx, Ecx, Edx);
+}
+
+/**
+ Retrieves CPUID information using an extended leaf identifier.
+
+ Executes the CPUID instruction with EAX set to the value specified by Index
+ and ECX set to the value specified by SubIndex. This function always returns
+ Index. This function is only available on IA-32 and x64.
+
+ If Eax is not NULL, then the value of EAX after CPUID is returned in Eax.
+ If Ebx is not NULL, then the value of EBX after CPUID is returned in Ebx.
+ If Ecx is not NULL, then the value of ECX after CPUID is returned in Ecx.
+ If Edx is not NULL, then the value of EDX after CPUID is returned in Edx.
+
+ @param Index The 32-bit value to load into EAX prior to invoking the
+ CPUID instruction.
+ @param SubIndex The 32-bit value to load into ECX prior to invoking the
+ CPUID instruction.
+ @param Eax The pointer to the 32-bit EAX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Ebx The pointer to the 32-bit EBX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Ecx The pointer to the 32-bit ECX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+ @param Edx The pointer to the 32-bit EDX value returned by the CPUID
+ instruction. This is an optional parameter that may be
+ NULL.
+
+ @return Index.
+
+**/
+UINT32
+EFIAPI
+AsmCpuidEx (
+ IN UINT32 Index,
+ IN UINT32 SubIndex,
+ OUT UINT32 *Eax, OPTIONAL
+ OUT UINT32 *Ebx, OPTIONAL
+ OUT UINT32 *Ecx, OPTIONAL
+ OUT UINT32 *Edx OPTIONAL
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmCpuidEx (Index, SubIndex, Eax, Ebx, Ecx, Edx);
+}
+
+/**
+ Set CD bit and clear NW bit of CR0 followed by a WBINVD.
+
+ Disables the caches by setting the CD bit of CR0 to 1, clearing the NW bit of CR0 to 0,
+ and executing a WBINVD instruction. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+AsmDisableCache (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmDisableCache ();
+}
+
+/**
+ Perform a WBINVD and clear both the CD and NW bits of CR0.
+
+ Enables the caches by executing a WBINVD instruction and then clear both the CD and NW
+ bits of CR0 to 0. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+AsmEnableCache (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmEnableCache ();
+}
+
+/**
+ Returns a 64-bit Machine Specific Register(MSR).
+
+ Reads and returns the 64-bit MSR specified by Index. No parameter checking is
+ performed on Index, and some Index values may cause CPU exceptions. The
+ caller must either guarantee that Index is valid, or the caller must set up
+ exception handlers to catch the exceptions. This function is only available
+ on IA-32 and x64.
+
+ @param Index The 32-bit MSR index to read.
+
+ @return The value of the MSR identified by Index.
+
+**/
+UINT64
+EFIAPI
+AsmReadMsr64 (
+ IN UINT32 Index
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadMsr64 (Index);
+}
+
+/**
+ Writes a 64-bit value to a Machine Specific Register(MSR), and returns the
+ value.
+
+ Writes the 64-bit value specified by Value to the MSR specified by Index. The
+ 64-bit value written to the MSR is returned. No parameter checking is
+ performed on Index or Value, and some of these may cause CPU exceptions. The
+ caller must either guarantee that Index and Value are valid, or the caller
+ must establish proper exception handlers. This function is only available on
+ IA-32 and x64.
+
+ @param Index The 32-bit MSR index to write.
+ @param Value The 64-bit value to write to the MSR.
+
+ @return Value
+
+**/
+UINT64
+EFIAPI
+AsmWriteMsr64 (
+ IN UINT32 Index,
+ IN UINT64 Value
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteMsr64 (Index, Value);
+}
+
+/**
+ Reads the current value of the Control Register 0 (CR0).
+
+ Reads and returns the current value of CR0. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 0 (CR0).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr0 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadCr0 ();
+}
+
+/**
+ Reads the current value of the Control Register 2 (CR2).
+
+ Reads and returns the current value of CR2. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 2 (CR2).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr2 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadCr2 ();
+}
+
+/**
+ Reads the current value of the Control Register 3 (CR3).
+
+ Reads and returns the current value of CR3. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 3 (CR3).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr3 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadCr3 ();
+}
+
+/**
+ Reads the current value of the Control Register 4 (CR4).
+
+ Reads and returns the current value of CR4. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of the Control Register 4 (CR4).
+
+**/
+UINTN
+EFIAPI
+AsmReadCr4 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadCr4 ();
+}
+
+/**
+ Writes a value to Control Register 0 (CR0).
+
+ Writes and returns a new value to CR0. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr0 The value to write to CR0.
+
+ @return The value written to CR0.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr0 (
+ UINTN Cr0
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteCr0 (Cr0);
+}
+
+/**
+ Writes a value to Control Register 2 (CR2).
+
+ Writes and returns a new value to CR2. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr2 The value to write to CR2.
+
+ @return The value written to CR2.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr2 (
+ UINTN Cr2
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteCr2 (Cr2);
+}
+
+/**
+ Writes a value to Control Register 3 (CR3).
+
+ Writes and returns a new value to CR3. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr3 The value to write to CR3.
+
+ @return The value written to CR3.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr3 (
+ UINTN Cr3
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteCr3 (Cr3);
+}
+
+/**
+ Writes a value to Control Register 4 (CR4).
+
+ Writes and returns a new value to CR4. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Cr4 The value to write to CR4.
+
+ @return The value written to CR4.
+
+**/
+UINTN
+EFIAPI
+AsmWriteCr4 (
+ UINTN Cr4
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteCr4 (Cr4);
+}
+
+/**
+ Reads the current value of Debug Register 0 (DR0).
+
+ Reads and returns the current value of DR0. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr0 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr0 ();
+}
+
+/**
+ Reads the current value of Debug Register 1 (DR1).
+
+ Reads and returns the current value of DR1. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr1 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr1 ();
+}
+
+/**
+ Reads the current value of Debug Register 2 (DR2).
+
+ Reads and returns the current value of DR2. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr2 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr2 ();
+}
+
+/**
+ Reads the current value of Debug Register 3 (DR3).
+
+ Reads and returns the current value of DR3. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr3 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr3 ();
+}
+
+/**
+ Reads the current value of Debug Register 4 (DR4).
+
+ Reads and returns the current value of DR4. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr4 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr4 ();
+}
+
+/**
+ Reads the current value of Debug Register 5 (DR5).
+
+ Reads and returns the current value of DR5. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr5 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr5 ();
+}
+
+/**
+ Reads the current value of Debug Register 6 (DR6).
+
+ Reads and returns the current value of DR6. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr6 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr6 ();
+}
+
+/**
+ Reads the current value of Debug Register 7 (DR7).
+
+ Reads and returns the current value of DR7. This function is only available
+ on IA-32 and x64. This returns a 32-bit value on IA-32 and a 64-bit value on
+ x64.
+
+ @return The value of Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+AsmReadDr7 (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDr7 ();
+}
+
+/**
+ Writes a value to Debug Register 0 (DR0).
+
+ Writes and returns a new value to DR0. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr0 The value to write to Dr0.
+
+ @return The value written to Debug Register 0 (DR0).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr0 (
+ UINTN Dr0
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr0 (Dr0);
+}
+
+/**
+ Writes a value to Debug Register 1 (DR1).
+
+ Writes and returns a new value to DR1. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr1 The value to write to Dr1.
+
+ @return The value written to Debug Register 1 (DR1).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr1 (
+ UINTN Dr1
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr1 (Dr1);
+}
+
+/**
+ Writes a value to Debug Register 2 (DR2).
+
+ Writes and returns a new value to DR2. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr2 The value to write to Dr2.
+
+ @return The value written to Debug Register 2 (DR2).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr2 (
+ UINTN Dr2
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr2 (Dr2);
+}
+
+/**
+ Writes a value to Debug Register 3 (DR3).
+
+ Writes and returns a new value to DR3. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr3 The value to write to Dr3.
+
+ @return The value written to Debug Register 3 (DR3).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr3 (
+ UINTN Dr3
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr3 (Dr3);
+}
+
+/**
+ Writes a value to Debug Register 4 (DR4).
+
+ Writes and returns a new value to DR4. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr4 The value to write to Dr4.
+
+ @return The value written to Debug Register 4 (DR4).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr4 (
+ UINTN Dr4
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr4 (Dr4);
+}
+
+/**
+ Writes a value to Debug Register 5 (DR5).
+
+ Writes and returns a new value to DR5. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr5 The value to write to Dr5.
+
+ @return The value written to Debug Register 5 (DR5).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr5 (
+ UINTN Dr5
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr5 (Dr5);
+}
+
+/**
+ Writes a value to Debug Register 6 (DR6).
+
+ Writes and returns a new value to DR6. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr6 The value to write to Dr6.
+
+ @return The value written to Debug Register 6 (DR6).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr6 (
+ UINTN Dr6
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr6 (Dr6);
+}
+
+/**
+ Writes a value to Debug Register 7 (DR7).
+
+ Writes and returns a new value to DR7. This function is only available on
+ IA-32 and x64. This writes a 32-bit value on IA-32 and a 64-bit value on x64.
+
+ @param Dr7 The value to write to Dr7.
+
+ @return The value written to Debug Register 7 (DR7).
+
+**/
+UINTN
+EFIAPI
+AsmWriteDr7 (
+ UINTN Dr7
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmWriteDr7 (Dr7);
+}
+
+/**
+ Reads the current value of Code Segment Register (CS).
+
+ Reads and returns the current value of CS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of CS.
+
+**/
+UINT16
+EFIAPI
+AsmReadCs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadCs ();
+}
+
+/**
+ Reads the current value of Data Segment Register (DS).
+
+ Reads and returns the current value of DS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of DS.
+
+**/
+UINT16
+EFIAPI
+AsmReadDs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadDs ();
+}
+
+/**
+ Reads the current value of Extra Segment Register (ES).
+
+ Reads and returns the current value of ES. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of ES.
+
+**/
+UINT16
+EFIAPI
+AsmReadEs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadEs ();
+}
+
+/**
+ Reads the current value of FS Data Segment Register (FS).
+
+ Reads and returns the current value of FS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of FS.
+
+**/
+UINT16
+EFIAPI
+AsmReadFs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadFs ();
+}
+
+/**
+ Reads the current value of GS Data Segment Register (GS).
+
+ Reads and returns the current value of GS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of GS.
+
+**/
+UINT16
+EFIAPI
+AsmReadGs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadGs ();
+}
+
+/**
+ Reads the current value of Stack Segment Register (SS).
+
+ Reads and returns the current value of SS. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of SS.
+
+**/
+UINT16
+EFIAPI
+AsmReadSs (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadSs ();
+}
+
+/**
+ Reads the current value of Task Register (TR).
+
+ Reads and returns the current value of TR. This function is only available on
+ IA-32 and x64.
+
+ @return The current value of TR.
+
+**/
+UINT16
+EFIAPI
+AsmReadTr (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadTr ();
+}
+
+/**
+ Reads the current Global Descriptor Table Register(GDTR) descriptor.
+
+ Reads and returns the current GDTR descriptor and returns it in Gdtr. This
+ function is only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmReadGdtr (
+ OUT IA32_DESCRIPTOR *Gdtr
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmReadGdtr (Gdtr);
+}
+
+/**
+ Writes the current Global Descriptor Table Register (GDTR) descriptor.
+
+ Writes and the current GDTR descriptor specified by Gdtr. This function is
+ only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmWriteGdtr (
+ IN CONST IA32_DESCRIPTOR *Gdtr
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmWriteGdtr (Gdtr);
+}
+
+/**
+ Reads the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Reads and returns the current IDTR descriptor and returns it in Idtr. This
+ function is only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmReadIdtr (
+ OUT IA32_DESCRIPTOR *Idtr
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmReadIdtr (Idtr);
+}
+
+/**
+ Writes the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Writes the current IDTR descriptor and returns it in Idtr. This function is
+ only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmWriteIdtr (
+ IN CONST IA32_DESCRIPTOR *Idtr
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmWriteIdtr (Idtr);
+}
+
+/**
+ Reads the current Local Descriptor Table Register(LDTR) selector.
+
+ Reads and returns the current 16-bit LDTR descriptor value. This function is
+ only available on IA-32 and x64.
+
+ @return The current selector of LDT.
+
+**/
+UINT16
+EFIAPI
+AsmReadLdtr (
+ VOID
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadLdtr ();
+}
+
+/**
+ Writes the current Local Descriptor Table Register (LDTR) selector.
+
+ Writes and the current LDTR descriptor specified by Ldtr. This function is
+ only available on IA-32 and x64.
+
+ @param Ldtr 16-bit LDTR selector value.
+
+**/
+VOID
+EFIAPI
+AsmWriteLdtr (
+ IN UINT16 Ldtr
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmWriteLdtr (Ldtr);
+}
+
+/**
+ Reads the current value of a Performance Counter (PMC).
+
+ Reads and returns the current value of performance counter specified by
+ Index. This function is only available on IA-32 and x64.
+
+ @param Index The 32-bit Performance Counter index to read.
+
+ @return The value of the PMC specified by Index.
+
+**/
+UINT64
+EFIAPI
+AsmReadPmc (
+ IN UINT32 Index
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmReadPmc (Index);
+}
+
+/**
+ Sets up a monitor buffer that is used by AsmMwait().
+
+ Executes a MONITOR instruction with the register state specified by Eax, Ecx
+ and Edx. Returns Eax. This function is only available on IA-32 and x64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+ @param Edx The value to load into EDX or RDX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+AsmMonitor (
+ IN UINTN Eax,
+ IN UINTN Ecx,
+ IN UINTN Edx
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmMonitor (Eax, Ecx, Edx);
+}
+
+/**
+ Executes an MWAIT instruction.
+
+ Executes an MWAIT instruction with the register state specified by Eax and
+ Ecx. Returns Eax. This function is only available on IA-32 and x64.
+
+ @param Eax The value to load into EAX or RAX before executing the MONITOR
+ instruction.
+ @param Ecx The value to load into ECX or RCX before executing the MONITOR
+ instruction.
+
+ @return Eax
+
+**/
+UINTN
+EFIAPI
+AsmMwait (
+ IN UINTN Eax,
+ IN UINTN Ecx
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmMwait (Eax, Ecx);
+}
+
+/**
+ Executes a WBINVD instruction.
+
+ Executes a WBINVD instruction. This function is only available on IA-32 and
+ x64.
+
+**/
+VOID
+EFIAPI
+AsmWbinvd (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmWbinvd ();
+}
+
+/**
+ Executes a INVD instruction.
+
+ Executes a INVD instruction. This function is only available on IA-32 and
+ x64.
+
+**/
+VOID
+EFIAPI
+AsmInvd (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmInvd ();
+}
+
+/**
+ Flushes a cache line from all the instruction and data caches within the
+ coherency domain of the CPU.
+
+ Flushed the cache line specified by LinearAddress, and returns LinearAddress.
+ This function is only available on IA-32 and x64.
+
+ @param LinearAddress The address of the cache line to flush. If the CPU is
+ in a physical addressing mode, then LinearAddress is a
+ physical address. If the CPU is in a virtual
+ addressing mode, then LinearAddress is a virtual
+ address.
+
+ @return LinearAddress.
+**/
+VOID *
+EFIAPI
+AsmFlushCacheLine (
+ IN VOID *LinearAddress
+ )
+{
+ return gUnitTestHostBaseLib.X86->AsmFlushCacheLine (LinearAddress);
+}
+
+/**
+ Enables the 32-bit paging mode on the CPU.
+
+ Enables the 32-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode. This function is
+ only available on IA-32. After the 32-bit paging mode is enabled, control is
+ transferred to the function specified by EntryPoint using the new stack
+ specified by NewStack and passing in the parameters specified by Context1 and
+ Context2. Context1 and Context2 are optional and may be NULL. The function
+ EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit protected mode with flat descriptors. This
+ means all descriptors must have a base of 0 and a limit of 4GB.
+ 3) CR0 and CR4 must be compatible with 32-bit protected mode with flat
+ descriptors.
+ 4) CR3 must point to valid page tables that will be used once the transition
+ is complete, and those page tables must guarantee that the pages for this
+ function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is enabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is enabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is enabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+AsmEnablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmEnablePaging32 (EntryPoint, Context1, Context2, NewStack);
+}
+
+/**
+ Disables the 32-bit paging mode on the CPU.
+
+ Disables the 32-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 32-paged protected
+ mode. This function is only available on IA-32. After the 32-bit paging mode
+ is disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be NULL. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit paged mode, then ASSERT().
+ If EntryPoint is NULL, then ASSERT().
+ If NewStack is NULL, then ASSERT().
+
+ There are a number of constraints that must be followed before calling this
+ function:
+ 1) Interrupts must be disabled.
+ 2) The caller must be in 32-bit paged mode.
+ 3) CR0, CR3, and CR4 must be compatible with 32-bit paged mode.
+ 4) CR3 must point to valid page tables that guarantee that the pages for
+ this function and the stack are identity mapped.
+
+ @param EntryPoint A pointer to function to call with the new stack after
+ paging is disabled.
+ @param Context1 A pointer to the context to pass into the EntryPoint
+ function as the first parameter after paging is disabled.
+ @param Context2 A pointer to the context to pass into the EntryPoint
+ function as the second parameter after paging is
+ disabled.
+ @param NewStack A pointer to the new stack to use for the EntryPoint
+ function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+AsmDisablePaging32 (
+ IN SWITCH_STACK_ENTRY_POINT EntryPoint,
+ IN VOID *Context1, OPTIONAL
+ IN VOID *Context2, OPTIONAL
+ IN VOID *NewStack
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmDisablePaging32 (EntryPoint, Context1, Context2, NewStack);
+}
+
+/**
+ Enables the 64-bit paging mode on the CPU.
+
+ Enables the 64-bit paging mode on the CPU. CR0, CR3, CR4, and the page tables
+ must be properly initialized prior to calling this service. This function
+ assumes the current execution mode is 32-bit protected mode with flat
+ descriptors. This function is only available on IA-32. After the 64-bit
+ paging mode is enabled, control is transferred to the function specified by
+ EntryPoint using the new stack specified by NewStack and passing in the
+ parameters specified by Context1 and Context2. Context1 and Context2 are
+ optional and may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 32-bit protected mode with flat
+ descriptors, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for long mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is enabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is enabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is enabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is enabled.
+
+**/
+VOID
+EFIAPI
+AsmEnablePaging64 (
+ IN UINT16 Cs,
+ IN UINT64 EntryPoint,
+ IN UINT64 Context1, OPTIONAL
+ IN UINT64 Context2, OPTIONAL
+ IN UINT64 NewStack
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmEnablePaging64 (Cs, EntryPoint, Context1, Context2, NewStack);
+}
+
+/**
+ Disables the 64-bit paging mode on the CPU.
+
+ Disables the 64-bit paging mode on the CPU and returns to 32-bit protected
+ mode. This function assumes the current execution mode is 64-paging mode.
+ This function is only available on x64. After the 64-bit paging mode is
+ disabled, control is transferred to the function specified by EntryPoint
+ using the new stack specified by NewStack and passing in the parameters
+ specified by Context1 and Context2. Context1 and Context2 are optional and
+ may be 0. The function EntryPoint must never return.
+
+ If the current execution mode is not 64-bit paged mode, then ASSERT().
+ If EntryPoint is 0, then ASSERT().
+ If NewStack is 0, then ASSERT().
+
+ @param Cs The 16-bit selector to load in the CS before EntryPoint
+ is called. The descriptor in the GDT that this selector
+ references must be setup for 32-bit protected mode.
+ @param EntryPoint The 64-bit virtual address of the function to call with
+ the new stack after paging is disabled.
+ @param Context1 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the first parameter after
+ paging is disabled.
+ @param Context2 The 64-bit virtual address of the context to pass into
+ the EntryPoint function as the second parameter after
+ paging is disabled.
+ @param NewStack The 64-bit virtual address of the new stack to use for
+ the EntryPoint function after paging is disabled.
+
+**/
+VOID
+EFIAPI
+AsmDisablePaging64 (
+ IN UINT16 Cs,
+ IN UINT32 EntryPoint,
+ IN UINT32 Context1, OPTIONAL
+ IN UINT32 Context2, OPTIONAL
+ IN UINT32 NewStack
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmDisablePaging64 (Cs, EntryPoint, Context1, Context2, NewStack);
+}
+
+/**
+ Retrieves the properties for 16-bit thunk functions.
+
+ Computes the size of the buffer and stack below 1MB required to use the
+ AsmPrepareThunk16(), AsmThunk16() and AsmPrepareAndThunk16() functions. This
+ buffer size is returned in RealModeBufferSize, and the stack size is returned
+ in ExtraStackSize. If parameters are passed to the 16-bit real mode code,
+ then the actual minimum stack size is ExtraStackSize plus the maximum number
+ of bytes that need to be passed to the 16-bit real mode code.
+
+ If RealModeBufferSize is NULL, then ASSERT().
+ If ExtraStackSize is NULL, then ASSERT().
+
+ @param RealModeBufferSize A pointer to the size of the buffer below 1MB
+ required to use the 16-bit thunk functions.
+ @param ExtraStackSize A pointer to the extra size of stack below 1MB
+ that the 16-bit thunk functions require for
+ temporary storage in the transition to and from
+ 16-bit real mode.
+
+**/
+VOID
+EFIAPI
+AsmGetThunk16Properties (
+ OUT UINT32 *RealModeBufferSize,
+ OUT UINT32 *ExtraStackSize
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmGetThunk16Properties (RealModeBufferSize, ExtraStackSize);
+}
+
+/**
+ Prepares all structures a code required to use AsmThunk16().
+
+ Prepares all structures and code required to use AsmThunk16().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ If ThunkContext is NULL, then ASSERT().
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmPrepareThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmPrepareThunk16 (ThunkContext);
+}
+
+/**
+ Transfers control to a 16-bit real mode entry point and returns the results.
+
+ Transfers control to a 16-bit real mode entry point and returns the results.
+ AsmPrepareThunk16() must be called with ThunkContext before this function is used.
+ This function must be called with interrupts disabled.
+
+ The register state from the RealModeState field of ThunkContext is restored just prior
+ to calling the 16-bit real mode entry point. This includes the EFLAGS field of RealModeState,
+ which is used to set the interrupt state when a 16-bit real mode entry point is called.
+ Control is transferred to the 16-bit real mode entry point specified by the CS and Eip fields of RealModeState.
+ The stack is initialized to the SS and ESP fields of RealModeState. Any parameters passed to
+ the 16-bit real mode code must be populated by the caller at SS:ESP prior to calling this function.
+ The 16-bit real mode entry point is invoked with a 16-bit CALL FAR instruction,
+ so when accessing stack contents, the 16-bit real mode code must account for the 16-bit segment
+ and 16-bit offset of the return address that were pushed onto the stack. The 16-bit real mode entry
+ point must exit with a RETF instruction. The register state is captured into RealModeState immediately
+ after the RETF instruction is executed.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ or any of the 16-bit real mode code makes a SW interrupt, then the caller is responsible for making sure
+ the IDT at address 0 is initialized to handle any HW or SW interrupts that may occur while in 16-bit real mode.
+
+ If EFLAGS specifies interrupts enabled, or any of the 16-bit real mode code enables interrupts,
+ then the caller is responsible for making sure the 8259 PIC is in a state compatible with 16-bit real mode.
+ This includes the base vectors, the interrupt masks, and the edge/level trigger mode.
+
+ If THUNK_ATTRIBUTE_BIG_REAL_MODE is set in the ThunkAttributes field of ThunkContext, then the user code
+ is invoked in big real mode. Otherwise, the user code is invoked in 16-bit real mode with 64KB segment limits.
+
+ If neither THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 nor THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then it is assumed that the user code did not enable the A20 mask, and no attempt is made to
+ disable the A20 mask.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is set and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is clear in
+ ThunkAttributes, then attempt to use the INT 15 service to disable the A20 mask. If this INT 15 call fails,
+ then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 is clear and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL is set in
+ ThunkAttributes, then attempt to disable the A20 mask by directly accessing the 8042 keyboard controller I/O ports.
+
+ If ThunkContext is NULL, then ASSERT().
+ If AsmPrepareThunk16() was not previously called with ThunkContext, then ASSERT().
+ If both THUNK_ATTRIBUTE_DISABLE_A20_MASK_INT_15 and THUNK_ATTRIBUTE_DISABLE_A20_MASK_KBD_CTRL are set in
+ ThunkAttributes, then ASSERT().
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer are mapped 1:1.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmThunk16 (ThunkContext);
+}
+
+/**
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results.
+
+ Prepares all structures and code for a 16-bit real mode thunk, transfers
+ control to a 16-bit real mode entry point, and returns the results. If the
+ caller only need to perform a single 16-bit real mode thunk, then this
+ service should be used. If the caller intends to make more than one 16-bit
+ real mode thunk, then it is more efficient if AsmPrepareThunk16() is called
+ once and AsmThunk16() can be called for each 16-bit real mode thunk.
+
+ This interface is limited to be used in either physical mode or virtual modes with paging enabled where the
+ virtual to physical mappings for ThunkContext.RealModeBuffer is mapped 1:1.
+
+ See AsmPrepareThunk16() and AsmThunk16() for the detailed description and ASSERT() conditions.
+
+ @param ThunkContext A pointer to the context structure that describes the
+ 16-bit real mode code to call.
+
+**/
+VOID
+EFIAPI
+AsmPrepareAndThunk16 (
+ IN OUT THUNK_CONTEXT *ThunkContext
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmPrepareAndThunk16 (ThunkContext);
+}
+
+/**
+ Load given selector into TR register.
+
+ @param[in] Selector Task segment selector
+**/
+VOID
+EFIAPI
+AsmWriteTr (
+ IN UINT16 Selector
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmWriteTr (Selector);
+}
+
+/**
+ Performs a serializing operation on all load-from-memory instructions that
+ were issued prior the AsmLfence function.
+
+ Executes a LFENCE instruction. This function is only available on IA-32 and x64.
+
+**/
+VOID
+EFIAPI
+AsmLfence (
+ VOID
+ )
+{
+ gUnitTestHostBaseLib.X86->AsmLfence ();
+}
+
+/**
+ Patch the immediate operand of an IA32 or X64 instruction such that the byte,
+ word, dword or qword operand is encoded at the end of the instruction's
+ binary representation.
+
+ This function should be used to update object code that was compiled with
+ NASM from assembly source code. Example:
+
+ NASM source code:
+
+ mov eax, strict dword 0 ; the imm32 zero operand will be patched
+ ASM_PFX(gPatchCr3):
+ mov cr3, eax
+
+ C source code:
+
+ X86_ASSEMBLY_PATCH_LABEL gPatchCr3;
+ PatchInstructionX86 (gPatchCr3, AsmReadCr3 (), 4);
+
+ @param[out] InstructionEnd Pointer right past the instruction to patch. The
+ immediate operand to patch is expected to
+ comprise the trailing bytes of the instruction.
+ If InstructionEnd is closer to address 0 than
+ ValueSize permits, then ASSERT().
+
+ @param[in] PatchValue The constant to write to the immediate operand.
+ The caller is responsible for ensuring that
+ PatchValue can be represented in the byte, word,
+ dword or qword operand (as indicated through
+ ValueSize); otherwise ASSERT().
+
+ @param[in] ValueSize The size of the operand in bytes; must be 1, 2,
+ 4, or 8. ASSERT() otherwise.
+**/
+VOID
+EFIAPI
+PatchInstructionX86 (
+ OUT X86_ASSEMBLY_PATCH_LABEL *InstructionEnd,
+ IN UINT64 PatchValue,
+ IN UINTN ValueSize
+ )
+{
+ gUnitTestHostBaseLib.X86->PatchInstructionX86 (InstructionEnd, PatchValue, ValueSize);
+}
+
+///
+/// Common services
+///
+STATIC UNIT_TEST_HOST_BASE_LIB_COMMON mUnitTestHostBaseLibCommon = {
+ UnitTestHostBaseLibEnableInterrupts,
+ UnitTestHostBaseLibDisableInterrupts,
+ UnitTestHostBaseLibEnableDisableInterrupts,
+ UnitTestHostBaseLibGetInterruptState,
+};
+
+///
+/// IA32/X64 services
+///
+STATIC UNIT_TEST_HOST_BASE_LIB_X86 mUnitTestHostBaseLibX86 = {
+ UnitTestHostBaseLibAsmCpuid,
+ UnitTestHostBaseLibAsmCpuidEx,
+ UnitTestHostBaseLibAsmDisableCache,
+ UnitTestHostBaseLibAsmEnableCache,
+ UnitTestHostBaseLibAsmReadMsr64,
+ UnitTestHostBaseLibAsmWriteMsr64,
+ UnitTestHostBaseLibAsmReadCr0,
+ UnitTestHostBaseLibAsmReadCr2,
+ UnitTestHostBaseLibAsmReadCr3,
+ UnitTestHostBaseLibAsmReadCr4,
+ UnitTestHostBaseLibAsmWriteCr0,
+ UnitTestHostBaseLibAsmWriteCr2,
+ UnitTestHostBaseLibAsmWriteCr3,
+ UnitTestHostBaseLibAsmWriteCr4,
+ UnitTestHostBaseLibAsmReadDr0,
+ UnitTestHostBaseLibAsmReadDr1,
+ UnitTestHostBaseLibAsmReadDr2,
+ UnitTestHostBaseLibAsmReadDr3,
+ UnitTestHostBaseLibAsmReadDr4,
+ UnitTestHostBaseLibAsmReadDr5,
+ UnitTestHostBaseLibAsmReadDr6,
+ UnitTestHostBaseLibAsmReadDr7,
+ UnitTestHostBaseLibAsmWriteDr0,
+ UnitTestHostBaseLibAsmWriteDr1,
+ UnitTestHostBaseLibAsmWriteDr2,
+ UnitTestHostBaseLibAsmWriteDr3,
+ UnitTestHostBaseLibAsmWriteDr4,
+ UnitTestHostBaseLibAsmWriteDr5,
+ UnitTestHostBaseLibAsmWriteDr6,
+ UnitTestHostBaseLibAsmWriteDr7,
+ UnitTestHostBaseLibAsmReadCs,
+ UnitTestHostBaseLibAsmReadDs,
+ UnitTestHostBaseLibAsmReadEs,
+ UnitTestHostBaseLibAsmReadFs,
+ UnitTestHostBaseLibAsmReadGs,
+ UnitTestHostBaseLibAsmReadSs,
+ UnitTestHostBaseLibAsmReadTr,
+ UnitTestHostBaseLibAsmReadGdtr,
+ UnitTestHostBaseLibAsmWriteGdtr,
+ UnitTestHostBaseLibAsmReadIdtr,
+ UnitTestHostBaseLibAsmWriteIdtr,
+ UnitTestHostBaseLibAsmReadLdtr,
+ UnitTestHostBaseLibAsmWriteLdtr,
+ UnitTestHostBaseLibAsmReadPmc,
+ UnitTestHostBaseLibAsmMonitor,
+ UnitTestHostBaseLibAsmMwait,
+ UnitTestHostBaseLibAsmWbinvd,
+ UnitTestHostBaseLibAsmInvd,
+ UnitTestHostBaseLibAsmFlushCacheLine,
+ UnitTestHostBaseLibAsmEnablePaging32,
+ UnitTestHostBaseLibAsmDisablePaging32,
+ UnitTestHostBaseLibAsmEnablePaging64,
+ UnitTestHostBaseLibAsmDisablePaging64,
+ UnitTestHostBaseLibAsmGetThunk16Properties,
+ UnitTestHostBaseLibAsmPrepareThunk16,
+ UnitTestHostBaseLibAsmThunk16,
+ UnitTestHostBaseLibAsmPrepareAndThunk16,
+ UnitTestHostBaseLibAsmWriteTr,
+ UnitTestHostBaseLibAsmLfence,
+ UnitTestHostBaseLibPatchInstructionX86
+};
+
+///
+/// Structure of hook functions for BaseLib functions that can not be used from
+/// a host application. A simple emulation of these function is provided by
+/// default. A specific unit test can provide its own implementation for any
+/// of these functions.
+///
+UNIT_TEST_HOST_BASE_LIB gUnitTestHostBaseLib = {
+ &mUnitTestHostBaseLibCommon,
+ &mUnitTestHostBaseLibX86
+};
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteGdtr.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteGdtr.c
new file mode 100644
index 0000000..1a570e3
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteGdtr.c
@@ -0,0 +1,33 @@
+/** @file
+ IA-32/x64 AsmWriteGdtr()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Writes the current Global Descriptor Table Register (GDTR) descriptor.
+
+ Writes and the current GDTR descriptor specified by Gdtr. This function is
+ only available on IA-32 and x64.
+
+ If Gdtr is NULL, then ASSERT().
+
+ @param Gdtr The pointer to a GDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmWriteGdtr (
+ IN CONST IA32_DESCRIPTOR *Gdtr
+ )
+{
+ ASSERT (Gdtr != NULL);
+ InternalX86WriteGdtr (Gdtr);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteIdtr.c b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteIdtr.c
new file mode 100644
index 0000000..9ea979b
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseLib/X86WriteIdtr.c
@@ -0,0 +1,33 @@
+/** @file
+ IA-32/x64 AsmWriteIdtr()
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "BaseLibInternals.h"
+
+/**
+ Writes the current Interrupt Descriptor Table Register(IDTR) descriptor.
+
+ Writes the current IDTR descriptor and returns it in Idtr. This function is
+ only available on IA-32 and x64.
+
+ If Idtr is NULL, then ASSERT().
+
+ @param Idtr The pointer to a IDTR descriptor.
+
+**/
+VOID
+EFIAPI
+AsmWriteIdtr (
+ IN CONST IA32_DESCRIPTOR *Idtr
+ )
+{
+ ASSERT (Idtr != NULL);
+ InternalX86WriteIdtr (Idtr);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CompareMemWrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CompareMemWrapper.c
new file mode 100644
index 0000000..57d82f0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CompareMemWrapper.c
@@ -0,0 +1,60 @@
+/** @file
+ CompareMem() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Compares the contents of two buffers.
+
+ This function compares Length bytes of SourceBuffer to Length bytes of DestinationBuffer.
+ If all Length bytes of the two buffers are identical, then 0 is returned. Otherwise, the
+ value returned is the first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+ If Length > 0 and DestinationBuffer is NULL, then ASSERT().
+ If Length > 0 and SourceBuffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - DestinationBuffer + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - SourceBuffer + 1), then ASSERT().
+
+ @param DestinationBuffer A pointer to the destination buffer to compare.
+ @param SourceBuffer A pointer to the source buffer to compare.
+ @param Length The number of bytes to compare.
+
+ @return 0 All Length bytes of the two buffers are identical.
+ @retval Non-zero The first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+**/
+INTN
+EFIAPI
+CompareMem (
+ IN CONST VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ )
+{
+ if (Length == 0 || DestinationBuffer == SourceBuffer) {
+ return 0;
+ }
+ ASSERT (DestinationBuffer != NULL);
+ ASSERT (SourceBuffer != NULL);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)DestinationBuffer));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)SourceBuffer));
+
+ return InternalMemCompareMem (DestinationBuffer, SourceBuffer, Length);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMem.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMem.c
new file mode 100644
index 0000000..55e8616
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMem.c
@@ -0,0 +1,148 @@
+/** @file
+ Implementation of the InternalMemCopyMem routine. This function is broken
+ out into its own source file so that it can be excluded from a build for a
+ particular platform easily if an optimized version is desired.
+
+ Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
+ Copyright (c) 2012 - 2013, ARM Ltd. All rights reserved.<BR>
+ Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "MemLibInternals.h"
+
+/**
+ Copy Length bytes from Source to Destination.
+
+ @param DestinationBuffer The target of the copy request.
+ @param SourceBuffer The place to copy from.
+ @param Length The number of bytes to copy.
+
+ @return Destination
+
+**/
+VOID *
+EFIAPI
+InternalMemCopyMem (
+ OUT VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ )
+{
+ //
+ // Declare the local variables that actually move the data elements as
+ // volatile to prevent the optimizer from replacing this function with
+ // the intrinsic memcpy()
+ //
+ volatile UINT8 *Destination8;
+ CONST UINT8 *Source8;
+ volatile UINT32 *Destination32;
+ CONST UINT32 *Source32;
+ volatile UINT64 *Destination64;
+ CONST UINT64 *Source64;
+ UINTN Alignment;
+
+ if ((((UINTN)DestinationBuffer & 0x7) == 0) && (((UINTN)SourceBuffer & 0x7) == 0) && (Length >= 8)) {
+ if (SourceBuffer > DestinationBuffer) {
+ Destination64 = (UINT64*)DestinationBuffer;
+ Source64 = (CONST UINT64*)SourceBuffer;
+ while (Length >= 8) {
+ *(Destination64++) = *(Source64++);
+ Length -= 8;
+ }
+
+ // Finish if there are still some bytes to copy
+ Destination8 = (UINT8*)Destination64;
+ Source8 = (CONST UINT8*)Source64;
+ while (Length-- != 0) {
+ *(Destination8++) = *(Source8++);
+ }
+ } else if (SourceBuffer < DestinationBuffer) {
+ Destination64 = (UINT64*)((UINTN)DestinationBuffer + Length);
+ Source64 = (CONST UINT64*)((UINTN)SourceBuffer + Length);
+
+ // Destination64 and Source64 were aligned on a 64-bit boundary
+ // but if length is not a multiple of 8 bytes then they won't be
+ // anymore.
+
+ Alignment = Length & 0x7;
+ if (Alignment != 0) {
+ Destination8 = (UINT8*)Destination64;
+ Source8 = (CONST UINT8*)Source64;
+
+ while (Alignment-- != 0) {
+ *(--Destination8) = *(--Source8);
+ --Length;
+ }
+ Destination64 = (UINT64*)Destination8;
+ Source64 = (CONST UINT64*)Source8;
+ }
+
+ while (Length > 0) {
+ *(--Destination64) = *(--Source64);
+ Length -= 8;
+ }
+ }
+ } else if ((((UINTN)DestinationBuffer & 0x3) == 0) && (((UINTN)SourceBuffer & 0x3) == 0) && (Length >= 4)) {
+ if (SourceBuffer > DestinationBuffer) {
+ Destination32 = (UINT32*)DestinationBuffer;
+ Source32 = (CONST UINT32*)SourceBuffer;
+ while (Length >= 4) {
+ *(Destination32++) = *(Source32++);
+ Length -= 4;
+ }
+
+ // Finish if there are still some bytes to copy
+ Destination8 = (UINT8*)Destination32;
+ Source8 = (CONST UINT8*)Source32;
+ while (Length-- != 0) {
+ *(Destination8++) = *(Source8++);
+ }
+ } else if (SourceBuffer < DestinationBuffer) {
+ Destination32 = (UINT32*)((UINTN)DestinationBuffer + Length);
+ Source32 = (CONST UINT32*)((UINTN)SourceBuffer + Length);
+
+ // Destination32 and Source32 were aligned on a 32-bit boundary
+ // but if length is not a multiple of 4 bytes then they won't be
+ // anymore.
+
+ Alignment = Length & 0x3;
+ if (Alignment != 0) {
+ Destination8 = (UINT8*)Destination32;
+ Source8 = (CONST UINT8*)Source32;
+
+ while (Alignment-- != 0) {
+ *(--Destination8) = *(--Source8);
+ --Length;
+ }
+ Destination32 = (UINT32*)Destination8;
+ Source32 = (CONST UINT32*)Source8;
+ }
+
+ while (Length > 0) {
+ *(--Destination32) = *(--Source32);
+ Length -= 4;
+ }
+ }
+ } else {
+ if (SourceBuffer > DestinationBuffer) {
+ Destination8 = (UINT8*)DestinationBuffer;
+ Source8 = (CONST UINT8*)SourceBuffer;
+ while (Length-- != 0) {
+ *(Destination8++) = *(Source8++);
+ }
+ } else if (SourceBuffer < DestinationBuffer) {
+ Destination8 = (UINT8*)DestinationBuffer + (Length - 1);
+ Source8 = (CONST UINT8*)SourceBuffer + (Length - 1);
+ while (Length-- != 0) {
+ *(Destination8--) = *(Source8--);
+ }
+ }
+ }
+ return DestinationBuffer;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMemWrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMemWrapper.c
new file mode 100644
index 0000000..1ac5f33
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/CopyMemWrapper.c
@@ -0,0 +1,57 @@
+/** @file
+ CopyMem() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Copies a source buffer to a destination buffer, and returns the destination buffer.
+
+ This function copies Length bytes from SourceBuffer to DestinationBuffer, and returns
+ DestinationBuffer. The implementation must be reentrant, and it must handle the case
+ where SourceBuffer overlaps DestinationBuffer.
+
+ If Length is greater than (MAX_ADDRESS - DestinationBuffer + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - SourceBuffer + 1), then ASSERT().
+
+ @param DestinationBuffer A pointer to the destination buffer of the memory copy.
+ @param SourceBuffer A pointer to the source buffer of the memory copy.
+ @param Length The number of bytes to copy from SourceBuffer to DestinationBuffer.
+
+ @return DestinationBuffer.
+
+**/
+VOID *
+EFIAPI
+CopyMem (
+ OUT VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ )
+{
+ if (Length == 0) {
+ return DestinationBuffer;
+ }
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)DestinationBuffer));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)SourceBuffer));
+
+ if (DestinationBuffer == SourceBuffer) {
+ return DestinationBuffer;
+ }
+ return InternalMemCopyMem (DestinationBuffer, SourceBuffer, Length);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/IsZeroBufferWrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/IsZeroBufferWrapper.c
new file mode 100644
index 0000000..10be081
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/IsZeroBufferWrapper.c
@@ -0,0 +1,48 @@
+/** @file
+ Implementation of IsZeroBuffer function.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Checks if the contents of a buffer are all zeros.
+
+ This function checks whether the contents of a buffer are all zeros. If the
+ contents are all zeros, return TRUE. Otherwise, return FALSE.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the buffer to be checked.
+ @param Length The size of the buffer (in bytes) to be checked.
+
+ @retval TRUE Contents of the buffer are all zeros.
+ @retval FALSE Contents of the buffer are not all zeros.
+
+**/
+BOOLEAN
+EFIAPI
+IsZeroBuffer (
+ IN CONST VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ ASSERT (!(Buffer == NULL && Length > 0));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ return InternalMemIsZeroBuffer (Buffer, Length);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGeneric.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGeneric.c
new file mode 100644
index 0000000..6a261ae
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGeneric.c
@@ -0,0 +1,287 @@
+/** @file
+ Architecture Independent Base Memory Library Implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with a 16-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 16-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem16 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ )
+{
+ for (; Length != 0; Length--) {
+ ((UINT16*)Buffer)[Length - 1] = Value;
+ }
+ return Buffer;
+}
+
+/**
+ Fills a target buffer with a 32-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 32-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem32 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ )
+{
+ for (; Length != 0; Length--) {
+ ((UINT32*)Buffer)[Length - 1] = Value;
+ }
+ return Buffer;
+}
+
+/**
+ Fills a target buffer with a 64-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 64-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem64 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ )
+{
+ for (; Length != 0; Length--) {
+ ((UINT64*)Buffer)[Length - 1] = Value;
+ }
+ return Buffer;
+}
+
+/**
+ Set Buffer to 0 for Size bytes.
+
+ @param Buffer Memory to set.
+ @param Length The number of bytes to set.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemZeroMem (
+ OUT VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ return InternalMemSetMem (Buffer, Length, 0);
+}
+
+/**
+ Compares two memory buffers of a given length.
+
+ @param DestinationBuffer The first memory buffer.
+ @param SourceBuffer The second memory buffer.
+ @param Length Length of DestinationBuffer and SourceBuffer memory
+ regions to compare. Must be non-zero.
+
+ @return 0 All Length bytes of the two buffers are identical.
+ @retval Non-zero The first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+**/
+INTN
+EFIAPI
+InternalMemCompareMem (
+ IN CONST VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ )
+{
+ while ((--Length != 0) &&
+ (*(INT8*)DestinationBuffer == *(INT8*)SourceBuffer)) {
+ DestinationBuffer = (INT8*)DestinationBuffer + 1;
+ SourceBuffer = (INT8*)SourceBuffer + 1;
+ }
+ return (INTN)*(UINT8*)DestinationBuffer - (INTN)*(UINT8*)SourceBuffer;
+}
+
+/**
+ Scans a target buffer for an 8-bit value, and returns a pointer to the
+ matching 8-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 8-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem8 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ )
+{
+ CONST UINT8 *Pointer;
+
+ Pointer = (CONST UINT8*)Buffer;
+ do {
+ if (*Pointer == Value) {
+ return Pointer;
+ }
+ ++Pointer;
+ } while (--Length != 0);
+ return NULL;
+}
+
+/**
+ Scans a target buffer for a 16-bit value, and returns a pointer to the
+ matching 16-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 16-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem16 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ )
+{
+ CONST UINT16 *Pointer;
+
+ Pointer = (CONST UINT16*)Buffer;
+ do {
+ if (*Pointer == Value) {
+ return Pointer;
+ }
+ ++Pointer;
+ } while (--Length != 0);
+ return NULL;
+}
+
+/**
+ Scans a target buffer for a 32-bit value, and returns a pointer to the
+ matching 32-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 32-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem32 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ )
+{
+ CONST UINT32 *Pointer;
+
+ Pointer = (CONST UINT32*)Buffer;
+ do {
+ if (*Pointer == Value) {
+ return Pointer;
+ }
+ ++Pointer;
+ } while (--Length != 0);
+ return NULL;
+}
+
+/**
+ Scans a target buffer for a 64-bit value, and returns a pointer to the
+ matching 64-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 64-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem64 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ )
+{
+ CONST UINT64 *Pointer;
+
+ Pointer = (CONST UINT64*)Buffer;
+ do {
+ if (*Pointer == Value) {
+ return Pointer;
+ }
+ ++Pointer;
+ } while (--Length != 0);
+ return NULL;
+}
+
+/**
+ Checks whether the contents of a buffer are all zeros.
+
+ @param Buffer The pointer to the buffer to be checked.
+ @param Length The size of the buffer (in bytes) to be checked.
+
+ @retval TRUE Contents of the buffer are all zeros.
+ @retval FALSE Contents of the buffer are not all zeros.
+
+**/
+BOOLEAN
+EFIAPI
+InternalMemIsZeroBuffer (
+ IN CONST VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ CONST UINT8 *BufferData;
+ UINTN Index;
+
+ BufferData = Buffer;
+ for (Index = 0; Index < Length; Index++) {
+ if (BufferData[Index] != 0) {
+ return FALSE;
+ }
+ }
+ return TRUE;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGuid.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGuid.c
new file mode 100644
index 0000000..e2976dd
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibGuid.c
@@ -0,0 +1,165 @@
+/** @file
+ Implementation of GUID functions.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Copies a source GUID to a destination GUID.
+
+ This function copies the contents of the 128-bit GUID specified by SourceGuid to
+ DestinationGuid, and returns DestinationGuid.
+
+ If DestinationGuid is NULL, then ASSERT().
+ If SourceGuid is NULL, then ASSERT().
+
+ @param DestinationGuid A pointer to the destination GUID.
+ @param SourceGuid A pointer to the source GUID.
+
+ @return DestinationGuid.
+
+**/
+GUID *
+EFIAPI
+CopyGuid (
+ OUT GUID *DestinationGuid,
+ IN CONST GUID *SourceGuid
+ )
+{
+ WriteUnaligned64 (
+ (UINT64*)DestinationGuid,
+ ReadUnaligned64 ((CONST UINT64*)SourceGuid)
+ );
+ WriteUnaligned64 (
+ (UINT64*)DestinationGuid + 1,
+ ReadUnaligned64 ((CONST UINT64*)SourceGuid + 1)
+ );
+ return DestinationGuid;
+}
+
+/**
+ Compares two GUIDs.
+
+ This function compares Guid1 to Guid2. If the GUIDs are identical then TRUE is returned.
+ If there are any bit differences in the two GUIDs, then FALSE is returned.
+
+ If Guid1 is NULL, then ASSERT().
+ If Guid2 is NULL, then ASSERT().
+
+ @param Guid1 A pointer to a 128 bit GUID.
+ @param Guid2 A pointer to a 128 bit GUID.
+
+ @retval TRUE Guid1 and Guid2 are identical.
+ @retval FALSE Guid1 and Guid2 are not identical.
+
+**/
+BOOLEAN
+EFIAPI
+CompareGuid (
+ IN CONST GUID *Guid1,
+ IN CONST GUID *Guid2
+ )
+{
+ UINT64 LowPartOfGuid1;
+ UINT64 LowPartOfGuid2;
+ UINT64 HighPartOfGuid1;
+ UINT64 HighPartOfGuid2;
+
+ LowPartOfGuid1 = ReadUnaligned64 ((CONST UINT64*) Guid1);
+ LowPartOfGuid2 = ReadUnaligned64 ((CONST UINT64*) Guid2);
+ HighPartOfGuid1 = ReadUnaligned64 ((CONST UINT64*) Guid1 + 1);
+ HighPartOfGuid2 = ReadUnaligned64 ((CONST UINT64*) Guid2 + 1);
+
+ return (BOOLEAN) (LowPartOfGuid1 == LowPartOfGuid2 && HighPartOfGuid1 == HighPartOfGuid2);
+}
+
+/**
+ Scans a target buffer for a GUID, and returns a pointer to the matching GUID
+ in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from
+ the lowest address to the highest address at 128-bit increments for the 128-bit
+ GUID value that matches Guid. If a match is found, then a pointer to the matching
+ GUID in the target buffer is returned. If no match is found, then NULL is returned.
+ If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 128-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Guid The value to search for in the target buffer.
+
+ @return A pointer to the matching Guid in the target buffer or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanGuid (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN CONST GUID *Guid
+ )
+{
+ CONST GUID *GuidPtr;
+
+ ASSERT (((UINTN)Buffer & (sizeof (Guid->Data1) - 1)) == 0);
+ ASSERT (Length <= (MAX_ADDRESS - (UINTN)Buffer + 1));
+ ASSERT ((Length & (sizeof (*GuidPtr) - 1)) == 0);
+
+ GuidPtr = (GUID*)Buffer;
+ Buffer = GuidPtr + Length / sizeof (*GuidPtr);
+ while (GuidPtr < (CONST GUID*)Buffer) {
+ if (CompareGuid (GuidPtr, Guid)) {
+ return (VOID*)GuidPtr;
+ }
+ GuidPtr++;
+ }
+ return NULL;
+}
+
+/**
+ Checks if the given GUID is a zero GUID.
+
+ This function checks whether the given GUID is a zero GUID. If the GUID is
+ identical to a zero GUID then TRUE is returned. Otherwise, FALSE is returned.
+
+ If Guid is NULL, then ASSERT().
+
+ @param Guid The pointer to a 128 bit GUID.
+
+ @retval TRUE Guid is a zero GUID.
+ @retval FALSE Guid is not a zero GUID.
+
+**/
+BOOLEAN
+EFIAPI
+IsZeroGuid (
+ IN CONST GUID *Guid
+ )
+{
+ UINT64 LowPartOfGuid;
+ UINT64 HighPartOfGuid;
+
+ LowPartOfGuid = ReadUnaligned64 ((CONST UINT64*) Guid);
+ HighPartOfGuid = ReadUnaligned64 ((CONST UINT64*) Guid + 1);
+
+ return (BOOLEAN) (LowPartOfGuid == 0 && HighPartOfGuid == 0);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibInternals.h b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibInternals.h
new file mode 100644
index 0000000..9d3730a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/MemLibInternals.h
@@ -0,0 +1,245 @@
+/** @file
+ Declaration of internal functions for Base Memory Library.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+
+ Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __MEM_LIB_INTERNALS__
+#define __MEM_LIB_INTERNALS__
+
+#include <Base.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+
+/**
+ Copy Length bytes from Source to Destination.
+
+ @param DestinationBuffer Target of copy
+ @param SourceBuffer Place to copy from
+ @param Length The number of bytes to copy
+
+ @return Destination
+
+**/
+VOID *
+EFIAPI
+InternalMemCopyMem (
+ OUT VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ );
+
+/**
+ Set Buffer to Value for Size bytes.
+
+ @param Buffer The memory to set.
+ @param Length The number of bytes to set
+ @param Value The value of the set operation.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ );
+
+/**
+ Fills a target buffer with a 16-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 16-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem16 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ );
+
+/**
+ Fills a target buffer with a 32-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 32-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem32 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ );
+
+/**
+ Fills a target buffer with a 64-bit value, and returns the target buffer.
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The count of 64-bit value to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem64 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ );
+
+/**
+ Set Buffer to 0 for Size bytes.
+
+ @param Buffer The memory to set.
+ @param Length The number of bytes to set.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemZeroMem (
+ OUT VOID *Buffer,
+ IN UINTN Length
+ );
+
+/**
+ Compares two memory buffers of a given length.
+
+ @param DestinationBuffer The first memory buffer.
+ @param SourceBuffer The second memory buffer.
+ @param Length The length of DestinationBuffer and SourceBuffer memory
+ regions to compare. Must be non-zero.
+
+ @return 0 All Length bytes of the two buffers are identical.
+ @retval Non-zero The first mismatched byte in SourceBuffer subtracted from the first
+ mismatched byte in DestinationBuffer.
+
+**/
+INTN
+EFIAPI
+InternalMemCompareMem (
+ IN CONST VOID *DestinationBuffer,
+ IN CONST VOID *SourceBuffer,
+ IN UINTN Length
+ );
+
+/**
+ Scans a target buffer for an 8-bit value, and returns a pointer to the
+ matching 8-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 8-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem8 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ );
+
+/**
+ Scans a target buffer for a 16-bit value, and returns a pointer to the
+ matching 16-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 16-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem16 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ );
+
+/**
+ Scans a target buffer for a 32-bit value, and returns a pointer to the
+ matching 32-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 32-bit value to scan. Must be non-zero.
+ @param Value The value to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem32 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ );
+
+/**
+ Scans a target buffer for a 64-bit value, and returns a pointer to the
+ matching 64-bit value in the target buffer.
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The count of 64-bit value to scan. Must be non-zero.
+ @param Value The calue to search for in the target buffer.
+
+ @return The pointer to the first occurrence, or NULL if not found.
+
+**/
+CONST VOID *
+EFIAPI
+InternalMemScanMem64 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ );
+
+/**
+ Checks whether the contents of a buffer are all zeros.
+
+ @param Buffer The pointer to the buffer to be checked.
+ @param Length The size of the buffer (in bytes) to be checked.
+
+ @retval TRUE Contents of the buffer are all zeros.
+ @retval FALSE Contents of the buffer are not all zeros.
+
+**/
+BOOLEAN
+EFIAPI
+InternalMemIsZeroBuffer (
+ IN CONST VOID *Buffer,
+ IN UINTN Length
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem16Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem16Wrapper.c
new file mode 100644
index 0000000..8201313
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem16Wrapper.c
@@ -0,0 +1,61 @@
+/** @file
+ ScanMem16() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Scans a target buffer for a 16-bit value, and returns a pointer to the matching 16-bit value
+ in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 16-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanMem16 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ )
+{
+ if (Length == 0) {
+ return NULL;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN)Buffer & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return (VOID*)InternalMemScanMem16 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem32Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem32Wrapper.c
new file mode 100644
index 0000000..22c0c79
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem32Wrapper.c
@@ -0,0 +1,60 @@
+/** @file
+ ScanMem32() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Scans a target buffer for a 32-bit value, and returns a pointer to the matching 32-bit value
+ in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 32-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanMem32 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ )
+{
+ if (Length == 0) {
+ return NULL;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN)Buffer & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return (VOID*)InternalMemScanMem32 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem64Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem64Wrapper.c
new file mode 100644
index 0000000..a617d87
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem64Wrapper.c
@@ -0,0 +1,61 @@
+/** @file
+ ScanMem64() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Scans a target buffer for a 64-bit value, and returns a pointer to the matching 64-bit value
+ in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from the lowest
+ address to the highest address for a 64-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanMem64 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ )
+{
+ if (Length == 0) {
+ return NULL;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT (((UINTN)Buffer & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return (VOID*)InternalMemScanMem64 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem8Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem8Wrapper.c
new file mode 100644
index 0000000..fb2c5a4
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ScanMem8Wrapper.c
@@ -0,0 +1,93 @@
+/** @file
+ ScanMem8() and ScanMemN() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Scans a target buffer for an 8-bit value, and returns a pointer to the matching 8-bit value
+ in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from the lowest
+ address to the highest address for an 8-bit value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanMem8 (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ )
+{
+ if (Length == 0) {
+ return NULL;
+ }
+ ASSERT (Buffer != NULL);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+
+ return (VOID*)InternalMemScanMem8 (Buffer, Length, Value);
+}
+
+/**
+ Scans a target buffer for a UINTN sized value, and returns a pointer to the matching
+ UINTN sized value in the target buffer.
+
+ This function searches the target buffer specified by Buffer and Length from the lowest
+ address to the highest address for a UINTN sized value that matches Value. If a match is found,
+ then a pointer to the matching byte in the target buffer is returned. If no match is found,
+ then NULL is returned. If Length is 0, then NULL is returned.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Buffer is not aligned on a UINTN boundary, then ASSERT().
+ If Length is not aligned on a UINTN boundary, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to scan.
+ @param Length The number of bytes in Buffer to scan.
+ @param Value The value to search for in the target buffer.
+
+ @return A pointer to the matching byte in the target buffer, or NULL otherwise.
+
+**/
+VOID *
+EFIAPI
+ScanMemN (
+ IN CONST VOID *Buffer,
+ IN UINTN Length,
+ IN UINTN Value
+ )
+{
+ if (sizeof (UINTN) == sizeof (UINT64)) {
+ return ScanMem64 (Buffer, Length, (UINT64)Value);
+ } else {
+ return ScanMem32 (Buffer, Length, (UINT32)Value);
+ }
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem.c
new file mode 100644
index 0000000..d42abb1
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem.c
@@ -0,0 +1,81 @@
+/** @file
+ Implementation of the EfiSetMem routine. This function is broken
+ out into its own source file so that it can be excluded from a
+ build for a particular platform easily if an optimized version
+ is desired.
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ Copyright (c) 2012 - 2013, ARM Ltd. All rights reserved.<BR>
+ Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "MemLibInternals.h"
+
+/**
+ Set Buffer to Value for Size bytes.
+
+ @param Buffer The memory to set.
+ @param Length The number of bytes to set.
+ @param Value The value of the set operation.
+
+ @return Buffer
+
+**/
+VOID *
+EFIAPI
+InternalMemSetMem (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ )
+{
+ //
+ // Declare the local variables that actually move the data elements as
+ // volatile to prevent the optimizer from replacing this function with
+ // the intrinsic memset()
+ //
+ volatile UINT8 *Pointer8;
+ volatile UINT32 *Pointer32;
+ volatile UINT64 *Pointer64;
+ UINT32 Value32;
+ UINT64 Value64;
+
+ if ((((UINTN)Buffer & 0x7) == 0) && (Length >= 8)) {
+ // Generate the 64bit value
+ Value32 = (Value << 24) | (Value << 16) | (Value << 8) | Value;
+ Value64 = LShiftU64 (Value32, 32) | Value32;
+
+ Pointer64 = (UINT64*)Buffer;
+ while (Length >= 8) {
+ *(Pointer64++) = Value64;
+ Length -= 8;
+ }
+
+ // Finish with bytes if needed
+ Pointer8 = (UINT8*)Pointer64;
+ } else if ((((UINTN)Buffer & 0x3) == 0) && (Length >= 4)) {
+ // Generate the 32bit value
+ Value32 = (Value << 24) | (Value << 16) | (Value << 8) | Value;
+
+ Pointer32 = (UINT32*)Buffer;
+ while (Length >= 4) {
+ *(Pointer32++) = Value32;
+ Length -= 4;
+ }
+
+ // Finish with bytes if needed
+ Pointer8 = (UINT8*)Pointer32;
+ } else {
+ Pointer8 = (UINT8*)Buffer;
+ }
+ while (Length-- > 0) {
+ *(Pointer8++) = Value;
+ }
+ return Buffer;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem16Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem16Wrapper.c
new file mode 100644
index 0000000..9ac4641
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem16Wrapper.c
@@ -0,0 +1,58 @@
+/** @file
+ SetMem16() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with a 16-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 16-bit value specified by
+ Value, and returns Buffer. Value is repeated every 16-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If Length is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem16 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT16 Value
+ )
+{
+ if (Length == 0) {
+ return Buffer;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((((UINTN)Buffer) & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return InternalMemSetMem16 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem32Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem32Wrapper.c
new file mode 100644
index 0000000..e504deb
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem32Wrapper.c
@@ -0,0 +1,58 @@
+/** @file
+ SetMem32() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with a 32-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 32-bit value specified by
+ Value, and returns Buffer. Value is repeated every 32-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem32 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT32 Value
+ )
+{
+ if (Length == 0) {
+ return Buffer;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((((UINTN)Buffer) & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return InternalMemSetMem32 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem64Wrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem64Wrapper.c
new file mode 100644
index 0000000..fbb3762
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMem64Wrapper.c
@@ -0,0 +1,58 @@
+/** @file
+ SetMem64() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with a 64-bit value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the 64-bit value specified by
+ Value, and returns Buffer. Value is repeated every 64-bits in for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a 64-bit boundary, then ASSERT().
+ If Length is not aligned on a 64-bit boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem64 (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT64 Value
+ )
+{
+ if (Length == 0) {
+ return Buffer;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+ ASSERT ((((UINTN)Buffer) & (sizeof (Value) - 1)) == 0);
+ ASSERT ((Length & (sizeof (Value) - 1)) == 0);
+
+ return InternalMemSetMem64 (Buffer, Length / sizeof (Value), Value);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMemWrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMemWrapper.c
new file mode 100644
index 0000000..39ec8cb
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/SetMemWrapper.c
@@ -0,0 +1,85 @@
+/** @file
+ SetMem() and SetMemN() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with a byte value, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with Value, and returns Buffer.
+
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The memory to set.
+ @param Length The number of bytes to set.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMem (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
+ )
+{
+ if (Length == 0) {
+ return Buffer;
+ }
+
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN)Buffer));
+
+ return InternalMemSetMem (Buffer, Length, Value);
+}
+
+/**
+ Fills a target buffer with a value that is size UINTN, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the UINTN sized value specified by
+ Value, and returns Buffer. Value is repeated every sizeof(UINTN) bytes for Length
+ bytes of Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+ If Buffer is not aligned on a UINTN boundary, then ASSERT().
+ If Length is not aligned on a UINTN boundary, then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill.
+ @param Length The number of bytes in Buffer to fill.
+ @param Value The value with which to fill Length bytes of Buffer.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+SetMemN (
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINTN Value
+ )
+{
+ if (sizeof (UINTN) == sizeof (UINT64)) {
+ return SetMem64 (Buffer, Length, (UINT64)Value);
+ } else {
+ return SetMem32 (Buffer, Length, (UINT32)Value);
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ZeroMemWrapper.c b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ZeroMemWrapper.c
new file mode 100644
index 0000000..5964118
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BaseMemoryLib/ZeroMemWrapper.c
@@ -0,0 +1,50 @@
+/** @file
+ ZeroMem() implementation.
+
+ The following BaseMemoryLib instances contain the same copy of this file:
+
+ BaseMemoryLib
+ BaseMemoryLibMmx
+ BaseMemoryLibSse2
+ BaseMemoryLibRepStr
+ BaseMemoryLibOptDxe
+ BaseMemoryLibOptPei
+ PeiMemoryLib
+ UefiMemoryLib
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "MemLibInternals.h"
+
+/**
+ Fills a target buffer with zeros, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with zeros, and returns Buffer.
+
+ If Length > 0 and Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to fill with zeros.
+ @param Length The number of bytes in Buffer to fill with zeros.
+
+ @return Buffer.
+
+**/
+VOID *
+EFIAPI
+ZeroMem (
+ OUT VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ if (Length == 0) {
+ return Buffer;
+ }
+
+ ASSERT (Buffer != NULL);
+ ASSERT (Length <= (MAX_ADDRESS - (UINTN)Buffer + 1));
+ return InternalMemZeroMem (Buffer, Length);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLib.c b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLib.c
new file mode 100644
index 0000000..8bfbab0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLib.c
@@ -0,0 +1,837 @@
+/** @file
+ Base Print Library instance implementation.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ Portions copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "PrintLibInternal.h"
+
+//
+// Declare a VA_LIST global variable that is used in calls to BasePrintLibSPrintMarker()
+// when the BASE_LIST parameter is valid and the VA_LIST parameter is ignored.
+// A NULL VA_LIST can not be passed into BasePrintLibSPrintMarker() because some
+// compilers define VA_LIST to be a structure.
+//
+VA_LIST gNullVaList;
+
+#define ASSERT_UNICODE_BUFFER(Buffer) ASSERT ((((UINTN) (Buffer)) & 0x01) == 0)
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on
+ a Null-terminated Unicode format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeVSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (StartOfBuffer);
+ ASSERT_UNICODE_BUFFER (FormatString);
+ return BasePrintLibSPrintMarker ((CHAR8 *)StartOfBuffer, BufferSize >> 1, FORMAT_UNICODE | OUTPUT_UNICODE, (CHAR8 *)FormatString, Marker, NULL);
+}
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on
+ a Null-terminated Unicode format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeBSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN BASE_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (StartOfBuffer);
+ ASSERT_UNICODE_BUFFER (FormatString);
+ return BasePrintLibSPrintMarker ((CHAR8 *)StartOfBuffer, BufferSize >> 1, FORMAT_UNICODE | OUTPUT_UNICODE, (CHAR8 *)FormatString, gNullVaList, Marker);
+}
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ Unicode format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then the output buffer is unmodified and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeSPrint (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN NumberOfPrinted;
+
+ VA_START (Marker, FormatString);
+ NumberOfPrinted = UnicodeVSPrint (StartOfBuffer, BufferSize, FormatString, Marker);
+ VA_END (Marker);
+ return NumberOfPrinted;
+}
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeVSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (StartOfBuffer);
+ return BasePrintLibSPrintMarker ((CHAR8 *)StartOfBuffer, BufferSize >> 1, OUTPUT_UNICODE, FormatString, Marker, NULL);
+}
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on the
+ contents of the format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeBSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN BASE_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (StartOfBuffer);
+ return BasePrintLibSPrintMarker ((CHAR8 *)StartOfBuffer, BufferSize >> 1, OUTPUT_UNICODE, FormatString, gNullVaList, Marker);
+}
+
+/**
+ Produces a Null-terminated Unicode string in an output buffer based on a Null-terminated
+ ASCII format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated Unicode string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The Unicode string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of Unicode characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If StartOfBuffer is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 1 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and BufferSize >
+ (PcdMaximumUnicodeStringLength * sizeof (CHAR16) + 1), then ASSERT(). Also, the output
+ buffer is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0 or 1, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ Unicode string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of Unicode characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+UnicodeSPrintAsciiFormat (
+ OUT CHAR16 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN NumberOfPrinted;
+
+ VA_START (Marker, FormatString);
+ NumberOfPrinted = UnicodeVSPrintAsciiFormat (StartOfBuffer, BufferSize, FormatString, Marker);
+ VA_END (Marker);
+ return NumberOfPrinted;
+}
+
+
+/**
+ Converts a decimal value to a Null-terminated Unicode string.
+
+ Converts the decimal number specified by Value to a Null-terminated Unicode
+ string specified by Buffer containing at most Width characters. No padding of
+ spaces is ever performed. If Width is 0 then a width of
+ MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more than
+ Width characters, then only the first Width characters are placed in Buffer.
+ Additional conversion parameters are specified in Flags.
+
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If RADIX_HEX is set in Flags, then the output buffer will be formatted in
+ hexadecimal format.
+ If Value is < 0 and RADIX_HEX is not set in Flags, then the fist character in
+ Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored, then
+ Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If Buffer is not aligned on a 16-bit boundary, then ASSERT().
+ If an error would be returned, then the function will also ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated Unicode string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of Unicode characters to place in
+ Buffer, not including the Null-terminator.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If PcdMaximumUnicodeStringLength is not
+ zero, and BufferSize is greater than
+ (PcdMaximumUnicodeStringLength *
+ sizeof (CHAR16) + 1).
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+EFIAPI
+UnicodeValueToStringS (
+ IN OUT CHAR16 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width
+ )
+{
+ ASSERT_UNICODE_BUFFER(Buffer);
+ return BasePrintLibConvertValueToStringS ((CHAR8 *)Buffer, BufferSize, Flags, Value, Width, 2);
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiVSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ return BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, 0, FormatString, Marker, NULL);
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiBSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ IN BASE_LIST Marker
+ )
+{
+ return BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, 0, FormatString, gNullVaList, Marker);
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ ASCII format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more than
+ PcdMaximumAsciiStringLength Ascii characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR8 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN NumberOfPrinted;
+
+ VA_START (Marker, FormatString);
+ NumberOfPrinted = AsciiVSPrint (StartOfBuffer, BufferSize, FormatString, Marker);
+ VA_END (Marker);
+ return NumberOfPrinted;
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and a VA_LIST argument list.
+
+ This function is similar as vsnprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiVSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (FormatString);
+ return BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, FORMAT_UNICODE, (CHAR8 *)FormatString, Marker, NULL);
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and a BASE_LIST argument list.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list specified by Marker based on
+ the contents of the format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param Marker BASE_LIST marker for the variable argument list.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiBSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ IN BASE_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (FormatString);
+ return BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, FORMAT_UNICODE, (CHAR8 *)FormatString, gNullVaList, Marker);
+}
+
+/**
+ Produces a Null-terminated ASCII string in an output buffer based on a Null-terminated
+ Unicode format string and variable argument list.
+
+ This function is similar as snprintf_s defined in C11.
+
+ Produces a Null-terminated ASCII string in the output buffer specified by StartOfBuffer
+ and BufferSize.
+ The ASCII string is produced by parsing the format string specified by FormatString.
+ Arguments are pulled from the variable argument list based on the contents of the
+ format string.
+ The number of ASCII characters in the produced output buffer is returned not including
+ the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If BufferSize > 0 and StartOfBuffer is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If BufferSize > 0 and FormatString is NULL, then ASSERT(). Also, the output buffer is
+ unmodified and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and BufferSize >
+ (PcdMaximumAsciiStringLength * sizeof (CHAR8)), then ASSERT(). Also, the output buffer
+ is unmodified and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more than
+ PcdMaximumUnicodeStringLength Unicode characters not including the Null-terminator, then
+ ASSERT(). Also, the output buffer is unmodified and 0 is returned.
+
+ If BufferSize is 0, then no output buffer is produced and 0 is returned.
+
+ @param StartOfBuffer A pointer to the output buffer for the produced Null-terminated
+ ASCII string.
+ @param BufferSize The size, in bytes, of the output buffer specified by StartOfBuffer.
+ @param FormatString A Null-terminated Unicode format string.
+ @param ... Variable argument list whose contents are accessed based on the
+ format string specified by FormatString.
+
+ @return The number of ASCII characters in the produced output buffer not including the
+ Null-terminator.
+
+**/
+UINTN
+EFIAPI
+AsciiSPrintUnicodeFormat (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN CONST CHAR16 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN NumberOfPrinted;
+
+ VA_START (Marker, FormatString);
+ NumberOfPrinted = AsciiVSPrintUnicodeFormat (StartOfBuffer, BufferSize, FormatString, Marker);
+ VA_END (Marker);
+ return NumberOfPrinted;
+}
+
+/**
+ Converts a decimal value to a Null-terminated Ascii string.
+
+ Converts the decimal number specified by Value to a Null-terminated Ascii
+ string specified by Buffer containing at most Width characters. No padding of
+ spaces is ever performed. If Width is 0 then a width of
+ MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more than
+ Width characters, then only the first Width characters are placed in Buffer.
+ Additional conversion parameters are specified in Flags.
+
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If RADIX_HEX is set in Flags, then the output buffer will be formatted in
+ hexadecimal format.
+ If Value is < 0 and RADIX_HEX is not set in Flags, then the fist character in
+ Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored, then
+ Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If an error would be returned, then the function will ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated Ascii string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of Ascii characters to place in
+ Buffer, not including the Null-terminator.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If PcdMaximumAsciiStringLength is not
+ zero, and BufferSize is greater than
+ PcdMaximumAsciiStringLength.
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+EFIAPI
+AsciiValueToStringS (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width
+ )
+{
+ return BasePrintLibConvertValueToStringS (Buffer, BufferSize, Flags, Value, Width, 1);
+}
+
+/**
+ Returns the number of characters that would be produced by if the formatted
+ output were produced not including the Null-terminator.
+
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ If FormatString is NULL, then ASSERT() and 0 is returned.
+ If PcdMaximumUnicodeStringLength is not zero, and FormatString contains more
+ than PcdMaximumUnicodeStringLength Unicode characters not including the
+ Null-terminator, then ASSERT() and 0 is returned.
+
+ @param[in] FormatString A Null-terminated Unicode format string.
+ @param[in] Marker VA_LIST marker for the variable argument list.
+
+ @return The number of characters that would be produced, not including the
+ Null-terminator.
+**/
+UINTN
+EFIAPI
+SPrintLength (
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ ASSERT_UNICODE_BUFFER (FormatString);
+ return BasePrintLibSPrintMarker (NULL, 0, FORMAT_UNICODE | OUTPUT_UNICODE | COUNT_ONLY_NO_PRINT, (CHAR8 *)FormatString, Marker, NULL);
+}
+
+/**
+ Returns the number of characters that would be produced by if the formatted
+ output were produced not including the Null-terminator.
+
+ If FormatString is NULL, then ASSERT() and 0 is returned.
+ If PcdMaximumAsciiStringLength is not zero, and FormatString contains more
+ than PcdMaximumAsciiStringLength Ascii characters not including the
+ Null-terminator, then ASSERT() and 0 is returned.
+
+ @param[in] FormatString A Null-terminated ASCII format string.
+ @param[in] Marker VA_LIST marker for the variable argument list.
+
+ @return The number of characters that would be produced, not including the
+ Null-terminator.
+**/
+UINTN
+EFIAPI
+SPrintLengthAsciiFormat (
+ IN CONST CHAR8 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ return BasePrintLibSPrintMarker (NULL, 0, OUTPUT_UNICODE | COUNT_ONLY_NO_PRINT, (CHAR8 *)FormatString, Marker, NULL);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.c b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.c
new file mode 100644
index 0000000..cdcd42d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.c
@@ -0,0 +1,1274 @@
+/** @file
+ Print Library internal worker functions.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "PrintLibInternal.h"
+#include "Library/BaseLib.h"
+#include "Efi_Defs.h"
+
+#define WARNING_STATUS_NUMBER 5
+#define ERROR_STATUS_NUMBER 33
+
+//
+// Safe print checks
+//
+#define RSIZE_MAX (PcdGet32 (PcdMaximumUnicodeStringLength))
+#define ASCII_RSIZE_MAX (PcdGet32 (PcdMaximumAsciiStringLength))
+
+#define SAFE_PRINT_CONSTRAINT_CHECK(Expression, RetVal) \
+ do { \
+ ASSERT (Expression); \
+ if (!(Expression)) { \
+ return RetVal; \
+ } \
+ } while (FALSE)
+
+GLOBAL_REMOVE_IF_UNREFERENCED CONST CHAR8 mHexStr[] = {'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
+
+//
+// Longest string: RETURN_WARN_BUFFER_TOO_SMALL => 24 characters plus NUL byte
+//
+GLOBAL_REMOVE_IF_UNREFERENCED CONST CHAR8 mWarningString[][24+1] = {
+ "Success", // RETURN_SUCCESS = 0
+ "Warning Unknown Glyph", // RETURN_WARN_UNKNOWN_GLYPH = 1
+ "Warning Delete Failure", // RETURN_WARN_DELETE_FAILURE = 2
+ "Warning Write Failure", // RETURN_WARN_WRITE_FAILURE = 3
+ "Warning Buffer Too Small", // RETURN_WARN_BUFFER_TOO_SMALL = 4
+ "Warning Stale Data", // RETURN_WARN_STALE_DATA = 5
+};
+
+//
+// Longest string: RETURN_INCOMPATIBLE_VERSION => 20 characters plus NUL byte
+//
+GLOBAL_REMOVE_IF_UNREFERENCED CONST CHAR8 mErrorString[][20+1] = {
+ "Load Error", // RETURN_LOAD_ERROR = 1 | MAX_BIT
+ "Invalid Parameter", // RETURN_INVALID_PARAMETER = 2 | MAX_BIT
+ "Unsupported", // RETURN_UNSUPPORTED = 3 | MAX_BIT
+ "Bad Buffer Size", // RETURN_BAD_BUFFER_SIZE = 4 | MAX_BIT
+ "Buffer Too Small", // RETURN_BUFFER_TOO_SMALL, = 5 | MAX_BIT
+ "Not Ready", // RETURN_NOT_READY = 6 | MAX_BIT
+ "Device Error", // RETURN_DEVICE_ERROR = 7 | MAX_BIT
+ "Write Protected", // RETURN_WRITE_PROTECTED = 8 | MAX_BIT
+ "Out of Resources", // RETURN_OUT_OF_RESOURCES = 9 | MAX_BIT
+ "Volume Corrupt", // RETURN_VOLUME_CORRUPTED = 10 | MAX_BIT
+ "Volume Full", // RETURN_VOLUME_FULL = 11 | MAX_BIT
+ "No Media", // RETURN_NO_MEDIA = 12 | MAX_BIT
+ "Media changed", // RETURN_MEDIA_CHANGED = 13 | MAX_BIT
+ "Not Found", // RETURN_NOT_FOUND = 14 | MAX_BIT
+ "Access Denied", // RETURN_ACCESS_DENIED = 15 | MAX_BIT
+ "No Response", // RETURN_NO_RESPONSE = 16 | MAX_BIT
+ "No mapping", // RETURN_NO_MAPPING = 17 | MAX_BIT
+ "Time out", // RETURN_TIMEOUT = 18 | MAX_BIT
+ "Not started", // RETURN_NOT_STARTED = 19 | MAX_BIT
+ "Already started", // RETURN_ALREADY_STARTED = 20 | MAX_BIT
+ "Aborted", // RETURN_ABORTED = 21 | MAX_BIT
+ "ICMP Error", // RETURN_ICMP_ERROR = 22 | MAX_BIT
+ "TFTP Error", // RETURN_TFTP_ERROR = 23 | MAX_BIT
+ "Protocol Error", // RETURN_PROTOCOL_ERROR = 24 | MAX_BIT
+ "Incompatible Version", // RETURN_INCOMPATIBLE_VERSION = 25 | MAX_BIT
+ "Security Violation", // RETURN_SECURITY_VIOLATION = 26 | MAX_BIT
+ "CRC Error", // RETURN_CRC_ERROR = 27 | MAX_BIT
+ "End of Media", // RETURN_END_OF_MEDIA = 28 | MAX_BIT
+ "Reserved (29)", // RESERVED = 29 | MAX_BIT
+ "Reserved (30)", // RESERVED = 30 | MAX_BIT
+ "End of File", // RETURN_END_OF_FILE = 31 | MAX_BIT
+ "Invalid Language", // RETURN_INVALID_LANGUAGE = 32 | MAX_BIT
+ "Compromised Data" // RETURN_COMPROMISED_DATA = 33 | MAX_BIT
+};
+
+
+/**
+ Internal function that places the character into the Buffer.
+
+ Internal function that places ASCII or Unicode character into the Buffer.
+
+ @param Buffer The buffer to place the Unicode or ASCII string.
+ @param EndBuffer The end of the input Buffer. No characters will be
+ placed after that.
+ @param Length The count of character to be placed into Buffer.
+ (Negative value indicates no buffer fill.)
+ @param Character The character to be placed into Buffer.
+ @param Increment The character increment in Buffer.
+
+ @return Buffer.
+
+**/
+CHAR8 *
+BasePrintLibFillBuffer (
+ OUT CHAR8 *Buffer,
+ IN CHAR8 *EndBuffer,
+ IN INTN Length,
+ IN UINTN Character,
+ IN INTN Increment
+ )
+{
+ INTN Index;
+
+ for (Index = 0; Index < Length && Buffer < EndBuffer; Index++) {
+ *Buffer = (CHAR8) Character;
+ if (Increment != 1) {
+ *(Buffer + 1) = (CHAR8)(Character >> 8);
+ }
+ Buffer += Increment;
+ }
+
+ return Buffer;
+}
+
+/**
+ Internal function that convert a number to a string in Buffer.
+
+ Print worker function that converts a decimal or hexadecimal number to an ASCII string in Buffer.
+
+ @param Buffer Location to place the ASCII string of Value.
+ @param Value The value to convert to a Decimal or Hexadecimal string in Buffer.
+ @param Radix Radix of the value
+
+ @return A pointer to the end of buffer filled with ASCII string.
+
+**/
+CHAR8 *
+BasePrintLibValueToString (
+ IN OUT CHAR8 *Buffer,
+ IN INT64 Value,
+ IN UINTN Radix
+ )
+{
+ UINT32 Remainder;
+
+ //
+ // Loop to convert one digit at a time in reverse order
+ //
+ *Buffer = 0;
+ do {
+ Value = (INT64)DivU64x32Remainder ((UINT64)Value, (UINT32)Radix, &Remainder);
+ *(++Buffer) = mHexStr[Remainder];
+ } while (Value != 0);
+
+ //
+ // Return pointer of the end of filled buffer.
+ //
+ return Buffer;
+}
+
+/**
+ Internal function that converts a decimal value to a Null-terminated string.
+
+ Converts the decimal number specified by Value to a Null-terminated
+ string specified by Buffer containing at most Width characters.
+ If Width is 0 then a width of MAXIMUM_VALUE_CHARACTERS is assumed.
+ The total number of characters placed in Buffer is returned.
+ If the conversion contains more than Width characters, then only the first
+ Width characters are returned, and the total number of characters
+ required to perform the conversion is returned.
+ Additional conversion parameters are specified in Flags.
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and commas
+ are inserted every 3rd digit starting from the right.
+ If Value is < 0, then the fist character in Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored,
+ then Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the Null-terminator
+ add up to Width characters.
+
+ If Buffer is NULL, then ASSERT().
+ If unsupported bits are set in Flags, then ASSERT().
+ If Width >= MAXIMUM_VALUE_CHARACTERS, then ASSERT()
+
+ @param Buffer The pointer to the output buffer for the produced Null-terminated
+ string.
+ @param Flags The bitmask of flags that specify left justification, zero pad,
+ and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of characters to place in Buffer, not including
+ the Null-terminator.
+ @param Increment The character increment in Buffer.
+
+ @return Total number of characters required to perform the conversion.
+
+**/
+UINTN
+BasePrintLibConvertValueToString (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width,
+ IN UINTN Increment
+ )
+{
+ CHAR8 *OriginalBuffer;
+ CHAR8 *EndBuffer;
+ CHAR8 ValueBuffer[MAXIMUM_VALUE_CHARACTERS];
+ CHAR8 *ValueBufferPtr;
+ UINTN Count;
+ UINTN Digits;
+ UINTN Index;
+ UINTN Radix;
+
+ //
+ // Make sure Buffer is not NULL and Width < MAXIMUM
+ //
+ ASSERT (Buffer != NULL);
+ ASSERT (Width < MAXIMUM_VALUE_CHARACTERS);
+ //
+ // Make sure Flags can only contain supported bits.
+ //
+ ASSERT ((Flags & ~(LEFT_JUSTIFY | COMMA_TYPE | PREFIX_ZERO | RADIX_HEX)) == 0);
+
+ //
+ // If both COMMA_TYPE and RADIX_HEX are set, then ASSERT ()
+ //
+ ASSERT (((Flags & COMMA_TYPE) == 0) || ((Flags & RADIX_HEX) == 0));
+
+ OriginalBuffer = Buffer;
+
+ //
+ // Width is 0 or COMMA_TYPE is set, PREFIX_ZERO is ignored.
+ //
+ if (Width == 0 || (Flags & COMMA_TYPE) != 0) {
+ Flags &= ~((UINTN) PREFIX_ZERO);
+ }
+ //
+ // If Width is 0 then a width of MAXIMUM_VALUE_CHARACTERS is assumed.
+ //
+ if (Width == 0) {
+ Width = MAXIMUM_VALUE_CHARACTERS - 1;
+ }
+ //
+ // Set the tag for the end of the input Buffer.
+ //
+ EndBuffer = Buffer + Width * Increment;
+
+ //
+ // Convert decimal negative
+ //
+ if ((Value < 0) && ((Flags & RADIX_HEX) == 0)) {
+ Value = -Value;
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, '-', Increment);
+ Width--;
+ }
+
+ //
+ // Count the length of the value string.
+ //
+ Radix = ((Flags & RADIX_HEX) == 0)? 10 : 16;
+ ValueBufferPtr = BasePrintLibValueToString (ValueBuffer, Value, Radix);
+ Count = ValueBufferPtr - ValueBuffer;
+
+ //
+ // Append Zero
+ //
+ if ((Flags & PREFIX_ZERO) != 0) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Count, '0', Increment);
+ }
+
+ //
+ // Print Comma type for every 3 characters
+ //
+ Digits = Count % 3;
+ if (Digits != 0) {
+ Digits = 3 - Digits;
+ }
+ for (Index = 0; Index < Count; Index++) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, *ValueBufferPtr--, Increment);
+ if ((Flags & COMMA_TYPE) != 0) {
+ Digits++;
+ if (Digits == 3) {
+ Digits = 0;
+ if ((Index + 1) < Count) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ',', Increment);
+ }
+ }
+ }
+ }
+
+ //
+ // Print Null-terminator
+ //
+ BasePrintLibFillBuffer (Buffer, EndBuffer + Increment, 1, 0, Increment);
+
+ return ((Buffer - OriginalBuffer) / Increment);
+}
+
+/**
+ Internal function that converts a decimal value to a Null-terminated string.
+
+ Converts the decimal number specified by Value to a Null-terminated string
+ specified by Buffer containing at most Width characters. If Width is 0 then a
+ width of MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more
+ than Width characters, then only the first Width characters are placed in
+ Buffer. Additional conversion parameters are specified in Flags.
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If Value is < 0, then the fist character in Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored,
+ then Buffer is padded with '0' characters so the combination of the optional
+ '-' sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If an error would be returned, the function will ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of characters to place in Buffer,
+ not including the Null-terminator.
+ @param Increment The character increment in Buffer.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If Increment is 1 and
+ PcdMaximumAsciiStringLength is not zero,
+ BufferSize is greater than
+ PcdMaximumAsciiStringLength.
+ If Increment is not 1 and
+ PcdMaximumUnicodeStringLength is not zero,
+ BufferSize is greater than
+ (PcdMaximumUnicodeStringLength *
+ sizeof (CHAR16) + 1).
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+BasePrintLibConvertValueToStringS (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width,
+ IN UINTN Increment
+ )
+{
+ CHAR8 *EndBuffer;
+ CHAR8 ValueBuffer[MAXIMUM_VALUE_CHARACTERS];
+ CHAR8 *ValueBufferPtr;
+ UINTN Count;
+ UINTN Digits;
+ UINTN Index;
+ UINTN Radix;
+
+ //
+ // 1. Buffer shall not be a null pointer.
+ //
+ SAFE_PRINT_CONSTRAINT_CHECK ((Buffer != NULL), RETURN_INVALID_PARAMETER);
+
+ //
+ // 2. BufferSize shall not be greater than (RSIZE_MAX * sizeof (CHAR16)) for
+ // Unicode output string or shall not be greater than ASCII_RSIZE_MAX for
+ // Ascii output string.
+ //
+ if (Increment == 1) {
+ //
+ // Ascii output string
+ //
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((BufferSize <= ASCII_RSIZE_MAX), RETURN_INVALID_PARAMETER);
+ }
+ } else {
+ //
+ // Unicode output string
+ //
+ if (RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((BufferSize <= RSIZE_MAX * sizeof (CHAR16) + 1), RETURN_INVALID_PARAMETER);
+ }
+ }
+
+ //
+ // 3. Flags shall be set properly.
+ //
+ SAFE_PRINT_CONSTRAINT_CHECK (((Flags & ~(LEFT_JUSTIFY | COMMA_TYPE | PREFIX_ZERO | RADIX_HEX)) == 0), RETURN_INVALID_PARAMETER);
+ SAFE_PRINT_CONSTRAINT_CHECK ((((Flags & COMMA_TYPE) == 0) || ((Flags & RADIX_HEX) == 0)), RETURN_INVALID_PARAMETER);
+
+ //
+ // 4. Width shall be smaller than MAXIMUM_VALUE_CHARACTERS.
+ //
+ SAFE_PRINT_CONSTRAINT_CHECK ((Width < MAXIMUM_VALUE_CHARACTERS), RETURN_INVALID_PARAMETER);
+
+ //
+ // Width is 0 or COMMA_TYPE is set, PREFIX_ZERO is ignored.
+ //
+ if (Width == 0 || (Flags & COMMA_TYPE) != 0) {
+ Flags &= ~((UINTN) PREFIX_ZERO);
+ }
+ //
+ // If Width is 0 then a width of MAXIMUM_VALUE_CHARACTERS is assumed.
+ //
+ if (Width == 0) {
+ Width = MAXIMUM_VALUE_CHARACTERS - 1;
+ }
+
+ //
+ // Count the characters of the output string.
+ //
+ Count = 0;
+ Radix = ((Flags & RADIX_HEX) == 0)? 10 : 16;
+
+ if ((Flags & PREFIX_ZERO) != 0) {
+ Count = Width;
+ } else {
+ if ((Value < 0) && ((Flags & RADIX_HEX) == 0)) {
+ Count++; // minus sign
+ ValueBufferPtr = BasePrintLibValueToString (ValueBuffer, -Value, Radix);
+ } else {
+ ValueBufferPtr = BasePrintLibValueToString (ValueBuffer, Value, Radix);
+ }
+ Digits = ValueBufferPtr - ValueBuffer;
+ Count += Digits;
+
+ if ((Flags & COMMA_TYPE) != 0) {
+ Count += (Digits - 1) / 3; // commas
+ }
+ }
+
+ Width = MIN (Count, Width);
+
+ //
+ // 5. BufferSize shall be large enough to hold the converted string.
+ //
+ SAFE_PRINT_CONSTRAINT_CHECK ((BufferSize >= (Width + 1) * Increment), RETURN_BUFFER_TOO_SMALL);
+
+ //
+ // Set the tag for the end of the input Buffer.
+ //
+ EndBuffer = Buffer + Width * Increment;
+
+ //
+ // Convert decimal negative
+ //
+ if ((Value < 0) && ((Flags & RADIX_HEX) == 0)) {
+ Value = -Value;
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, '-', Increment);
+ Width--;
+ }
+
+ //
+ // Count the length of the value string.
+ //
+ ValueBufferPtr = BasePrintLibValueToString (ValueBuffer, Value, Radix);
+ Count = ValueBufferPtr - ValueBuffer;
+
+ //
+ // Append Zero
+ //
+ if ((Flags & PREFIX_ZERO) != 0) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Count, '0', Increment);
+ }
+
+ //
+ // Print Comma type for every 3 characters
+ //
+ Digits = Count % 3;
+ if (Digits != 0) {
+ Digits = 3 - Digits;
+ }
+ for (Index = 0; Index < Count; Index++) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, *ValueBufferPtr--, Increment);
+ if ((Flags & COMMA_TYPE) != 0) {
+ Digits++;
+ if (Digits == 3) {
+ Digits = 0;
+ if ((Index + 1) < Count) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ',', Increment);
+ }
+ }
+ }
+ }
+
+ //
+ // Print Null-terminator
+ //
+ BasePrintLibFillBuffer (Buffer, EndBuffer + Increment, 1, 0, Increment);
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Worker function that produces a Null-terminated string in an output buffer
+ based on a Null-terminated format string and a VA_LIST argument list.
+
+ VSPrint function to process format and place the results in Buffer. Since a
+ VA_LIST is used this routine allows the nesting of Vararg routines. Thus
+ this is the main print working routine.
+
+ If COUNT_ONLY_NO_PRINT is set in Flags, Buffer will not be modified at all.
+
+ @param[out] Buffer The character buffer to print the results of the
+ parsing of Format into.
+ @param[in] BufferSize The maximum number of characters to put into
+ buffer.
+ @param[in] Flags Initial flags value.
+ Can only have FORMAT_UNICODE, OUTPUT_UNICODE,
+ and COUNT_ONLY_NO_PRINT set.
+ @param[in] Format A Null-terminated format string.
+ @param[in] VaListMarker VA_LIST style variable argument list consumed by
+ processing Format.
+ @param[in] BaseListMarker BASE_LIST style variable argument list consumed
+ by processing Format.
+
+ @return The number of characters printed not including the Null-terminator.
+ If COUNT_ONLY_NO_PRINT was set returns the same, but without any
+ modification to Buffer.
+
+**/
+UINTN
+BasePrintLibSPrintMarker (
+ OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN CONST CHAR8 *Format,
+ IN VA_LIST VaListMarker, OPTIONAL
+ IN BASE_LIST BaseListMarker OPTIONAL
+ )
+{
+ CHAR8 *OriginalBuffer;
+ CHAR8 *EndBuffer;
+ CHAR8 ValueBuffer[MAXIMUM_VALUE_CHARACTERS];
+ UINT32 BytesPerOutputCharacter;
+ UINTN BytesPerFormatCharacter;
+ UINTN FormatMask;
+ UINTN FormatCharacter;
+ UINTN Width;
+ UINTN Precision;
+ INT64 Value;
+ CONST CHAR8 *ArgumentString;
+ UINTN Character;
+ GUID *TmpGuid;
+ TIME *TmpTime;
+ UINTN Count;
+ UINTN ArgumentMask;
+ INTN BytesPerArgumentCharacter;
+ UINTN ArgumentCharacter;
+ BOOLEAN Done;
+ UINTN Index;
+ CHAR8 Prefix;
+ BOOLEAN ZeroPad;
+ BOOLEAN Comma;
+ UINTN Digits;
+ UINTN Radix;
+ RETURN_STATUS Status;
+ UINT32 GuidData1;
+ UINT16 GuidData2;
+ UINT16 GuidData3;
+ UINTN LengthToReturn;
+
+ //
+ // If you change this code be sure to match the 2 versions of this function.
+ // Nearly identical logic is found in the BasePrintLib and
+ // DxePrintLibPrint2Protocol (both PrintLib instances).
+ //
+
+ //
+ // 1. Buffer shall not be a null pointer when both BufferSize > 0 and
+ // COUNT_ONLY_NO_PRINT is not set in Flags.
+ //
+ if ((BufferSize > 0) && ((Flags & COUNT_ONLY_NO_PRINT) == 0)) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((Buffer != NULL), 0);
+ }
+
+ //
+ // 2. Format shall not be a null pointer when BufferSize > 0 or when
+ // COUNT_ONLY_NO_PRINT is set in Flags.
+ //
+ if ((BufferSize > 0) || ((Flags & COUNT_ONLY_NO_PRINT) != 0)) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((Format != NULL), 0);
+ }
+
+ //
+ // 3. BufferSize shall not be greater than RSIZE_MAX for Unicode output or
+ // ASCII_RSIZE_MAX for Ascii output.
+ //
+ if ((Flags & OUTPUT_UNICODE) != 0) {
+ if (RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((BufferSize <= RSIZE_MAX), 0);
+ }
+ BytesPerOutputCharacter = 2;
+ } else {
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((BufferSize <= ASCII_RSIZE_MAX), 0);
+ }
+ BytesPerOutputCharacter = 1;
+ }
+
+ //
+ // 4. Format shall not contain more than RSIZE_MAX Unicode characters or
+ // ASCII_RSIZE_MAX Ascii characters.
+ //
+ if ((Flags & FORMAT_UNICODE) != 0) {
+ if (RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((StrnLenS ((CHAR16 *)Format, RSIZE_MAX + 1) <= RSIZE_MAX), 0);
+ }
+ BytesPerFormatCharacter = 2;
+ FormatMask = 0xffff;
+ } else {
+ if (ASCII_RSIZE_MAX != 0) {
+ SAFE_PRINT_CONSTRAINT_CHECK ((AsciiStrnLenS (Format, ASCII_RSIZE_MAX + 1) <= ASCII_RSIZE_MAX), 0);
+ }
+ BytesPerFormatCharacter = 1;
+ FormatMask = 0xff;
+ }
+
+ if ((Flags & COUNT_ONLY_NO_PRINT) != 0) {
+ if (BufferSize == 0) {
+ Buffer = NULL;
+ }
+ } else {
+ //
+ // We can run without a Buffer for counting only.
+ //
+ if (BufferSize == 0) {
+ return 0;
+ }
+ }
+
+ LengthToReturn = 0;
+ EndBuffer = NULL;
+ OriginalBuffer = NULL;
+
+ //
+ // Reserve space for the Null terminator.
+ //
+ if (Buffer != NULL) {
+ BufferSize--;
+ OriginalBuffer = Buffer;
+
+ //
+ // Set the tag for the end of the input Buffer.
+ //
+ EndBuffer = Buffer + BufferSize * BytesPerOutputCharacter;
+ }
+
+ //
+ // Get the first character from the format string
+ //
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+
+ //
+ // Loop until the end of the format string is reached or the output buffer is full
+ //
+ while (FormatCharacter != 0) {
+ if ((Buffer != NULL) && (Buffer >= EndBuffer)) {
+ break;
+ }
+ //
+ // Clear all the flag bits except those that may have been passed in
+ //
+ Flags &= (UINTN) (OUTPUT_UNICODE | FORMAT_UNICODE | COUNT_ONLY_NO_PRINT);
+
+ //
+ // Set the default width to zero, and the default precision to 1
+ //
+ Width = 0;
+ Precision = 1;
+ Prefix = 0;
+ Comma = FALSE;
+ ZeroPad = FALSE;
+ Count = 0;
+ Digits = 0;
+
+ switch (FormatCharacter) {
+ case '%':
+ //
+ // Parse Flags and Width
+ //
+ for (Done = FALSE; !Done; ) {
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ switch (FormatCharacter) {
+ case '.':
+ Flags |= PRECISION;
+ break;
+ case '-':
+ Flags |= LEFT_JUSTIFY;
+ break;
+ case '+':
+ Flags |= PREFIX_SIGN;
+ break;
+ case ' ':
+ Flags |= PREFIX_BLANK;
+ break;
+ case ',':
+ Flags |= COMMA_TYPE;
+ break;
+ case 'L':
+ case 'l':
+ Flags |= LONG_TYPE;
+ break;
+ case '*':
+ if ((Flags & PRECISION) == 0) {
+ Flags |= PAD_TO_WIDTH;
+ if (BaseListMarker == NULL) {
+ Width = VA_ARG (VaListMarker, UINTN);
+ } else {
+ Width = BASE_ARG (BaseListMarker, UINTN);
+ }
+ } else {
+ if (BaseListMarker == NULL) {
+ Precision = VA_ARG (VaListMarker, UINTN);
+ } else {
+ Precision = BASE_ARG (BaseListMarker, UINTN);
+ }
+ }
+ break;
+ case '0':
+ if ((Flags & PRECISION) == 0) {
+ Flags |= PREFIX_ZERO;
+ }
+ case '1':
+ case '2':
+ case '3':
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ case '8':
+ case '9':
+ for (Count = 0; ((FormatCharacter >= '0') && (FormatCharacter <= '9')); ){
+ Count = (Count * 10) + FormatCharacter - '0';
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ }
+ Format -= BytesPerFormatCharacter;
+ if ((Flags & PRECISION) == 0) {
+ Flags |= PAD_TO_WIDTH;
+ Width = Count;
+ } else {
+ Precision = Count;
+ }
+ break;
+
+ case '\0':
+ //
+ // Make no output if Format string terminates unexpectedly when
+ // looking up for flag, width, precision and type.
+ //
+ Format -= BytesPerFormatCharacter;
+ Precision = 0;
+ //
+ // break skipped on purpose.
+ //
+ default:
+ Done = TRUE;
+ break;
+ }
+ }
+
+ //
+ // Handle each argument type
+ //
+ switch (FormatCharacter) {
+ case 'p':
+ //
+ // Flag space, +, 0, L & l are invalid for type p.
+ //
+ Flags &= ~((UINTN) (PREFIX_BLANK | PREFIX_SIGN | PREFIX_ZERO | LONG_TYPE));
+ if (sizeof (VOID *) > 4) {
+ Flags |= LONG_TYPE;
+ }
+ //
+ // break skipped on purpose
+ //
+ case 'X':
+ Flags |= PREFIX_ZERO;
+ //
+ // break skipped on purpose
+ //
+ case 'x':
+ Flags |= RADIX_HEX;
+ //
+ // break skipped on purpose
+ //
+ case 'u':
+ if ((Flags & RADIX_HEX) == 0) {
+ Flags &= ~((UINTN) (PREFIX_SIGN));
+ Flags |= UNSIGNED_TYPE;
+ }
+ //
+ // break skipped on purpose
+ //
+ case 'd':
+ if ((Flags & LONG_TYPE) == 0) {
+ //
+ // 'd', 'u', 'x', and 'X' that are not preceded by 'l' or 'L' are assumed to be type "int".
+ // This assumption is made so the format string definition is compatible with the ANSI C
+ // Specification for formatted strings. It is recommended that the Base Types be used
+ // everywhere, but in this one case, compliance with ANSI C is more important, and
+ // provides an implementation that is compatible with that largest possible set of CPU
+ // architectures. This is why the type "int" is used in this one case.
+ //
+ if (BaseListMarker == NULL) {
+ Value = VA_ARG (VaListMarker, int);
+ } else {
+ Value = BASE_ARG (BaseListMarker, int);
+ }
+ } else {
+ if (BaseListMarker == NULL) {
+ Value = VA_ARG (VaListMarker, INT64);
+ } else {
+ Value = BASE_ARG (BaseListMarker, INT64);
+ }
+ }
+ if ((Flags & PREFIX_BLANK) != 0) {
+ Prefix = ' ';
+ }
+ if ((Flags & PREFIX_SIGN) != 0) {
+ Prefix = '+';
+ }
+ if ((Flags & COMMA_TYPE) != 0) {
+ Comma = TRUE;
+ }
+ if ((Flags & RADIX_HEX) == 0) {
+ Radix = 10;
+ if (Comma) {
+ Flags &= ~((UINTN) PREFIX_ZERO);
+ Precision = 1;
+ }
+ if (Value < 0 && (Flags & UNSIGNED_TYPE) == 0) {
+ Flags |= PREFIX_SIGN;
+ Prefix = '-';
+ Value = -Value;
+ } else if ((Flags & UNSIGNED_TYPE) != 0 && (Flags & LONG_TYPE) == 0) {
+ //
+ // 'd', 'u', 'x', and 'X' that are not preceded by 'l' or 'L' are assumed to be type "int".
+ // This assumption is made so the format string definition is compatible with the ANSI C
+ // Specification for formatted strings. It is recommended that the Base Types be used
+ // everywhere, but in this one case, compliance with ANSI C is more important, and
+ // provides an implementation that is compatible with that largest possible set of CPU
+ // architectures. This is why the type "unsigned int" is used in this one case.
+ //
+ Value = (unsigned int)Value;
+ }
+ } else {
+ Radix = 16;
+ Comma = FALSE;
+ if ((Flags & LONG_TYPE) == 0 && Value < 0) {
+ //
+ // 'd', 'u', 'x', and 'X' that are not preceded by 'l' or 'L' are assumed to be type "int".
+ // This assumption is made so the format string definition is compatible with the ANSI C
+ // Specification for formatted strings. It is recommended that the Base Types be used
+ // everywhere, but in this one case, compliance with ANSI C is more important, and
+ // provides an implementation that is compatible with that largest possible set of CPU
+ // architectures. This is why the type "unsigned int" is used in this one case.
+ //
+ Value = (unsigned int)Value;
+ }
+ }
+ //
+ // Convert Value to a reversed string
+ //
+ Count = BasePrintLibValueToString (ValueBuffer, Value, Radix) - ValueBuffer;
+ if (Value == 0 && Precision == 0) {
+ Count = 0;
+ }
+ ArgumentString = (CHAR8 *)ValueBuffer + Count;
+
+ Digits = Count % 3;
+ if (Digits != 0) {
+ Digits = 3 - Digits;
+ }
+ if (Comma && Count != 0) {
+ Count += ((Count - 1) / 3);
+ }
+ if (Prefix != 0) {
+ Count++;
+ Precision++;
+ }
+ Flags |= ARGUMENT_REVERSED;
+ ZeroPad = TRUE;
+ if ((Flags & PREFIX_ZERO) != 0) {
+ if ((Flags & LEFT_JUSTIFY) == 0) {
+ if ((Flags & PAD_TO_WIDTH) != 0) {
+ if ((Flags & PRECISION) == 0) {
+ Precision = Width;
+ }
+ }
+ }
+ }
+ break;
+
+ case 's':
+ case 'S':
+ Flags |= ARGUMENT_UNICODE;
+ //
+ // break skipped on purpose
+ //
+ case 'a':
+ if (BaseListMarker == NULL) {
+ ArgumentString = VA_ARG (VaListMarker, CHAR8 *);
+ } else {
+ ArgumentString = BASE_ARG (BaseListMarker, CHAR8 *);
+ }
+ if (ArgumentString == NULL) {
+ Flags &= ~((UINTN) ARGUMENT_UNICODE);
+ ArgumentString = "<null string>";
+ }
+ //
+ // Set the default precision for string to be zero if not specified.
+ //
+ if ((Flags & PRECISION) == 0) {
+ Precision = 0;
+ }
+ break;
+
+ case 'c':
+ if (BaseListMarker == NULL) {
+ Character = VA_ARG (VaListMarker, UINTN) & 0xffff;
+ } else {
+ Character = BASE_ARG (BaseListMarker, UINTN) & 0xffff;
+ }
+ ArgumentString = (CHAR8 *)&Character;
+ Flags |= ARGUMENT_UNICODE;
+ break;
+
+ case 'g':
+ if (BaseListMarker == NULL) {
+ TmpGuid = VA_ARG (VaListMarker, GUID *);
+ } else {
+ TmpGuid = BASE_ARG (BaseListMarker, GUID *);
+ }
+ if (TmpGuid == NULL) {
+ ArgumentString = "<null guid>";
+ } else {
+ GuidData1 = ReadUnaligned32 (&(TmpGuid->Data1));
+ GuidData2 = ReadUnaligned16 (&(TmpGuid->Data2));
+ GuidData3 = ReadUnaligned16 (&(TmpGuid->Data3));
+ BasePrintLibSPrint (
+ ValueBuffer,
+ MAXIMUM_VALUE_CHARACTERS,
+ 0,
+ "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
+ GuidData1,
+ GuidData2,
+ GuidData3,
+ TmpGuid->Data4[0],
+ TmpGuid->Data4[1],
+ TmpGuid->Data4[2],
+ TmpGuid->Data4[3],
+ TmpGuid->Data4[4],
+ TmpGuid->Data4[5],
+ TmpGuid->Data4[6],
+ TmpGuid->Data4[7]
+ );
+ ArgumentString = ValueBuffer;
+ }
+ break;
+
+ case 't':
+ if (BaseListMarker == NULL) {
+ TmpTime = VA_ARG (VaListMarker, TIME *);
+ } else {
+ TmpTime = BASE_ARG (BaseListMarker, TIME *);
+ }
+ if (TmpTime == NULL) {
+ ArgumentString = "<null time>";
+ } else {
+ BasePrintLibSPrint (
+ ValueBuffer,
+ MAXIMUM_VALUE_CHARACTERS,
+ 0,
+ "%02d/%02d/%04d %02d:%02d",
+ TmpTime->Month,
+ TmpTime->Day,
+ TmpTime->Year,
+ TmpTime->Hour,
+ TmpTime->Minute
+ );
+ ArgumentString = ValueBuffer;
+ }
+ break;
+
+ case 'r':
+ if (BaseListMarker == NULL) {
+ Status = VA_ARG (VaListMarker, RETURN_STATUS);
+ } else {
+ Status = BASE_ARG (BaseListMarker, RETURN_STATUS);
+ }
+ ArgumentString = ValueBuffer;
+ if (RETURN_ERROR (Status)) {
+ //
+ // Clear error bit
+ //
+ Index = Status & ~MAX_BIT;
+ if (Index > 0 && Index <= ERROR_STATUS_NUMBER) {
+ ArgumentString = mErrorString [Index - 1];
+ }
+ } else {
+ Index = Status;
+ if (Index <= WARNING_STATUS_NUMBER) {
+ ArgumentString = mWarningString [Index];
+ }
+ }
+ if (ArgumentString == ValueBuffer) {
+ BasePrintLibSPrint ((CHAR8 *) ValueBuffer, MAXIMUM_VALUE_CHARACTERS, 0, "%08X", Status);
+ }
+ break;
+
+ case '\r':
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ if (FormatCharacter == '\n') {
+ //
+ // Translate '\r\n' to '\r\n'
+ //
+ ArgumentString = "\r\n";
+ } else {
+ //
+ // Translate '\r' to '\r'
+ //
+ ArgumentString = "\r";
+ Format -= BytesPerFormatCharacter;
+ }
+ break;
+
+ case '\n':
+ //
+ // Translate '\n' to '\r\n' and '\n\r' to '\r\n'
+ //
+ ArgumentString = "\r\n";
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ if (FormatCharacter != '\r') {
+ Format -= BytesPerFormatCharacter;
+ }
+ break;
+
+ case '%':
+ default:
+ //
+ // if the type is '%' or unknown, then print it to the screen
+ //
+ ArgumentString = (CHAR8 *)&FormatCharacter;
+ Flags |= ARGUMENT_UNICODE;
+ break;
+ }
+ break;
+
+ case '\r':
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ if (FormatCharacter == '\n') {
+ //
+ // Translate '\r\n' to '\r\n'
+ //
+ ArgumentString = "\r\n";
+ } else {
+ //
+ // Translate '\r' to '\r'
+ //
+ ArgumentString = "\r";
+ Format -= BytesPerFormatCharacter;
+ }
+ break;
+
+ case '\n':
+ //
+ // Translate '\n' to '\r\n' and '\n\r' to '\r\n'
+ //
+ ArgumentString = "\r\n";
+ Format += BytesPerFormatCharacter;
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ if (FormatCharacter != '\r') {
+ Format -= BytesPerFormatCharacter;
+ }
+ break;
+
+ default:
+ ArgumentString = (CHAR8 *)&FormatCharacter;
+ Flags |= ARGUMENT_UNICODE;
+ break;
+ }
+
+ //
+ // Retrieve the ArgumentString attriubutes
+ //
+ if ((Flags & ARGUMENT_UNICODE) != 0) {
+ ArgumentMask = 0xffff;
+ BytesPerArgumentCharacter = 2;
+ } else {
+ ArgumentMask = 0xff;
+ BytesPerArgumentCharacter = 1;
+ }
+ if ((Flags & ARGUMENT_REVERSED) != 0) {
+ BytesPerArgumentCharacter = -BytesPerArgumentCharacter;
+ } else {
+ //
+ // Compute the number of characters in ArgumentString and store it in Count
+ // ArgumentString is either null-terminated, or it contains Precision characters
+ //
+ for (Count = 0;
+ (ArgumentString[Count * BytesPerArgumentCharacter] != '\0' ||
+ (BytesPerArgumentCharacter > 1 &&
+ ArgumentString[Count * BytesPerArgumentCharacter + 1]!= '\0')) &&
+ (Count < Precision || ((Flags & PRECISION) == 0));
+ Count++) {
+ ArgumentCharacter = ((ArgumentString[Count * BytesPerArgumentCharacter] & 0xff) | ((ArgumentString[Count * BytesPerArgumentCharacter + 1]) << 8)) & ArgumentMask;
+ if (ArgumentCharacter == 0) {
+ break;
+ }
+ }
+ }
+
+ if (Precision < Count) {
+ Precision = Count;
+ }
+
+ //
+ // Pad before the string
+ //
+ if ((Flags & (PAD_TO_WIDTH | LEFT_JUSTIFY)) == (PAD_TO_WIDTH)) {
+ LengthToReturn += ((Width - Precision) * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Precision, ' ', BytesPerOutputCharacter);
+ }
+ }
+
+ if (ZeroPad) {
+ if (Prefix != 0) {
+ LengthToReturn += (1 * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, Prefix, BytesPerOutputCharacter);
+ }
+ }
+ LengthToReturn += ((Precision - Count) * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Precision - Count, '0', BytesPerOutputCharacter);
+ }
+ } else {
+ LengthToReturn += ((Precision - Count) * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Precision - Count, ' ', BytesPerOutputCharacter);
+ }
+ if (Prefix != 0) {
+ LengthToReturn += (1 * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, Prefix, BytesPerOutputCharacter);
+ }
+ }
+ }
+
+ //
+ // Output the Prefix character if it is present
+ //
+ Index = 0;
+ if (Prefix != 0) {
+ Index++;
+ }
+
+ //
+ // Copy the string into the output buffer performing the required type conversions
+ //
+ while (Index < Count &&
+ (ArgumentString[0] != '\0' ||
+ (BytesPerArgumentCharacter > 1 && ArgumentString[1] != '\0'))) {
+ ArgumentCharacter = ((*ArgumentString & 0xff) | (((UINT8)*(ArgumentString + 1)) << 8)) & ArgumentMask;
+
+ LengthToReturn += (1 * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ArgumentCharacter, BytesPerOutputCharacter);
+ }
+ ArgumentString += BytesPerArgumentCharacter;
+ Index++;
+ if (Comma) {
+ Digits++;
+ if (Digits == 3) {
+ Digits = 0;
+ Index++;
+ if (Index < Count) {
+ LengthToReturn += (1 * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ',', BytesPerOutputCharacter);
+ }
+ }
+ }
+ }
+ }
+
+ //
+ // Pad after the string
+ //
+ if ((Flags & (PAD_TO_WIDTH | LEFT_JUSTIFY)) == (PAD_TO_WIDTH | LEFT_JUSTIFY)) {
+ LengthToReturn += ((Width - Precision) * BytesPerOutputCharacter);
+ if ((Flags & COUNT_ONLY_NO_PRINT) == 0 && Buffer != NULL) {
+ Buffer = BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Precision, ' ', BytesPerOutputCharacter);
+ }
+ }
+
+ //
+ // Get the next character from the format string
+ //
+ Format += BytesPerFormatCharacter;
+
+ //
+ // Get the next character from the format string
+ //
+ FormatCharacter = ((*Format & 0xff) | ((BytesPerFormatCharacter == 1) ? 0 : (*(Format + 1) << 8))) & FormatMask;
+ }
+
+ if ((Flags & COUNT_ONLY_NO_PRINT) != 0) {
+ return (LengthToReturn / BytesPerOutputCharacter);
+ }
+
+ ASSERT (Buffer != NULL);
+ //
+ // Null terminate the Unicode or ASCII string
+ //
+ BasePrintLibFillBuffer (Buffer, EndBuffer + BytesPerOutputCharacter, 1, 0, BytesPerOutputCharacter);
+
+ return ((Buffer - OriginalBuffer) / BytesPerOutputCharacter);
+}
+
+/**
+ Worker function that produces a Null-terminated string in an output buffer
+ based on a Null-terminated format string and variable argument list.
+
+ VSPrint function to process format and place the results in Buffer. Since a
+ VA_LIST is used this routine allows the nesting of Vararg routines. Thus
+ this is the main print working routine
+
+ @param StartOfBuffer The character buffer to print the results of the parsing
+ of Format into.
+ @param BufferSize The maximum number of characters to put into buffer.
+ Zero means no limit.
+ @param Flags Initial flags value.
+ Can only have FORMAT_UNICODE and OUTPUT_UNICODE set
+ @param FormatString A Null-terminated format string.
+ @param ... The variable argument list.
+
+ @return The number of characters printed.
+
+**/
+UINTN
+EFIAPI
+BasePrintLibSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN CONST CHAR8 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN NumberOfPrinted;
+
+ VA_START (Marker, FormatString);
+ NumberOfPrinted = BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, Flags, FormatString, Marker, NULL);
+ VA_END (Marker);
+ return NumberOfPrinted;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.h b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.h
new file mode 100644
index 0000000..c20a582
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/BasePrintLib/PrintLibInternal.h
@@ -0,0 +1,271 @@
+/** @file
+ Base Print Library instance Internal Functions definition.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __PRINT_LIB_INTERNAL_H__
+#define __PRINT_LIB_INTERNAL_H__
+
+#include <Base.h>
+#include <Library/PrintLib.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+
+
+//
+// Print primitives
+//
+#define PREFIX_SIGN BIT1
+#define PREFIX_BLANK BIT2
+#define LONG_TYPE BIT4
+#define OUTPUT_UNICODE BIT6
+#define FORMAT_UNICODE BIT8
+#define PAD_TO_WIDTH BIT9
+#define ARGUMENT_UNICODE BIT10
+#define PRECISION BIT11
+#define ARGUMENT_REVERSED BIT12
+#define COUNT_ONLY_NO_PRINT BIT13
+#define UNSIGNED_TYPE BIT14
+
+//
+// Record date and time information
+//
+typedef struct {
+ UINT16 Year;
+ UINT8 Month;
+ UINT8 Day;
+ UINT8 Hour;
+ UINT8 Minute;
+ UINT8 Second;
+ UINT8 Pad1;
+ UINT32 Nanosecond;
+ INT16 TimeZone;
+ UINT8 Daylight;
+ UINT8 Pad2;
+} TIME;
+
+/**
+ Worker function that produces a Null-terminated string in an output buffer
+ based on a Null-terminated format string and a VA_LIST argument list.
+
+ VSPrint function to process format and place the results in Buffer. Since a
+ VA_LIST is used this routine allows the nesting of Vararg routines. Thus
+ this is the main print working routine.
+
+ If COUNT_ONLY_NO_PRINT is set in Flags, Buffer will not be modified at all.
+
+ @param[out] Buffer The character buffer to print the results of the
+ parsing of Format into.
+ @param[in] BufferSize The maximum number of characters to put into
+ buffer.
+ @param[in] Flags Initial flags value.
+ Can only have FORMAT_UNICODE, OUTPUT_UNICODE,
+ and COUNT_ONLY_NO_PRINT set.
+ @param[in] Format A Null-terminated format string.
+ @param[in] VaListMarker VA_LIST style variable argument list consumed by
+ processing Format.
+ @param[in] BaseListMarker BASE_LIST style variable argument list consumed
+ by processing Format.
+
+ @return The number of characters printed not including the Null-terminator.
+ If COUNT_ONLY_NO_PRINT was set returns the same, but without any
+ modification to Buffer.
+
+**/
+UINTN
+BasePrintLibSPrintMarker (
+ OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN CONST CHAR8 *Format,
+ IN VA_LIST VaListMarker, OPTIONAL
+ IN BASE_LIST BaseListMarker OPTIONAL
+ );
+
+/**
+ Worker function that produces a Null-terminated string in an output buffer
+ based on a Null-terminated format string and variable argument list.
+
+ VSPrint function to process format and place the results in Buffer. Since a
+ VA_LIST is used this routine allows the nesting of Vararg routines. Thus
+ this is the main print working routine
+
+ @param StartOfBuffer The character buffer to print the results of the parsing
+ of Format into.
+ @param BufferSize The maximum number of characters to put into buffer.
+ Zero means no limit.
+ @param Flags Initial flags value.
+ Can only have FORMAT_UNICODE and OUTPUT_UNICODE set
+ @param FormatString Null-terminated format string.
+ @param ... The variable argument list.
+
+ @return The number of characters printed.
+
+**/
+UINTN
+EFIAPI
+BasePrintLibSPrint (
+ OUT CHAR8 *StartOfBuffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN CONST CHAR8 *FormatString,
+ ...
+ );
+
+/**
+ Internal function that places the character into the Buffer.
+
+ Internal function that places ASCII or Unicode character into the Buffer.
+
+ @param Buffer Buffer to place the Unicode or ASCII string.
+ @param EndBuffer The end of the input Buffer. No characters will be
+ placed after that.
+ @param Length The count of character to be placed into Buffer.
+ (Negative value indicates no buffer fill.)
+ @param Character The character to be placed into Buffer.
+ @param Increment The character increment in Buffer.
+
+ @return Buffer Buffer filled with the input Character.
+
+**/
+CHAR8 *
+BasePrintLibFillBuffer (
+ OUT CHAR8 *Buffer,
+ IN CHAR8 *EndBuffer,
+ IN INTN Length,
+ IN UINTN Character,
+ IN INTN Increment
+ );
+
+/**
+ Internal function that convert a number to a string in Buffer.
+
+ Print worker function that converts a decimal or hexadecimal number to an ASCII string in Buffer.
+
+ @param Buffer Location to place the ASCII string of Value.
+ @param Value The value to convert to a Decimal or Hexadecimal string in Buffer.
+ @param Radix Radix of the value
+
+ @return A pointer to the end of buffer filled with ASCII string.
+
+**/
+CHAR8 *
+BasePrintLibValueToString (
+ IN OUT CHAR8 *Buffer,
+ IN INT64 Value,
+ IN UINTN Radix
+ );
+
+/**
+ Internal function that converts a decimal value to a Null-terminated string.
+
+ Converts the decimal number specified by Value to a Null-terminated
+ string specified by Buffer containing at most Width characters.
+ If Width is 0 then a width of MAXIMUM_VALUE_CHARACTERS is assumed.
+ The total number of characters placed in Buffer is returned.
+ If the conversion contains more than Width characters, then only the first
+ Width characters are returned, and the total number of characters
+ required to perform the conversion is returned.
+ Additional conversion parameters are specified in Flags.
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and commas
+ are inserted every 3rd digit starting from the right.
+ If Value is < 0, then the fist character in Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored,
+ then Buffer is padded with '0' characters so the combination of the optional '-'
+ sign character, '0' characters, digit characters for Value, and the Null-terminator
+ add up to Width characters.
+
+ If Buffer is NULL, then ASSERT().
+ If unsupported bits are set in Flags, then ASSERT().
+ If Width >= MAXIMUM_VALUE_CHARACTERS, then ASSERT()
+
+ @param Buffer The pointer to the output buffer for the produced Null-terminated
+ string.
+ @param Flags The bitmask of flags that specify left justification, zero pad,
+ and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of characters to place in Buffer, not including
+ the Null-terminator.
+ @param Increment Character increment in Buffer.
+
+ @return Total number of characters required to perform the conversion.
+
+**/
+UINTN
+BasePrintLibConvertValueToString (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width,
+ IN UINTN Increment
+ );
+
+/**
+ Internal function that converts a decimal value to a Null-terminated string.
+
+ Converts the decimal number specified by Value to a Null-terminated string
+ specified by Buffer containing at most Width characters. If Width is 0 then a
+ width of MAXIMUM_VALUE_CHARACTERS is assumed. If the conversion contains more
+ than Width characters, then only the first Width characters are placed in
+ Buffer. Additional conversion parameters are specified in Flags.
+ The Flags bit LEFT_JUSTIFY is always ignored.
+ All conversions are left justified in Buffer.
+ If Width is 0, PREFIX_ZERO is ignored in Flags.
+ If COMMA_TYPE is set in Flags, then PREFIX_ZERO is ignored in Flags, and
+ commas are inserted every 3rd digit starting from the right.
+ If Value is < 0, then the fist character in Buffer is a '-'.
+ If PREFIX_ZERO is set in Flags and PREFIX_ZERO is not being ignored,
+ then Buffer is padded with '0' characters so the combination of the optional
+ '-' sign character, '0' characters, digit characters for Value, and the
+ Null-terminator add up to Width characters.
+
+ If an error would be returned, the function will ASSERT().
+
+ @param Buffer The pointer to the output buffer for the produced
+ Null-terminated string.
+ @param BufferSize The size of Buffer in bytes, including the
+ Null-terminator.
+ @param Flags The bitmask of flags that specify left justification,
+ zero pad, and commas.
+ @param Value The 64-bit signed value to convert to a string.
+ @param Width The maximum number of characters to place in Buffer,
+ not including the Null-terminator.
+ @param Increment The character increment in Buffer.
+
+ @retval RETURN_SUCCESS The decimal value is converted.
+ @retval RETURN_BUFFER_TOO_SMALL If BufferSize cannot hold the converted
+ value.
+ @retval RETURN_INVALID_PARAMETER If Buffer is NULL.
+ If Increment is 1 and
+ PcdMaximumAsciiStringLength is not zero,
+ BufferSize is greater than
+ PcdMaximumAsciiStringLength.
+ If Increment is not 1 and
+ PcdMaximumUnicodeStringLength is not zero,
+ BufferSize is greater than
+ (PcdMaximumUnicodeStringLength *
+ sizeof (CHAR16) + 1).
+ If unsupported bits are set in Flags.
+ If both COMMA_TYPE and RADIX_HEX are set in
+ Flags.
+ If Width >= MAXIMUM_VALUE_CHARACTERS.
+
+**/
+RETURN_STATUS
+BasePrintLibConvertValueToStringS (
+ IN OUT CHAR8 *Buffer,
+ IN UINTN BufferSize,
+ IN UINTN Flags,
+ IN INT64 Value,
+ IN UINTN Width,
+ IN UINTN Increment
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/MemoryAllocationLib.c b/efi_memtest/memtest86+/efi/Include/src/MemoryAllocationLib.c
new file mode 100644
index 0000000..554b6a7
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/MemoryAllocationLib.c
@@ -0,0 +1,815 @@
+/** @file
+ Support routines for memory allocation routines based
+ on boot services for Dxe phase drivers.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include <Uefi.h>
+
+
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+
+/**
+ Allocates one or more 4KB pages of a certain memory type.
+
+ Allocates the number of 4KB pages of a certain memory type and returns a pointer to the allocated
+ buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL is returned.
+ If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param MemoryType The type of memory to allocate.
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalAllocatePages (
+ IN EFI_MEMORY_TYPE MemoryType,
+ IN UINTN Pages
+ )
+{
+ EFI_STATUS Status;
+ EFI_PHYSICAL_ADDRESS Memory;
+
+ if (Pages == 0) {
+ return NULL;
+ }
+
+ Status = gBS->AllocatePages (AllocateAnyPages, MemoryType, Pages, &Memory);
+ if (EFI_ERROR (Status)) {
+ return NULL;
+ }
+ return (VOID *) (UINTN) Memory;
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiBootServicesData.
+
+ Allocates the number of 4KB pages of type EfiBootServicesData and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocatePages (
+ IN UINTN Pages
+ )
+{
+ return InternalAllocatePages (EfiBootServicesData, Pages);
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiRuntimeServicesData.
+
+ Allocates the number of 4KB pages of type EfiRuntimeServicesData and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimePages (
+ IN UINTN Pages
+ )
+{
+ return InternalAllocatePages (EfiRuntimeServicesData, Pages);
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiReservedMemoryType.
+
+ Allocates the number of 4KB pages of type EfiReservedMemoryType and returns a pointer to the
+ allocated buffer. The buffer returned is aligned on a 4KB boundary. If Pages is 0, then NULL
+ is returned. If there is not enough memory remaining to satisfy the request, then NULL is
+ returned.
+
+ @param Pages The number of 4 KB pages to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedPages (
+ IN UINTN Pages
+ )
+{
+ return InternalAllocatePages (EfiReservedMemoryType, Pages);
+}
+
+/**
+ Frees one or more 4KB pages that were previously allocated with one of the page allocation
+ functions in the Memory Allocation Library.
+
+ Frees the number of 4KB pages specified by Pages from the buffer specified by Buffer. Buffer
+ must have been allocated on a previous call to the page allocation services of the Memory
+ Allocation Library. If it is not possible to free allocated pages, then this function will
+ perform no actions.
+
+ If Buffer was not allocated with a page allocation function in the Memory Allocation Library,
+ then ASSERT().
+ If Pages is zero, then ASSERT().
+
+ @param Buffer The pointer to the buffer of pages to free.
+ @param Pages The number of 4 KB pages to free.
+
+**/
+VOID
+EFIAPI
+FreePages (
+ IN VOID *Buffer,
+ IN UINTN Pages
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (Pages != 0);
+ Status = gBS->FreePages ((EFI_PHYSICAL_ADDRESS) (UINTN) Buffer, Pages);
+ ASSERT_EFI_ERROR (Status);
+}
+
+/**
+ Allocates one or more 4KB pages of a certain memory type at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of a certain memory type with an alignment
+ specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is returned.
+ If there is not enough memory at the specified alignment remaining to satisfy the request, then
+ NULL is returned.
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param MemoryType The type of memory to allocate.
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalAllocateAlignedPages (
+ IN EFI_MEMORY_TYPE MemoryType,
+ IN UINTN Pages,
+ IN UINTN Alignment
+ )
+{
+ EFI_STATUS Status;
+ EFI_PHYSICAL_ADDRESS Memory;
+ UINTN AlignedMemory;
+ UINTN AlignmentMask;
+ UINTN UnalignedPages;
+ UINTN RealPages;
+
+ //
+ // Alignment must be a power of two or zero.
+ //
+ ASSERT ((Alignment & (Alignment - 1)) == 0);
+
+ if (Pages == 0) {
+ return NULL;
+ }
+ if (Alignment > EFI_PAGE_SIZE) {
+ //
+ // Calculate the total number of pages since alignment is larger than page size.
+ //
+ AlignmentMask = Alignment - 1;
+ RealPages = Pages + EFI_SIZE_TO_PAGES (Alignment);
+ //
+ // Make sure that Pages plus EFI_SIZE_TO_PAGES (Alignment) does not overflow.
+ //
+ ASSERT (RealPages > Pages);
+
+ Status = gBS->AllocatePages (AllocateAnyPages, MemoryType, RealPages, &Memory);
+ if (EFI_ERROR (Status)) {
+ return NULL;
+ }
+ AlignedMemory = ((UINTN) Memory + AlignmentMask) & ~AlignmentMask;
+ UnalignedPages = EFI_SIZE_TO_PAGES (AlignedMemory - (UINTN) Memory);
+ if (UnalignedPages > 0) {
+ //
+ // Free first unaligned page(s).
+ //
+ Status = gBS->FreePages (Memory, UnalignedPages);
+ ASSERT_EFI_ERROR (Status);
+ }
+ Memory = AlignedMemory + EFI_PAGES_TO_SIZE (Pages);
+ UnalignedPages = RealPages - Pages - UnalignedPages;
+ if (UnalignedPages > 0) {
+ //
+ // Free last unaligned page(s).
+ //
+ Status = gBS->FreePages (Memory, UnalignedPages);
+ ASSERT_EFI_ERROR (Status);
+ }
+ } else {
+ //
+ // Do not over-allocate pages in this case.
+ //
+ Status = gBS->AllocatePages (AllocateAnyPages, MemoryType, Pages, &Memory);
+ if (EFI_ERROR (Status)) {
+ return NULL;
+ }
+ AlignedMemory = (UINTN) Memory;
+ }
+ return (VOID *) AlignedMemory;
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiBootServicesData at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiBootServicesData with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedPages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ )
+{
+ return InternalAllocateAlignedPages (EfiBootServicesData, Pages, Alignment);
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiRuntimeServicesData at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiRuntimeServicesData with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedRuntimePages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ )
+{
+ return InternalAllocateAlignedPages (EfiRuntimeServicesData, Pages, Alignment);
+}
+
+/**
+ Allocates one or more 4KB pages of type EfiReservedMemoryType at a specified alignment.
+
+ Allocates the number of 4KB pages specified by Pages of type EfiReservedMemoryType with an
+ alignment specified by Alignment. The allocated buffer is returned. If Pages is 0, then NULL is
+ returned. If there is not enough memory at the specified alignment remaining to satisfy the
+ request, then NULL is returned.
+
+ If Alignment is not a power of two and Alignment is not zero, then ASSERT().
+ If Pages plus EFI_SIZE_TO_PAGES (Alignment) overflows, then ASSERT().
+
+ @param Pages The number of 4 KB pages to allocate.
+ @param Alignment The requested alignment of the allocation. Must be a power of two.
+ If Alignment is zero, then byte alignment is used.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateAlignedReservedPages (
+ IN UINTN Pages,
+ IN UINTN Alignment
+ )
+{
+ return InternalAllocateAlignedPages (EfiReservedMemoryType, Pages, Alignment);
+}
+
+/**
+ Frees one or more 4KB pages that were previously allocated with one of the aligned page
+ allocation functions in the Memory Allocation Library.
+
+ Frees the number of 4KB pages specified by Pages from the buffer specified by Buffer. Buffer
+ must have been allocated on a previous call to the aligned page allocation services of the Memory
+ Allocation Library. If it is not possible to free allocated pages, then this function will
+ perform no actions.
+
+ If Buffer was not allocated with an aligned page allocation function in the Memory Allocation
+ Library, then ASSERT().
+ If Pages is zero, then ASSERT().
+
+ @param Buffer The pointer to the buffer of pages to free.
+ @param Pages The number of 4 KB pages to free.
+
+**/
+VOID
+EFIAPI
+FreeAlignedPages (
+ IN VOID *Buffer,
+ IN UINTN Pages
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (Pages != 0);
+ Status = gBS->FreePages ((EFI_PHYSICAL_ADDRESS) (UINTN) Buffer, Pages);
+ ASSERT_EFI_ERROR (Status);
+}
+
+/**
+ Allocates a buffer of a certain pool type.
+
+ Allocates the number bytes specified by AllocationSize of a certain pool type and returns a
+ pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param MemoryType The type of memory to allocate.
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalAllocatePool (
+ IN EFI_MEMORY_TYPE MemoryType,
+ IN UINTN AllocationSize
+ )
+{
+ EFI_STATUS Status;
+ VOID *Memory;
+
+ Status = gBS->AllocatePool (MemoryType, AllocationSize, &Memory);
+ if (EFI_ERROR (Status)) {
+ Memory = NULL;
+ }
+ return Memory;
+}
+
+/**
+ Allocates a buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData and returns a
+ pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocatePool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocatePool (EfiBootServicesData, AllocationSize);
+}
+
+/**
+ Allocates a buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData and returns
+ a pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimePool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocatePool (EfiRuntimeServicesData, AllocationSize);
+}
+
+/**
+ Allocates a buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType and returns
+ a pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
+ returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedPool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocatePool (EfiReservedMemoryType, AllocationSize);
+}
+
+/**
+ Allocates and zeros a buffer of a certain pool type.
+
+ Allocates the number bytes specified by AllocationSize of a certain pool type, clears the buffer
+ with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a valid
+ buffer of 0 size is returned. If there is not enough memory remaining to satisfy the request,
+ then NULL is returned.
+
+ @param PoolType The type of memory to allocate.
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalAllocateZeroPool (
+ IN EFI_MEMORY_TYPE PoolType,
+ IN UINTN AllocationSize
+ )
+{
+ VOID *Memory;
+
+ Memory = InternalAllocatePool (PoolType, AllocationSize);
+ if (Memory != NULL) {
+ Memory = ZeroMem (Memory, AllocationSize);
+ }
+ return Memory;
+}
+
+/**
+ Allocates and zeros a buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateZeroPool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocateZeroPool (EfiBootServicesData, AllocationSize);
+}
+
+/**
+ Allocates and zeros a buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimeZeroPool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocateZeroPool (EfiRuntimeServicesData, AllocationSize);
+}
+
+/**
+ Allocates and zeros a buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType, clears the
+ buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
+ valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
+ request, then NULL is returned.
+
+ @param AllocationSize The number of bytes to allocate and zero.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedZeroPool (
+ IN UINTN AllocationSize
+ )
+{
+ return InternalAllocateZeroPool (EfiReservedMemoryType, AllocationSize);
+}
+
+/**
+ Copies a buffer to an allocated buffer of a certain pool type.
+
+ Allocates the number bytes specified by AllocationSize of a certain pool type, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param PoolType The type of pool to allocate.
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalAllocateCopyPool (
+ IN EFI_MEMORY_TYPE PoolType,
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ )
+{
+ VOID *Memory;
+
+ ASSERT (Buffer != NULL);
+ ASSERT (AllocationSize <= (MAX_ADDRESS - (UINTN) Buffer + 1));
+
+ Memory = InternalAllocatePool (PoolType, AllocationSize);
+ if (Memory != NULL) {
+ Memory = CopyMem (Memory, Buffer, AllocationSize);
+ }
+ return Memory;
+}
+
+/**
+ Copies a buffer to an allocated buffer of type EfiBootServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiBootServicesData, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ )
+{
+ return InternalAllocateCopyPool (EfiBootServicesData, AllocationSize, Buffer);
+}
+
+/**
+ Copies a buffer to an allocated buffer of type EfiRuntimeServicesData.
+
+ Allocates the number bytes specified by AllocationSize of type EfiRuntimeServicesData, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateRuntimeCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ )
+{
+ return InternalAllocateCopyPool (EfiRuntimeServicesData, AllocationSize, Buffer);
+}
+
+/**
+ Copies a buffer to an allocated buffer of type EfiReservedMemoryType.
+
+ Allocates the number bytes specified by AllocationSize of type EfiReservedMemoryType, copies
+ AllocationSize bytes from Buffer to the newly allocated buffer, and returns a pointer to the
+ allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is returned. If there
+ is not enough memory remaining to satisfy the request, then NULL is returned.
+
+ If Buffer is NULL, then ASSERT().
+ If AllocationSize is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param AllocationSize The number of bytes to allocate and zero.
+ @param Buffer The buffer to copy to the allocated buffer.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+AllocateReservedCopyPool (
+ IN UINTN AllocationSize,
+ IN CONST VOID *Buffer
+ )
+{
+ return InternalAllocateCopyPool (EfiReservedMemoryType, AllocationSize, Buffer);
+}
+
+/**
+ Reallocates a buffer of a specified memory type.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of the type
+ specified by PoolType. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param PoolType The type of pool to allocate.
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+InternalReallocatePool (
+ IN EFI_MEMORY_TYPE PoolType,
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ )
+{
+ VOID *NewBuffer;
+
+ NewBuffer = InternalAllocateZeroPool (PoolType, NewSize);
+ if (NewBuffer != NULL && OldBuffer != NULL) {
+ CopyMem (NewBuffer, OldBuffer, MIN (OldSize, NewSize));
+ FreePool (OldBuffer);
+ }
+ return NewBuffer;
+}
+
+/**
+ Reallocates a buffer of type EfiBootServicesData.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiBootServicesData. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocatePool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ )
+{
+ return InternalReallocatePool (EfiBootServicesData, OldSize, NewSize, OldBuffer);
+}
+
+/**
+ Reallocates a buffer of type EfiRuntimeServicesData.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiRuntimeServicesData. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocateRuntimePool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ )
+{
+ return InternalReallocatePool (EfiRuntimeServicesData, OldSize, NewSize, OldBuffer);
+}
+
+/**
+ Reallocates a buffer of type EfiReservedMemoryType.
+
+ Allocates and zeros the number bytes specified by NewSize from memory of type
+ EfiReservedMemoryType. If OldBuffer is not NULL, then the smaller of OldSize and
+ NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
+ OldBuffer is freed. A pointer to the newly allocated buffer is returned.
+ If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
+ enough memory remaining to satisfy the request, then NULL is returned.
+
+ If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
+ is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
+
+ @param OldSize The size, in bytes, of OldBuffer.
+ @param NewSize The size, in bytes, of the buffer to reallocate.
+ @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
+ parameter that may be NULL.
+
+ @return A pointer to the allocated buffer or NULL if allocation fails.
+
+**/
+VOID *
+EFIAPI
+ReallocateReservedPool (
+ IN UINTN OldSize,
+ IN UINTN NewSize,
+ IN VOID *OldBuffer OPTIONAL
+ )
+{
+ return InternalReallocatePool (EfiReservedMemoryType, OldSize, NewSize, OldBuffer);
+}
+
+/**
+ Frees a buffer that was previously allocated with one of the pool allocation functions in the
+ Memory Allocation Library.
+
+ Frees the buffer specified by Buffer. Buffer must have been allocated on a previous call to the
+ pool allocation services of the Memory Allocation Library. If it is not possible to free pool
+ resources, then this function will perform no actions.
+
+ If Buffer was not allocated with a pool allocation function in the Memory Allocation Library,
+ then ASSERT().
+
+ @param Buffer The pointer to the buffer to free.
+
+**/
+VOID
+EFIAPI
+FreePool (
+ IN VOID *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ Status = gBS->FreePool (Buffer);
+ ASSERT_EFI_ERROR (Status);
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/PcdLib.c b/efi_memtest/memtest86+/efi/Include/src/PcdLib.c
new file mode 100644
index 0000000..265fae5
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/PcdLib.c
@@ -0,0 +1,1113 @@
+/** @file
+ A emptry template implementation of PCD Library.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Base.h>
+
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BaseMemoryLib.h>
+
+
+/**
+ This function provides a means by which SKU support can be established in the PCD infrastructure.
+
+ Sets the current SKU in the PCD database to the value specified by SkuId. SkuId is returned.
+
+ @param[in] SkuId The SKU value that will be used when the PCD service will retrieve and
+ set values associated with a PCD token.
+
+ @return Return the SKU ID that just be set.
+
+**/
+UINTN
+EFIAPI
+LibPcdSetSku (
+ IN UINTN SkuId
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 8-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 8-bit value for the token specified by TokenNumber.
+
+**/
+UINT8
+EFIAPI
+LibPcdGet8 (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 16-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 16-bit value for the token specified by TokenNumber.
+
+**/
+UINT16
+EFIAPI
+LibPcdGet16 (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 32-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 32-bit value for the token specified by TokenNumber.
+
+**/
+UINT32
+EFIAPI
+LibPcdGet32 (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 64-bit value for the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the 64-bit value for the token specified by TokenNumber.
+
+**/
+UINT64
+EFIAPI
+LibPcdGet64 (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the pointer to the buffer of the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the pointer to the token specified by TokenNumber.
+
+**/
+VOID *
+EFIAPI
+LibPcdGetPtr (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the Boolean value of the token specified by TokenNumber.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the Boolean value of the token specified by TokenNumber.
+
+**/
+BOOLEAN
+EFIAPI
+LibPcdGetBool (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve the size of a given PCD token.
+
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Returns the size of the token specified by TokenNumber.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetSize (
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 8-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT8.
+
+**/
+UINT8
+EFIAPI
+LibPcdGetEx8 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 16-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT16.
+
+**/
+UINT16
+EFIAPI
+LibPcdGetEx16 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ Returns the 32-bit value for the token specified by TokenNumber and Guid.
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT32.
+
+**/
+UINT32
+EFIAPI
+LibPcdGetEx32 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the 64-bit value for the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the UINT64.
+
+**/
+UINT64
+EFIAPI
+LibPcdGetEx64 (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the pointer to the buffer of token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the VOID* pointer.
+
+**/
+VOID *
+EFIAPI
+LibPcdGetExPtr (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve a value for a given PCD token.
+
+ Returns the Boolean value of the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the BOOLEAN.
+
+**/
+BOOLEAN
+EFIAPI
+LibPcdGetExBool (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ This function provides a means by which to retrieve the size of a given PCD token.
+
+ Returns the size of the token specified by TokenNumber and Guid.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates
+ which namespace to retrieve a value from.
+ @param[in] TokenNumber The PCD token number to retrieve a current value for.
+
+ @return Return the size.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetExSize (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 8-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet8S (
+ IN UINTN TokenNumber,
+ IN UINT8 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 16-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet16S (
+ IN UINTN TokenNumber,
+ IN UINT16 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 32-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet32S (
+ IN UINTN TokenNumber,
+ IN UINT32 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 64-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSet64S (
+ IN UINTN TokenNumber,
+ IN UINT64 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets a buffer for the token specified by TokenNumber to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than the maximum size
+ support by TokenNumber, then set SizeOfBuffer to the maximum size supported by
+ TokenNumber and return EFI_INVALID_PARAMETER to indicate that the set operation
+ was not actually performed.
+
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to the
+ maximum size supported by TokenName and EFI_INVALID_PARAMETER must be returned.
+
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in, out] SizeOfBuffer The size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetPtrS (
+ IN UINTN TokenNumber,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the boolean value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetBoolS (
+ IN UINTN TokenNumber,
+ IN BOOLEAN Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 8-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 8-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx8S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT8 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 16-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 16-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx16S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT16 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 32-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 32-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx32S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT32 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the 64-bit value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The 64-bit value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetEx64S (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN UINT64 Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets a buffer for the token specified by TokenNumber to the value specified by
+ Buffer and SizeOfBuffer. If SizeOfBuffer is greater than the maximum size
+ support by TokenNumber, then set SizeOfBuffer to the maximum size supported by
+ TokenNumber and return EFI_INVALID_PARAMETER to indicate that the set operation
+ was not actually performed.
+
+ If Guid is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[in] Guid Pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in, out] SizeOfBuffer The size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetExPtrS (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN OUT UINTN *SizeOfBuffer,
+ IN VOID *Buffer
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ This function provides a means by which to set a value for a given PCD token.
+
+ Sets the boolean value for the token specified by TokenNumber
+ to the value specified by Value.
+
+ If Guid is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that
+ designates which namespace to set a value from.
+ @param[in] TokenNumber The PCD token number to set a current value for.
+ @param[in] Value The boolean value to set.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPcdSetExBoolS (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ IN BOOLEAN Value
+ )
+{
+ ASSERT (FALSE);
+
+ return RETURN_INVALID_PARAMETER;
+}
+
+/**
+ Set up a notification function that is called when a specified token is set.
+
+ When the token specified by TokenNumber and Guid is set,
+ then notification function specified by NotificationFunction is called.
+ If Guid is NULL, then the default token space is used.
+
+ If NotificationFunction is NULL, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates which
+ namespace to set a value from. If NULL, then the default
+ token space is used.
+ @param[in] TokenNumber The PCD token number to monitor.
+ @param[in] NotificationFunction The function to call when the token
+ specified by Guid and TokenNumber is set.
+
+**/
+VOID
+EFIAPI
+LibPcdCallbackOnSet (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber,
+ IN PCD_CALLBACK NotificationFunction
+ )
+{
+ ASSERT (FALSE);
+}
+
+
+
+/**
+ Disable a notification function that was established with LibPcdCallbackonSet().
+
+ Disable a notification function that was previously established with LibPcdCallbackOnSet().
+
+ If NotificationFunction is NULL, then ASSERT().
+ If LibPcdCallbackOnSet() was not previously called with Guid, TokenNumber,
+ and NotificationFunction, then ASSERT().
+
+ @param[in] Guid Specify the GUID token space.
+ @param[in] TokenNumber Specify the token number.
+ @param[in] NotificationFunction The callback function to be unregistered.
+
+**/
+VOID
+EFIAPI
+LibPcdCancelCallback (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber,
+ IN PCD_CALLBACK NotificationFunction
+ )
+{
+ ASSERT (FALSE);
+}
+
+
+
+/**
+ Retrieves the next token in a token space.
+
+ Retrieves the next PCD token number from the token space specified by Guid.
+ If Guid is NULL, then the default token space is used. If TokenNumber is 0,
+ then the first token number is returned. Otherwise, the token number that
+ follows TokenNumber in the token space is returned. If TokenNumber is the last
+ token number in the token space, then 0 is returned.
+
+ If TokenNumber is not 0 and is not in the token space specified by Guid, then ASSERT().
+
+ @param[in] Guid The pointer to a 128-bit unique value that designates which namespace
+ to set a value from. If NULL, then the default token space is used.
+ @param[in] TokenNumber The previous PCD token number. If 0, then retrieves the first PCD
+ token number.
+
+ @return The next valid token number.
+
+**/
+UINTN
+EFIAPI
+LibPcdGetNextToken (
+ IN CONST GUID *Guid, OPTIONAL
+ IN UINTN TokenNumber
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
+
+
+/**
+ Used to retrieve the list of available PCD token space GUIDs.
+
+ Returns the PCD token space GUID that follows TokenSpaceGuid in the list of token spaces
+ in the platform.
+ If TokenSpaceGuid is NULL, then a pointer to the first PCD token spaces returned.
+ If TokenSpaceGuid is the last PCD token space GUID in the list, then NULL is returned.
+
+ @param TokenSpaceGuid The pointer to a PCD token space GUID.
+
+ @return The next valid token namespace.
+
+**/
+GUID *
+EFIAPI
+LibPcdGetNextTokenSpace (
+ IN CONST GUID *TokenSpaceGuid
+ )
+{
+ ASSERT (FALSE);
+
+ return NULL;
+}
+
+
+/**
+ Sets a value of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified by Buffer
+ and SizeOfBuffer. Buffer is returned. If SizeOfBuffer is greater than
+ MaximumDatumSize, then set SizeOfBuffer to MaximumDatumSize and return
+ NULL to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and NULL must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return Return the pointer to the buffer that was set.
+
+**/
+VOID *
+EFIAPI
+LibPatchPcdSetPtr (
+ OUT VOID *PatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ )
+{
+ ASSERT (PatchVariable != NULL);
+ ASSERT (SizeOfBuffer != NULL);
+
+ if (*SizeOfBuffer > 0) {
+ ASSERT (Buffer != NULL);
+ }
+
+ if ((*SizeOfBuffer > MaximumDatumSize) ||
+ (*SizeOfBuffer == MAX_ADDRESS)) {
+ *SizeOfBuffer = MaximumDatumSize;
+ return NULL;
+ }
+
+ CopyMem (PatchVariable, Buffer, *SizeOfBuffer);
+
+ return (VOID *) Buffer;
+}
+
+/**
+ Sets a value of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than MaximumDatumSize,
+ then set SizeOfBuffer to MaximumDatumSize and return RETURN_INVALID_PARAMETER
+ to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and RETURN_INVALID_PARAMETER must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPatchPcdSetPtrS (
+ OUT VOID *PatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ )
+{
+ ASSERT (PatchVariable != NULL);
+ ASSERT (SizeOfBuffer != NULL);
+
+ if (*SizeOfBuffer > 0) {
+ ASSERT (Buffer != NULL);
+ }
+
+ if ((*SizeOfBuffer > MaximumDatumSize) ||
+ (*SizeOfBuffer == MAX_ADDRESS)) {
+ *SizeOfBuffer = MaximumDatumSize;
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ CopyMem (PatchVariable, Buffer, *SizeOfBuffer);
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Sets a value and size of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified by Buffer
+ and SizeOfBuffer. Buffer is returned. If SizeOfBuffer is greater than
+ MaximumDatumSize, then set SizeOfBuffer to MaximumDatumSize and return
+ NULL to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and NULL must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfPatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[out] SizeOfPatchVariable A pointer to the size, in bytes, of PatchVariable.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return Return the pointer to the buffer been set.
+
+**/
+VOID *
+EFIAPI
+LibPatchPcdSetPtrAndSize (
+ OUT VOID *PatchVariable,
+ OUT UINTN *SizeOfPatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ )
+{
+ ASSERT (PatchVariable != NULL);
+ ASSERT (SizeOfPatchVariable != NULL);
+ ASSERT (SizeOfBuffer != NULL);
+
+ if (*SizeOfBuffer > 0) {
+ ASSERT (Buffer != NULL);
+ }
+
+ if ((*SizeOfBuffer > MaximumDatumSize) ||
+ (*SizeOfBuffer == MAX_ADDRESS)) {
+ *SizeOfBuffer = MaximumDatumSize;
+ return NULL;
+ }
+
+ CopyMem (PatchVariable, Buffer, *SizeOfBuffer);
+ *SizeOfPatchVariable = *SizeOfBuffer;
+
+ return (VOID *) Buffer;
+}
+
+/**
+ Sets a value and size of a patchable PCD entry that is type pointer.
+
+ Sets the PCD entry specified by PatchVariable to the value specified
+ by Buffer and SizeOfBuffer. If SizeOfBuffer is greater than MaximumDatumSize,
+ then set SizeOfBuffer to MaximumDatumSize and return RETURN_INVALID_PARAMETER
+ to indicate that the set operation was not actually performed.
+ If SizeOfBuffer is set to MAX_ADDRESS, then SizeOfBuffer must be set to
+ MaximumDatumSize and RETURN_INVALID_PARAMETER must be returned.
+
+ If PatchVariable is NULL, then ASSERT().
+ If SizeOfPatchVariable is NULL, then ASSERT().
+ If SizeOfBuffer is NULL, then ASSERT().
+ If SizeOfBuffer > 0 and Buffer is NULL, then ASSERT().
+
+ @param[out] PatchVariable A pointer to the global variable in a module that is
+ the target of the set operation.
+ @param[out] SizeOfPatchVariable A pointer to the size, in bytes, of PatchVariable.
+ @param[in] MaximumDatumSize The maximum size allowed for the PCD entry specified by PatchVariable.
+ @param[in, out] SizeOfBuffer A pointer to the size, in bytes, of Buffer.
+ @param[in] Buffer A pointer to the buffer to used to set the target variable.
+
+ @return The status of the set operation.
+
+**/
+RETURN_STATUS
+EFIAPI
+LibPatchPcdSetPtrAndSizeS (
+ OUT VOID *PatchVariable,
+ OUT UINTN *SizeOfPatchVariable,
+ IN UINTN MaximumDatumSize,
+ IN OUT UINTN *SizeOfBuffer,
+ IN CONST VOID *Buffer
+ )
+{
+ ASSERT (PatchVariable != NULL);
+ ASSERT (SizeOfPatchVariable != NULL);
+ ASSERT (SizeOfBuffer != NULL);
+
+ if (*SizeOfBuffer > 0) {
+ ASSERT (Buffer != NULL);
+ }
+
+ if ((*SizeOfBuffer > MaximumDatumSize) ||
+ (*SizeOfBuffer == MAX_ADDRESS)) {
+ *SizeOfBuffer = MaximumDatumSize;
+ return RETURN_INVALID_PARAMETER;
+ }
+
+ CopyMem (PatchVariable, Buffer, *SizeOfBuffer);
+ *SizeOfPatchVariable = *SizeOfBuffer;
+
+ return RETURN_SUCCESS;
+}
+
+/**
+ Retrieve additional information associated with a PCD token.
+
+ This includes information such as the type of value the TokenNumber is associated with as well as possible
+ human readable name that is associated with the token.
+
+ If TokenNumber is not in the default token space specified, then ASSERT().
+
+ @param[in] TokenNumber The PCD token number.
+ @param[out] PcdInfo The returned information associated with the requested TokenNumber.
+ The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
+**/
+VOID
+EFIAPI
+LibPcdGetInfo (
+ IN UINTN TokenNumber,
+ OUT PCD_INFO *PcdInfo
+ )
+{
+ ASSERT (FALSE);
+}
+
+/**
+ Retrieve additional information associated with a PCD token.
+
+ This includes information such as the type of value the TokenNumber is associated with as well as possible
+ human readable name that is associated with the token.
+
+ If TokenNumber is not in the token space specified by Guid, then ASSERT().
+
+ @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
+ @param[in] TokenNumber The PCD token number.
+ @param[out] PcdInfo The returned information associated with the requested TokenNumber.
+ The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
+**/
+VOID
+EFIAPI
+LibPcdGetInfoEx (
+ IN CONST GUID *Guid,
+ IN UINTN TokenNumber,
+ OUT PCD_INFO *PcdInfo
+ )
+{
+ ASSERT (FALSE);
+}
+
+/**
+ Retrieve the currently set SKU Id.
+
+ @return The currently set SKU Id. If the platform has not set at a SKU Id, then the
+ default SKU Id value of 0 is returned. If the platform has set a SKU Id, then the currently set SKU
+ Id is returned.
+**/
+UINTN
+EFIAPI
+LibPcdGetSku (
+ VOID
+ )
+{
+ ASSERT (FALSE);
+
+ return 0;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiBootServicesTableLib.c b/efi_memtest/memtest86+/efi/Include/src/UefiBootServicesTableLib.c
new file mode 100644
index 0000000..4fb6bc8
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiBootServicesTableLib.c
@@ -0,0 +1,60 @@
+/** @file
+ This library retrieve the EFI_BOOT_SERVICES pointer from EFI system table in
+ library's constructor.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include <Uefi.h>
+
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/DebugLib.h>
+
+EFI_HANDLE gImageHandle = NULL;
+EFI_SYSTEM_TABLE *gST = NULL;
+EFI_BOOT_SERVICES *gBS = NULL;
+
+/**
+ The constructor function caches the pointer of Boot Services Table.
+
+ The constructor function caches the pointer of Boot Services Table through System Table.
+ It will ASSERT() if the pointer of System Table is NULL.
+ It will ASSERT() if the pointer of Boot Services Table is NULL.
+ It will always return EFI_SUCCESS.
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The constructor always returns EFI_SUCCESS.
+
+**/
+EFI_STATUS
+EFIAPI
+UefiBootServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ //
+ // Cache the Image Handle
+ //
+ gImageHandle = ImageHandle;
+ ASSERT (gImageHandle != NULL);
+
+ //
+ // Cache pointer to the EFI System Table
+ //
+ gST = SystemTable;
+ ASSERT (gST != NULL);
+
+ //
+ // Cache pointer to the EFI Boot Services Table
+ //
+ gBS = SystemTable->BootServices;
+ ASSERT (gBS != NULL);
+
+ return EFI_SUCCESS;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLib.c b/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLib.c
new file mode 100644
index 0000000..6140bbd
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLib.c
@@ -0,0 +1,377 @@
+/** @file
+ UEFI Debug Lib that sends messages to the Standard Error Device in the EFI System Table.
+
+ Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include <Uefi.h>
+
+#include <Library/DebugLib.h>
+#include <Library/PrintLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugPrintErrorLevelLib.h>
+
+#include "Efi_Defs.h"
+
+//
+// Define the maximum debug and assert message length that this library supports
+//
+#define MAX_DEBUG_MESSAGE_LENGTH 0x100
+
+
+//
+// VA_LIST can not initialize to NULL for all compiler, so we use this to
+// indicate a null VA_LIST
+//
+VA_LIST mVaListNull;
+
+extern BOOLEAN mPostEBS;
+extern EFI_SYSTEM_TABLE *mDebugST;
+
+/**
+ Prints a debug message to the debug output device if the specified error level is enabled.
+
+ If any bit in ErrorLevel is also set in DebugPrintErrorLevelLib function
+ GetDebugPrintErrorLevel (), then print the message specified by Format and the
+ associated variable argument list to the debug output device.
+
+ If Format is NULL, then ASSERT().
+
+ @param ErrorLevel The error level of the debug message.
+ @param Format The format string for the debug message to print.
+ @param ... The variable argument list whose contents are accessed
+ based on the format string specified by Format.
+
+**/
+VOID
+EFIAPI
+DebugPrint (
+ IN UINTN ErrorLevel,
+ IN CONST CHAR8 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+
+ VA_START (Marker, Format);
+ DebugVPrint (ErrorLevel, Format, Marker);
+ VA_END (Marker);
+}
+
+
+/**
+ Prints a debug message to the debug output device if the specified
+ error level is enabled base on Null-terminated format string and a
+ VA_LIST argument list or a BASE_LIST argument list.
+
+ If any bit in ErrorLevel is also set in DebugPrintErrorLevelLib function
+ GetDebugPrintErrorLevel (), then print the message specified by Format and
+ the associated variable argument list to the debug output device.
+
+ If Format is NULL, then ASSERT().
+
+ @param ErrorLevel The error level of the debug message.
+ @param Format Format string for the debug message to print.
+ @param VaListMarker VA_LIST marker for the variable argument list.
+ @param BaseListMarker BASE_LIST marker for the variable argument list.
+
+**/
+VOID
+DebugPrintMarker (
+ IN UINTN ErrorLevel,
+ IN CONST CHAR8 *Format,
+ IN VA_LIST VaListMarker,
+ IN BASE_LIST BaseListMarker
+ )
+{
+ CHAR16 Buffer[MAX_DEBUG_MESSAGE_LENGTH];
+
+ if (!mPostEBS) {
+ //
+ // If Format is NULL, then ASSERT().
+ //
+ ASSERT (Format != NULL);
+
+ //
+ // Check driver debug mask value and global mask
+ //
+ if ((ErrorLevel & GetDebugPrintErrorLevel ()) == 0) {
+ return;
+ }
+
+ //
+ // Convert the DEBUG() message to a Unicode String
+ //
+ if (BaseListMarker == NULL) {
+ UnicodeVSPrintAsciiFormat (Buffer, sizeof (Buffer), Format, VaListMarker);
+ } else {
+ UnicodeBSPrintAsciiFormat (Buffer, sizeof (Buffer), Format, BaseListMarker);
+ }
+
+ //
+ // Send the print string to the Standard Error device
+ //
+ if ((mDebugST != NULL) && (mDebugST->StdErr != NULL)) {
+ mDebugST->StdErr->OutputString (mDebugST->StdErr, Buffer);
+ }
+ }
+}
+
+
+/**
+ Prints a debug message to the debug output device if the specified
+ error level is enabled.
+
+ If any bit in ErrorLevel is also set in DebugPrintErrorLevelLib function
+ GetDebugPrintErrorLevel (), then print the message specified by Format and
+ the associated variable argument list to the debug output device.
+
+ If Format is NULL, then ASSERT().
+
+ @param ErrorLevel The error level of the debug message.
+ @param Format Format string for the debug message to print.
+ @param VaListMarker VA_LIST marker for the variable argument list.
+
+**/
+VOID
+EFIAPI
+DebugVPrint (
+ IN UINTN ErrorLevel,
+ IN CONST CHAR8 *Format,
+ IN VA_LIST VaListMarker
+ )
+{
+ DebugPrintMarker (ErrorLevel, Format, VaListMarker, NULL);
+}
+
+
+/**
+ Prints a debug message to the debug output device if the specified
+ error level is enabled.
+ This function use BASE_LIST which would provide a more compatible
+ service than VA_LIST.
+
+ If any bit in ErrorLevel is also set in DebugPrintErrorLevelLib function
+ GetDebugPrintErrorLevel (), then print the message specified by Format and
+ the associated variable argument list to the debug output device.
+
+ If Format is NULL, then ASSERT().
+
+ @param ErrorLevel The error level of the debug message.
+ @param Format Format string for the debug message to print.
+ @param BaseListMarker BASE_LIST marker for the variable argument list.
+
+**/
+VOID
+EFIAPI
+DebugBPrint (
+ IN UINTN ErrorLevel,
+ IN CONST CHAR8 *Format,
+ IN BASE_LIST BaseListMarker
+ )
+{
+ DebugPrintMarker (ErrorLevel, Format, mVaListNull, BaseListMarker);
+}
+
+
+/**
+ Prints an assert message containing a filename, line number, and description.
+ This may be followed by a breakpoint or a dead loop.
+
+ Print a message of the form "ASSERT <FileName>(<LineNumber>): <Description>\n"
+ to the debug output device. If DEBUG_PROPERTY_ASSERT_BREAKPOINT_ENABLED bit of
+ PcdDebugProperyMask is set then CpuBreakpoint() is called. Otherwise, if
+ DEBUG_PROPERTY_ASSERT_DEADLOOP_ENABLED bit of PcdDebugProperyMask is set then
+ CpuDeadLoop() is called. If neither of these bits are set, then this function
+ returns immediately after the message is printed to the debug output device.
+ DebugAssert() must actively prevent recursion. If DebugAssert() is called while
+ processing another DebugAssert(), then DebugAssert() must return immediately.
+
+ If FileName is NULL, then a <FileName> string of "(NULL) Filename" is printed.
+ If Description is NULL, then a <Description> string of "(NULL) Description" is printed.
+
+ @param FileName The pointer to the name of the source file that generated
+ the assert condition.
+ @param LineNumber The line number in the source file that generated the
+ assert condition
+ @param Description The pointer to the description of the assert condition.
+
+**/
+VOID
+EFIAPI
+DebugAssert (
+ IN CONST CHAR8 *FileName,
+ IN UINTN LineNumber,
+ IN CONST CHAR8 *Description
+ )
+{
+ CHAR16 Buffer[MAX_DEBUG_MESSAGE_LENGTH];
+
+ if (!mPostEBS) {
+ //
+ // Generate the ASSERT() message in Unicode format
+ //
+ UnicodeSPrintAsciiFormat (
+ Buffer,
+ sizeof (Buffer),
+ "ASSERT [%a] %a(%d): %a\n",
+ gEfiCallerBaseName,
+ FileName,
+ LineNumber,
+ Description
+ );
+
+ //
+ // Send the print string to the Standard Error device
+ //
+ if ((mDebugST != NULL) && (mDebugST->StdErr != NULL)) {
+ mDebugST->StdErr->OutputString (mDebugST->StdErr, Buffer);
+ }
+
+ //
+ // Generate a Breakpoint, DeadLoop, or NOP based on PCD settings
+ //
+ if ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_ASSERT_BREAKPOINT_ENABLED) != 0) {
+ CpuBreakpoint ();
+ } else if ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_ASSERT_DEADLOOP_ENABLED) != 0) {
+ CpuDeadLoop ();
+ }
+ }
+}
+
+
+/**
+ Fills a target buffer with PcdDebugClearMemoryValue, and returns the target buffer.
+
+ This function fills Length bytes of Buffer with the value specified by
+ PcdDebugClearMemoryValue, and returns Buffer.
+
+ If Buffer is NULL, then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ @param Buffer The pointer to the target buffer to be filled with PcdDebugClearMemoryValue.
+ @param Length The number of bytes in Buffer to fill with zeros PcdDebugClearMemoryValue.
+
+ @return Buffer The pointer to the target buffer filled with PcdDebugClearMemoryValue.
+
+**/
+VOID *
+EFIAPI
+DebugClearMemory (
+ OUT VOID *Buffer,
+ IN UINTN Length
+ )
+{
+ //
+ // If Buffer is NULL, then ASSERT().
+ //
+ ASSERT (Buffer != NULL);
+
+ //
+ // SetMem() checks for the the ASSERT() condition on Length and returns Buffer
+ //
+ return SetMem (Buffer, Length, PcdGet8(PcdDebugClearMemoryValue));
+}
+
+
+/**
+ Returns TRUE if ASSERT() macros are enabled.
+
+ This function returns TRUE if the DEBUG_PROPERTY_DEBUG_ASSERT_ENABLED bit of
+ PcdDebugProperyMask is set. Otherwise FALSE is returned.
+
+ @retval TRUE The DEBUG_PROPERTY_DEBUG_ASSERT_ENABLED bit of PcdDebugProperyMask is set.
+ @retval FALSE The DEBUG_PROPERTY_DEBUG_ASSERT_ENABLED bit of PcdDebugProperyMask is clear.
+
+**/
+BOOLEAN
+EFIAPI
+DebugAssertEnabled (
+ VOID
+ )
+{
+ return (BOOLEAN) ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_DEBUG_ASSERT_ENABLED) != 0);
+}
+
+
+/**
+ Returns TRUE if DEBUG() macros are enabled.
+
+ This function returns TRUE if the DEBUG_PROPERTY_DEBUG_PRINT_ENABLED bit of
+ PcdDebugProperyMask is set. Otherwise FALSE is returned.
+
+ @retval TRUE The DEBUG_PROPERTY_DEBUG_PRINT_ENABLED bit of PcdDebugProperyMask is set.
+ @retval FALSE The DEBUG_PROPERTY_DEBUG_PRINT_ENABLED bit of PcdDebugProperyMask is clear.
+
+**/
+BOOLEAN
+EFIAPI
+DebugPrintEnabled (
+ VOID
+ )
+{
+ return (BOOLEAN) ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_DEBUG_PRINT_ENABLED) != 0);
+}
+
+
+/**
+ Returns TRUE if DEBUG_CODE() macros are enabled.
+
+ This function returns TRUE if the DEBUG_PROPERTY_DEBUG_CODE_ENABLED bit of
+ PcdDebugProperyMask is set. Otherwise FALSE is returned.
+
+ @retval TRUE The DEBUG_PROPERTY_DEBUG_CODE_ENABLED bit of PcdDebugProperyMask is set.
+ @retval FALSE The DEBUG_PROPERTY_DEBUG_CODE_ENABLED bit of PcdDebugProperyMask is clear.
+
+**/
+BOOLEAN
+EFIAPI
+DebugCodeEnabled (
+ VOID
+ )
+{
+ return (BOOLEAN) ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_DEBUG_CODE_ENABLED) != 0);
+}
+
+
+/**
+ Returns TRUE if DEBUG_CLEAR_MEMORY() macro is enabled.
+
+ This function returns TRUE if the DEBUG_PROPERTY_CLEAR_MEMORY_ENABLED bit of
+ PcdDebugProperyMask is set. Otherwise FALSE is returned.
+
+ @retval TRUE The DEBUG_PROPERTY_CLEAR_MEMORY_ENABLED bit of PcdDebugProperyMask is set.
+ @retval FALSE The DEBUG_PROPERTY_CLEAR_MEMORY_ENABLED bit of PcdDebugProperyMask is clear.
+
+**/
+BOOLEAN
+EFIAPI
+DebugClearMemoryEnabled (
+ VOID
+ )
+{
+ return (BOOLEAN) ((PcdGet8(PcdDebugPropertyMask) & DEBUG_PROPERTY_CLEAR_MEMORY_ENABLED) != 0);
+}
+
+/**
+ Returns TRUE if any one of the bit is set both in ErrorLevel and PcdFixedDebugPrintErrorLevel.
+
+ This function compares the bit mask of ErrorLevel and PcdFixedDebugPrintErrorLevel.
+
+ @retval TRUE Current ErrorLevel is supported.
+ @retval FALSE Current ErrorLevel is not supported.
+
+**/
+BOOLEAN
+EFIAPI
+DebugPrintLevelEnabled (
+ IN CONST UINTN ErrorLevel
+ )
+{
+ return (BOOLEAN) ((ErrorLevel & PcdGet32(PcdFixedDebugPrintErrorLevel)) != 0);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLibConstructor.c b/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLibConstructor.c
new file mode 100644
index 0000000..b4ac17c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDebugLibStdErr/DebugLibConstructor.c
@@ -0,0 +1,99 @@
+/** @file
+ UEFI Dxe DebugLib constructor that prevent some debug service after ExitBootServices event,
+ because some pointer is nulled at that phase.
+
+ Copyright (c) 2018, Microsoft Corporation
+ Copyright (c) 2015 - 2019, Intel Corporation. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+
+//
+// BOOLEAN value to indicate if it is at the post ExitBootServices pahse
+//
+BOOLEAN mPostEBS = FALSE;
+
+static EFI_EVENT mExitBootServicesEvent;
+
+//
+// Pointer to SystemTable
+// This library instance may have a cycle consume with UefiBootServicesTableLib
+// because of the constructors.
+//
+EFI_SYSTEM_TABLE *mDebugST;
+
+/**
+ This routine sets the mPostEBS for exit boot servies true
+ to prevent DebugPort protocol dereferences when the pointer is nulled.
+
+ @param Event Event whose notification function is being invoked.
+ @param Context Pointer to the notification function's context.
+
+**/
+VOID
+EFIAPI
+ExitBootServicesCallback (
+ EFI_EVENT Event,
+ VOID* Context
+ )
+{
+ mPostEBS = TRUE;
+ return;
+}
+
+/**
+ The constructor gets the pointers to the system table.
+ And create a event to indicate it is after ExitBootServices.
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The constructor always returns EFI_SUCCESS.
+
+**/
+EFI_STATUS
+EFIAPI
+DxeDebugLibConstructor(
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ mDebugST = SystemTable;
+
+ SystemTable->BootServices->CreateEvent (
+ EVT_SIGNAL_EXIT_BOOT_SERVICES,
+ TPL_NOTIFY,
+ ExitBootServicesCallback,
+ NULL,
+ &mExitBootServicesEvent
+ );
+
+ return EFI_SUCCESS;
+}
+
+/**
+ The destructor closes Exit Boot Services Event.
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The destructor always returns EFI_SUCCESS.
+
+**/
+EFI_STATUS
+EFIAPI
+DxeDebugLibDestructor(
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ if (mExitBootServicesEvent != NULL) {
+ SystemTable->BootServices->CloseEvent (mExitBootServicesEvent);
+ }
+
+ return EFI_SUCCESS;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathFromText.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathFromText.c
new file mode 100644
index 0000000..1515d2d
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathFromText.c
@@ -0,0 +1,3666 @@
+/** @file
+ DevicePathFromText protocol as defined in the UEFI 2.0 specification.
+
+Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiDevicePathLib.h"
+
+/**
+
+ Duplicates a string.
+
+ @param Src Source string.
+
+ @return The duplicated string.
+
+**/
+CHAR16 *
+UefiDevicePathLibStrDuplicate (
+ IN CONST CHAR16 *Src
+ )
+{
+ return AllocateCopyPool (StrSize (Src), Src);
+}
+
+/**
+
+ Get parameter in a pair of parentheses follow the given node name.
+ For example, given the "Pci(0,1)" and NodeName "Pci", it returns "0,1".
+
+ @param Str Device Path Text.
+ @param NodeName Name of the node.
+
+ @return Parameter text for the node.
+
+**/
+CHAR16 *
+GetParamByNodeName (
+ IN CHAR16 *Str,
+ IN CHAR16 *NodeName
+ )
+{
+ CHAR16 *ParamStr;
+ CHAR16 *StrPointer;
+ UINTN NodeNameLength;
+ UINTN ParameterLength;
+
+ //
+ // Check whether the node name matchs
+ //
+ NodeNameLength = StrLen (NodeName);
+ if (StrnCmp (Str, NodeName, NodeNameLength) != 0) {
+ return NULL;
+ }
+
+ ParamStr = Str + NodeNameLength;
+ if (!IS_LEFT_PARENTH (*ParamStr)) {
+ return NULL;
+ }
+
+ //
+ // Skip the found '(' and find first occurrence of ')'
+ //
+ ParamStr++;
+ ParameterLength = 0;
+ StrPointer = ParamStr;
+ while (!IS_NULL (*StrPointer)) {
+ if (IS_RIGHT_PARENTH (*StrPointer)) {
+ break;
+ }
+ StrPointer++;
+ ParameterLength++;
+ }
+ if (IS_NULL (*StrPointer)) {
+ //
+ // ')' not found
+ //
+ return NULL;
+ }
+
+ ParamStr = AllocateCopyPool ((ParameterLength + 1) * sizeof (CHAR16), ParamStr);
+ if (ParamStr == NULL) {
+ return NULL;
+ }
+ //
+ // Terminate the parameter string
+ //
+ ParamStr[ParameterLength] = L'\0';
+
+ return ParamStr;
+}
+
+/**
+ Gets current sub-string from a string list, before return
+ the list header is moved to next sub-string. The sub-string is separated
+ by the specified character. For example, the separator is ',', the string
+ list is "2,0,3", it returns "2", the remain list move to "0,3"
+
+ @param List A string list separated by the specified separator
+ @param Separator The separator character
+
+ @return A pointer to the current sub-string
+
+**/
+CHAR16 *
+SplitStr (
+ IN OUT CHAR16 **List,
+ IN CHAR16 Separator
+ )
+{
+ CHAR16 *Str;
+ CHAR16 *ReturnStr;
+
+ Str = *List;
+ ReturnStr = Str;
+
+ if (IS_NULL (*Str)) {
+ return ReturnStr;
+ }
+
+ //
+ // Find first occurrence of the separator
+ //
+ while (!IS_NULL (*Str)) {
+ if (*Str == Separator) {
+ break;
+ }
+ Str++;
+ }
+
+ if (*Str == Separator) {
+ //
+ // Find a sub-string, terminate it
+ //
+ *Str = L'\0';
+ Str++;
+ }
+
+ //
+ // Move to next sub-string
+ //
+ *List = Str;
+
+ return ReturnStr;
+}
+
+/**
+ Gets the next parameter string from the list.
+
+ @param List A string list separated by the specified separator
+
+ @return A pointer to the current sub-string
+
+**/
+CHAR16 *
+GetNextParamStr (
+ IN OUT CHAR16 **List
+ )
+{
+ //
+ // The separator is comma
+ //
+ return SplitStr (List, L',');
+}
+
+/**
+ Get one device node from entire device path text.
+
+ @param DevicePath On input, the current Device Path node; on output, the next device path node
+ @param IsInstanceEnd This node is the end of a device path instance
+
+ @return A device node text or NULL if no more device node available
+
+**/
+CHAR16 *
+GetNextDeviceNodeStr (
+ IN OUT CHAR16 **DevicePath,
+ OUT BOOLEAN *IsInstanceEnd
+ )
+{
+ CHAR16 *Str;
+ CHAR16 *ReturnStr;
+ UINTN ParenthesesStack;
+
+ Str = *DevicePath;
+ if (IS_NULL (*Str)) {
+ return NULL;
+ }
+
+ //
+ // Skip the leading '/', '(', ')' and ','
+ //
+ while (!IS_NULL (*Str)) {
+ if (!IS_SLASH (*Str) &&
+ !IS_COMMA (*Str) &&
+ !IS_LEFT_PARENTH (*Str) &&
+ !IS_RIGHT_PARENTH (*Str)) {
+ break;
+ }
+ Str++;
+ }
+
+ ReturnStr = Str;
+
+ //
+ // Scan for the separator of this device node, '/' or ','
+ //
+ ParenthesesStack = 0;
+ while (!IS_NULL (*Str)) {
+ if ((IS_COMMA (*Str) || IS_SLASH (*Str)) && (ParenthesesStack == 0)) {
+ break;
+ }
+
+ if (IS_LEFT_PARENTH (*Str)) {
+ ParenthesesStack++;
+ } else if (IS_RIGHT_PARENTH (*Str)) {
+ ParenthesesStack--;
+ }
+
+ Str++;
+ }
+
+ if (ParenthesesStack != 0) {
+ //
+ // The '(' doesn't pair with ')', invalid device path text
+ //
+ return NULL;
+ }
+
+ if (IS_COMMA (*Str)) {
+ *IsInstanceEnd = TRUE;
+ *Str = L'\0';
+ Str++;
+ } else {
+ *IsInstanceEnd = FALSE;
+ if (!IS_NULL (*Str)) {
+ *Str = L'\0';
+ Str++;
+ }
+ }
+
+ *DevicePath = Str;
+
+ return ReturnStr;
+}
+
+
+/**
+ Return whether the integer string is a hex string.
+
+ @param Str The integer string
+
+ @retval TRUE Hex string
+ @retval FALSE Decimal string
+
+**/
+BOOLEAN
+IsHexStr (
+ IN CHAR16 *Str
+ )
+{
+ //
+ // skip preceeding white space
+ //
+ while ((*Str != 0) && *Str == L' ') {
+ Str ++;
+ }
+ //
+ // skip preceeding zeros
+ //
+ while ((*Str != 0) && *Str == L'0') {
+ Str ++;
+ }
+
+ return (BOOLEAN) (*Str == L'x' || *Str == L'X');
+}
+
+/**
+
+ Convert integer string to uint.
+
+ @param Str The integer string. If leading with "0x" or "0X", it's hexadecimal.
+
+ @return A UINTN value represented by Str
+
+**/
+UINTN
+Strtoi (
+ IN CHAR16 *Str
+ )
+{
+ if (IsHexStr (Str)) {
+ return StrHexToUintn (Str);
+ } else {
+ return StrDecimalToUintn (Str);
+ }
+}
+
+/**
+
+ Convert integer string to 64 bit data.
+
+ @param Str The integer string. If leading with "0x" or "0X", it's hexadecimal.
+ @param Data A pointer to the UINT64 value represented by Str
+
+**/
+VOID
+Strtoi64 (
+ IN CHAR16 *Str,
+ OUT UINT64 *Data
+ )
+{
+ if (IsHexStr (Str)) {
+ *Data = StrHexToUint64 (Str);
+ } else {
+ *Data = StrDecimalToUint64 (Str);
+ }
+}
+
+/**
+ Converts a Unicode string to ASCII string.
+
+ @param Str The equivalent Unicode string
+ @param AsciiStr On input, it points to destination ASCII string buffer; on output, it points
+ to the next ASCII string next to it
+
+**/
+VOID
+StrToAscii (
+ IN CHAR16 *Str,
+ IN OUT CHAR8 **AsciiStr
+ )
+{
+ CHAR8 *Dest;
+
+ Dest = *AsciiStr;
+ while (!IS_NULL (*Str)) {
+ *(Dest++) = (CHAR8) *(Str++);
+ }
+ *Dest = 0;
+
+ //
+ // Return the string next to it
+ //
+ *AsciiStr = Dest + 1;
+}
+
+/**
+ Converts a generic text device path node to device path structure.
+
+ @param Type The type of the device path node.
+ @param TextDeviceNode The input text device path node.
+
+ @return A pointer to device path structure.
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextGenericPath (
+ IN UINT8 Type,
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *Node;
+ CHAR16 *SubtypeStr;
+ CHAR16 *DataStr;
+ UINTN DataLength;
+
+ SubtypeStr = GetNextParamStr (&TextDeviceNode);
+ DataStr = GetNextParamStr (&TextDeviceNode);
+
+ if (DataStr == NULL) {
+ DataLength = 0;
+ } else {
+ DataLength = StrLen (DataStr) / 2;
+ }
+ Node = CreateDeviceNode (
+ Type,
+ (UINT8) Strtoi (SubtypeStr),
+ (UINT16) (sizeof (EFI_DEVICE_PATH_PROTOCOL) + DataLength)
+ );
+
+ StrHexToBytes (DataStr, DataLength * 2, (UINT8 *) (Node + 1), DataLength);
+ return Node;
+}
+
+/**
+ Converts a generic text device path node to device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *TypeStr;
+
+ TypeStr = GetNextParamStr (&TextDeviceNode);
+
+ return DevPathFromTextGenericPath ((UINT8) Strtoi (TypeStr), TextDeviceNode);
+}
+
+/**
+ Converts a generic hardware text device path node to Hardware device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to Hardware device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextHardwarePath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return DevPathFromTextGenericPath (HARDWARE_DEVICE_PATH, TextDeviceNode);
+}
+
+/**
+ Converts a text device path node to Hardware PCI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to Hardware PCI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPci (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *FunctionStr;
+ CHAR16 *DeviceStr;
+ PCI_DEVICE_PATH *Pci;
+
+ DeviceStr = GetNextParamStr (&TextDeviceNode);
+ FunctionStr = GetNextParamStr (&TextDeviceNode);
+ Pci = (PCI_DEVICE_PATH *) CreateDeviceNode (
+ HARDWARE_DEVICE_PATH,
+ HW_PCI_DP,
+ (UINT16) sizeof (PCI_DEVICE_PATH)
+ );
+
+ Pci->Function = (UINT8) Strtoi (FunctionStr);
+ Pci->Device = (UINT8) Strtoi (DeviceStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Pci;
+}
+
+/**
+ Converts a text device path node to Hardware PC card device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to Hardware PC card device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPcCard (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *FunctionNumberStr;
+ PCCARD_DEVICE_PATH *Pccard;
+
+ FunctionNumberStr = GetNextParamStr (&TextDeviceNode);
+ Pccard = (PCCARD_DEVICE_PATH *) CreateDeviceNode (
+ HARDWARE_DEVICE_PATH,
+ HW_PCCARD_DP,
+ (UINT16) sizeof (PCCARD_DEVICE_PATH)
+ );
+
+ Pccard->FunctionNumber = (UINT8) Strtoi (FunctionNumberStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Pccard;
+}
+
+/**
+ Converts a text device path node to Hardware memory map device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to Hardware memory map device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextMemoryMapped (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *MemoryTypeStr;
+ CHAR16 *StartingAddressStr;
+ CHAR16 *EndingAddressStr;
+ MEMMAP_DEVICE_PATH *MemMap;
+
+ MemoryTypeStr = GetNextParamStr (&TextDeviceNode);
+ StartingAddressStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddressStr = GetNextParamStr (&TextDeviceNode);
+ MemMap = (MEMMAP_DEVICE_PATH *) CreateDeviceNode (
+ HARDWARE_DEVICE_PATH,
+ HW_MEMMAP_DP,
+ (UINT16) sizeof (MEMMAP_DEVICE_PATH)
+ );
+
+ MemMap->MemoryType = (UINT32) Strtoi (MemoryTypeStr);
+ Strtoi64 (StartingAddressStr, &MemMap->StartingAddress);
+ Strtoi64 (EndingAddressStr, &MemMap->EndingAddress);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) MemMap;
+}
+
+/**
+ Converts a text device path node to Vendor device path structure based on the input Type
+ and SubType.
+
+ @param TextDeviceNode The input Text device path node.
+ @param Type The type of device path node.
+ @param SubType The subtype of device path node.
+
+ @return A pointer to the newly-created Vendor device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+ConvertFromTextVendor (
+ IN CHAR16 *TextDeviceNode,
+ IN UINT8 Type,
+ IN UINT8 SubType
+ )
+{
+ CHAR16 *GuidStr;
+ CHAR16 *DataStr;
+ UINTN Length;
+ VENDOR_DEVICE_PATH *Vendor;
+
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+
+ DataStr = GetNextParamStr (&TextDeviceNode);
+ Length = StrLen (DataStr);
+ //
+ // Two hex characters make up 1 buffer byte
+ //
+ Length = (Length + 1) / 2;
+
+ Vendor = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ Type,
+ SubType,
+ (UINT16) (sizeof (VENDOR_DEVICE_PATH) + Length)
+ );
+
+ StrToGuid (GuidStr, &Vendor->Guid);
+ StrHexToBytes (DataStr, Length * 2, (UINT8 *) (Vendor + 1), Length);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vendor;
+}
+
+/**
+ Converts a text device path node to Vendor Hardware device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor Hardware device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenHw (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextVendor (
+ TextDeviceNode,
+ HARDWARE_DEVICE_PATH,
+ HW_VENDOR_DP
+ );
+}
+
+/**
+ Converts a text device path node to Hardware Controller device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Hardware Controller device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextCtrl (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *ControllerStr;
+ CONTROLLER_DEVICE_PATH *Controller;
+
+ ControllerStr = GetNextParamStr (&TextDeviceNode);
+ Controller = (CONTROLLER_DEVICE_PATH *) CreateDeviceNode (
+ HARDWARE_DEVICE_PATH,
+ HW_CONTROLLER_DP,
+ (UINT16) sizeof (CONTROLLER_DEVICE_PATH)
+ );
+ Controller->ControllerNumber = (UINT32) Strtoi (ControllerStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Controller;
+}
+
+/**
+ Converts a text device path node to BMC device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created BMC device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextBmc (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *InterfaceTypeStr;
+ CHAR16 *BaseAddressStr;
+ BMC_DEVICE_PATH *BmcDp;
+
+ InterfaceTypeStr = GetNextParamStr (&TextDeviceNode);
+ BaseAddressStr = GetNextParamStr (&TextDeviceNode);
+ BmcDp = (BMC_DEVICE_PATH *) CreateDeviceNode (
+ HARDWARE_DEVICE_PATH,
+ HW_BMC_DP,
+ (UINT16) sizeof (BMC_DEVICE_PATH)
+ );
+
+ BmcDp->InterfaceType = (UINT8) Strtoi (InterfaceTypeStr);
+ WriteUnaligned64 (
+ (UINT64 *) (&BmcDp->BaseAddress),
+ StrHexToUint64 (BaseAddressStr)
+ );
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) BmcDp;
+}
+
+/**
+ Converts a generic ACPI text device path node to ACPI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to ACPI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAcpiPath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return DevPathFromTextGenericPath (ACPI_DEVICE_PATH, TextDeviceNode);
+}
+
+/**
+ Converts a string to EisaId.
+
+ @param Text The input string.
+
+ @return UINT32 EISA ID.
+**/
+UINT32
+EisaIdFromText (
+ IN CHAR16 *Text
+ )
+{
+ return (((Text[0] - 'A' + 1) & 0x1f) << 10)
+ + (((Text[1] - 'A' + 1) & 0x1f) << 5)
+ + (((Text[2] - 'A' + 1) & 0x1f) << 0)
+ + (UINT32) (StrHexToUintn (&Text[3]) << 16)
+ ;
+}
+
+/**
+ Converts a text device path node to ACPI HID device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created ACPI HID device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAcpi (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *HIDStr;
+ CHAR16 *UIDStr;
+ ACPI_HID_DEVICE_PATH *Acpi;
+
+ HIDStr = GetNextParamStr (&TextDeviceNode);
+ UIDStr = GetNextParamStr (&TextDeviceNode);
+ Acpi = (ACPI_HID_DEVICE_PATH *) CreateDeviceNode (
+ ACPI_DEVICE_PATH,
+ ACPI_DP,
+ (UINT16) sizeof (ACPI_HID_DEVICE_PATH)
+ );
+
+ Acpi->HID = EisaIdFromText (HIDStr);
+ Acpi->UID = (UINT32) Strtoi (UIDStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Acpi;
+}
+
+/**
+ Converts a text device path node to ACPI HID device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+ @param PnPId The input plug and play identification.
+
+ @return A pointer to the newly-created ACPI HID device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+ConvertFromTextAcpi (
+ IN CHAR16 *TextDeviceNode,
+ IN UINT32 PnPId
+ )
+{
+ CHAR16 *UIDStr;
+ ACPI_HID_DEVICE_PATH *Acpi;
+
+ UIDStr = GetNextParamStr (&TextDeviceNode);
+ Acpi = (ACPI_HID_DEVICE_PATH *) CreateDeviceNode (
+ ACPI_DEVICE_PATH,
+ ACPI_DP,
+ (UINT16) sizeof (ACPI_HID_DEVICE_PATH)
+ );
+
+ Acpi->HID = EFI_PNP_ID (PnPId);
+ Acpi->UID = (UINT32) Strtoi (UIDStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Acpi;
+}
+
+/**
+ Converts a text device path node to PCI root device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created PCI root device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPciRoot (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0a03);
+}
+
+/**
+ Converts a text device path node to PCIE root device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created PCIE root device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPcieRoot (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0a08);
+}
+
+/**
+ Converts a text device path node to Floppy device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Floppy device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFloppy (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0604);
+}
+
+/**
+ Converts a text device path node to Keyboard device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Keyboard device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextKeyboard (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0301);
+}
+
+/**
+ Converts a text device path node to Serial device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Serial device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextSerial (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0501);
+}
+
+/**
+ Converts a text device path node to Parallel Port device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Parallel Port device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextParallelPort (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextAcpi (TextDeviceNode, 0x0401);
+}
+
+/**
+ Converts a text device path node to ACPI extension device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created ACPI extension device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAcpiEx (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *HIDStr;
+ CHAR16 *CIDStr;
+ CHAR16 *UIDStr;
+ CHAR16 *HIDSTRStr;
+ CHAR16 *CIDSTRStr;
+ CHAR16 *UIDSTRStr;
+ CHAR8 *AsciiStr;
+ UINT16 Length;
+ ACPI_EXTENDED_HID_DEVICE_PATH *AcpiEx;
+
+ HIDStr = GetNextParamStr (&TextDeviceNode);
+ CIDStr = GetNextParamStr (&TextDeviceNode);
+ UIDStr = GetNextParamStr (&TextDeviceNode);
+ HIDSTRStr = GetNextParamStr (&TextDeviceNode);
+ CIDSTRStr = GetNextParamStr (&TextDeviceNode);
+ UIDSTRStr = GetNextParamStr (&TextDeviceNode);
+
+ Length = (UINT16) (sizeof (ACPI_EXTENDED_HID_DEVICE_PATH) + StrLen (HIDSTRStr) + 1);
+ Length = (UINT16) (Length + StrLen (UIDSTRStr) + 1);
+ Length = (UINT16) (Length + StrLen (CIDSTRStr) + 1);
+ AcpiEx = (ACPI_EXTENDED_HID_DEVICE_PATH *) CreateDeviceNode (
+ ACPI_DEVICE_PATH,
+ ACPI_EXTENDED_DP,
+ Length
+ );
+
+ AcpiEx->HID = EisaIdFromText (HIDStr);
+ AcpiEx->CID = EisaIdFromText (CIDStr);
+ AcpiEx->UID = (UINT32) Strtoi (UIDStr);
+
+ AsciiStr = (CHAR8 *) ((UINT8 *)AcpiEx + sizeof (ACPI_EXTENDED_HID_DEVICE_PATH));
+ StrToAscii (HIDSTRStr, &AsciiStr);
+ StrToAscii (UIDSTRStr, &AsciiStr);
+ StrToAscii (CIDSTRStr, &AsciiStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) AcpiEx;
+}
+
+/**
+ Converts a text device path node to ACPI extension device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created ACPI extension device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAcpiExp (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *HIDStr;
+ CHAR16 *CIDStr;
+ CHAR16 *UIDSTRStr;
+ CHAR8 *AsciiStr;
+ UINT16 Length;
+ ACPI_EXTENDED_HID_DEVICE_PATH *AcpiEx;
+
+ HIDStr = GetNextParamStr (&TextDeviceNode);
+ CIDStr = GetNextParamStr (&TextDeviceNode);
+ UIDSTRStr = GetNextParamStr (&TextDeviceNode);
+ Length = (UINT16) (sizeof (ACPI_EXTENDED_HID_DEVICE_PATH) + StrLen (UIDSTRStr) + 3);
+ AcpiEx = (ACPI_EXTENDED_HID_DEVICE_PATH *) CreateDeviceNode (
+ ACPI_DEVICE_PATH,
+ ACPI_EXTENDED_DP,
+ Length
+ );
+
+ AcpiEx->HID = EisaIdFromText (HIDStr);
+ //
+ // According to UEFI spec, the CID parametr is optional and has a default value of 0.
+ // So when the CID parametr is not specified or specified as 0 in the text device node.
+ // Set the CID to 0 in the ACPI extension device path structure.
+ //
+ if (*CIDStr == L'\0' || *CIDStr == L'0') {
+ AcpiEx->CID = 0;
+ } else {
+ AcpiEx->CID = EisaIdFromText (CIDStr);
+ }
+ AcpiEx->UID = 0;
+
+ AsciiStr = (CHAR8 *) ((UINT8 *)AcpiEx + sizeof (ACPI_EXTENDED_HID_DEVICE_PATH));
+ //
+ // HID string is NULL
+ //
+ *AsciiStr = '\0';
+ //
+ // Convert UID string
+ //
+ AsciiStr++;
+ StrToAscii (UIDSTRStr, &AsciiStr);
+ //
+ // CID string is NULL
+ //
+ *AsciiStr = '\0';
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) AcpiEx;
+}
+
+/**
+ Converts a text device path node to ACPI _ADR device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created ACPI _ADR device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAcpiAdr (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *DisplayDeviceStr;
+ ACPI_ADR_DEVICE_PATH *AcpiAdr;
+ UINTN Index;
+ UINTN Length;
+
+ AcpiAdr = (ACPI_ADR_DEVICE_PATH *) CreateDeviceNode (
+ ACPI_DEVICE_PATH,
+ ACPI_ADR_DP,
+ (UINT16) sizeof (ACPI_ADR_DEVICE_PATH)
+ );
+ ASSERT (AcpiAdr != NULL);
+
+ for (Index = 0; ; Index++) {
+ DisplayDeviceStr = GetNextParamStr (&TextDeviceNode);
+ if (IS_NULL (*DisplayDeviceStr)) {
+ break;
+ }
+ if (Index > 0) {
+ Length = DevicePathNodeLength (AcpiAdr);
+ AcpiAdr = ReallocatePool (
+ Length,
+ Length + sizeof (UINT32),
+ AcpiAdr
+ );
+ ASSERT (AcpiAdr != NULL);
+ SetDevicePathNodeLength (AcpiAdr, Length + sizeof (UINT32));
+ }
+
+ (&AcpiAdr->ADR)[Index] = (UINT32) Strtoi (DisplayDeviceStr);
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) AcpiAdr;
+}
+
+/**
+ Converts a generic messaging text device path node to messaging device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to messaging device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextMsg (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return DevPathFromTextGenericPath (MESSAGING_DEVICE_PATH, TextDeviceNode);
+}
+
+/**
+ Converts a text device path node to Parallel Port device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Parallel Port device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextAta (
+IN CHAR16 *TextDeviceNode
+)
+{
+ CHAR16 *PrimarySecondaryStr;
+ CHAR16 *SlaveMasterStr;
+ CHAR16 *LunStr;
+ ATAPI_DEVICE_PATH *Atapi;
+
+ Atapi = (ATAPI_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_ATAPI_DP,
+ (UINT16) sizeof (ATAPI_DEVICE_PATH)
+ );
+
+ PrimarySecondaryStr = GetNextParamStr (&TextDeviceNode);
+ SlaveMasterStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+
+ if (StrCmp (PrimarySecondaryStr, L"Primary") == 0) {
+ Atapi->PrimarySecondary = 0;
+ } else if (StrCmp (PrimarySecondaryStr, L"Secondary") == 0) {
+ Atapi->PrimarySecondary = 1;
+ } else {
+ Atapi->PrimarySecondary = (UINT8) Strtoi (PrimarySecondaryStr);
+ }
+ if (StrCmp (SlaveMasterStr, L"Master") == 0) {
+ Atapi->SlaveMaster = 0;
+ } else if (StrCmp (SlaveMasterStr, L"Slave") == 0) {
+ Atapi->SlaveMaster = 1;
+ } else {
+ Atapi->SlaveMaster = (UINT8) Strtoi (SlaveMasterStr);
+ }
+
+ Atapi->Lun = (UINT16) Strtoi (LunStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Atapi;
+}
+
+/**
+ Converts a text device path node to SCSI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created SCSI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextScsi (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *PunStr;
+ CHAR16 *LunStr;
+ SCSI_DEVICE_PATH *Scsi;
+
+ PunStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ Scsi = (SCSI_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_SCSI_DP,
+ (UINT16) sizeof (SCSI_DEVICE_PATH)
+ );
+
+ Scsi->Pun = (UINT16) Strtoi (PunStr);
+ Scsi->Lun = (UINT16) Strtoi (LunStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Scsi;
+}
+
+/**
+ Converts a text device path node to Fibre device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Fibre device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFibre (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *WWNStr;
+ CHAR16 *LunStr;
+ FIBRECHANNEL_DEVICE_PATH *Fibre;
+
+ WWNStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ Fibre = (FIBRECHANNEL_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_FIBRECHANNEL_DP,
+ (UINT16) sizeof (FIBRECHANNEL_DEVICE_PATH)
+ );
+
+ Fibre->Reserved = 0;
+ Strtoi64 (WWNStr, &Fibre->WWN);
+ Strtoi64 (LunStr, &Fibre->Lun);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Fibre;
+}
+
+/**
+ Converts a text device path node to FibreEx device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created FibreEx device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFibreEx (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *WWNStr;
+ CHAR16 *LunStr;
+ FIBRECHANNELEX_DEVICE_PATH *FibreEx;
+
+ WWNStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ FibreEx = (FIBRECHANNELEX_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_FIBRECHANNELEX_DP,
+ (UINT16) sizeof (FIBRECHANNELEX_DEVICE_PATH)
+ );
+
+ FibreEx->Reserved = 0;
+ Strtoi64 (WWNStr, (UINT64 *) (&FibreEx->WWN));
+ Strtoi64 (LunStr, (UINT64 *) (&FibreEx->Lun));
+
+ *(UINT64 *) (&FibreEx->WWN) = SwapBytes64 (*(UINT64 *) (&FibreEx->WWN));
+ *(UINT64 *) (&FibreEx->Lun) = SwapBytes64 (*(UINT64 *) (&FibreEx->Lun));
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) FibreEx;
+}
+
+/**
+ Converts a text device path node to 1394 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created 1394 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromText1394 (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *GuidStr;
+ F1394_DEVICE_PATH *F1394DevPath;
+
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+ F1394DevPath = (F1394_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_1394_DP,
+ (UINT16) sizeof (F1394_DEVICE_PATH)
+ );
+
+ F1394DevPath->Reserved = 0;
+ F1394DevPath->Guid = StrHexToUint64 (GuidStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) F1394DevPath;
+}
+
+/**
+ Converts a text device path node to USB device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsb (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *PortStr;
+ CHAR16 *InterfaceStr;
+ USB_DEVICE_PATH *Usb;
+
+ PortStr = GetNextParamStr (&TextDeviceNode);
+ InterfaceStr = GetNextParamStr (&TextDeviceNode);
+ Usb = (USB_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_USB_DP,
+ (UINT16) sizeof (USB_DEVICE_PATH)
+ );
+
+ Usb->ParentPortNumber = (UINT8) Strtoi (PortStr);
+ Usb->InterfaceNumber = (UINT8) Strtoi (InterfaceStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Usb;
+}
+
+/**
+ Converts a text device path node to I20 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created I20 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextI2O (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *TIDStr;
+ I2O_DEVICE_PATH *I2ODevPath;
+
+ TIDStr = GetNextParamStr (&TextDeviceNode);
+ I2ODevPath = (I2O_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_I2O_DP,
+ (UINT16) sizeof (I2O_DEVICE_PATH)
+ );
+
+ I2ODevPath->Tid = (UINT32) Strtoi (TIDStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) I2ODevPath;
+}
+
+/**
+ Converts a text device path node to Infini Band device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Infini Band device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextInfiniband (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *FlagsStr;
+ CHAR16 *GuidStr;
+ CHAR16 *SidStr;
+ CHAR16 *TidStr;
+ CHAR16 *DidStr;
+ INFINIBAND_DEVICE_PATH *InfiniBand;
+
+ FlagsStr = GetNextParamStr (&TextDeviceNode);
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+ SidStr = GetNextParamStr (&TextDeviceNode);
+ TidStr = GetNextParamStr (&TextDeviceNode);
+ DidStr = GetNextParamStr (&TextDeviceNode);
+ InfiniBand = (INFINIBAND_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_INFINIBAND_DP,
+ (UINT16) sizeof (INFINIBAND_DEVICE_PATH)
+ );
+
+ InfiniBand->ResourceFlags = (UINT32) Strtoi (FlagsStr);
+ StrToGuid (GuidStr, (EFI_GUID *) InfiniBand->PortGid);
+ Strtoi64 (SidStr, &InfiniBand->ServiceId);
+ Strtoi64 (TidStr, &InfiniBand->TargetPortId);
+ Strtoi64 (DidStr, &InfiniBand->DeviceId);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) InfiniBand;
+}
+
+/**
+ Converts a text device path node to Vendor-Defined Messaging device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor-Defined Messaging device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenMsg (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextVendor (
+ TextDeviceNode,
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP
+ );
+}
+
+/**
+ Converts a text device path node to Vendor defined PC-ANSI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor defined PC-ANSI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenPcAnsi (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ VENDOR_DEVICE_PATH *Vendor;
+
+ Vendor = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (VENDOR_DEVICE_PATH));
+ CopyGuid (&Vendor->Guid, &gEfiPcAnsiGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vendor;
+}
+
+/**
+ Converts a text device path node to Vendor defined VT100 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor defined VT100 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenVt100 (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ VENDOR_DEVICE_PATH *Vendor;
+
+ Vendor = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (VENDOR_DEVICE_PATH));
+ CopyGuid (&Vendor->Guid, &gEfiVT100Guid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vendor;
+}
+
+/**
+ Converts a text device path node to Vendor defined VT100 Plus device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor defined VT100 Plus device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenVt100Plus (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ VENDOR_DEVICE_PATH *Vendor;
+
+ Vendor = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (VENDOR_DEVICE_PATH));
+ CopyGuid (&Vendor->Guid, &gEfiVT100PlusGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vendor;
+}
+
+/**
+ Converts a text device path node to Vendor defined UTF8 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor defined UTF8 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenUtf8 (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ VENDOR_DEVICE_PATH *Vendor;
+
+ Vendor = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (VENDOR_DEVICE_PATH));
+ CopyGuid (&Vendor->Guid, &gEfiVTUTF8Guid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vendor;
+}
+
+/**
+ Converts a text device path node to UART Flow Control device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created UART Flow Control device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUartFlowCtrl (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *ValueStr;
+ UART_FLOW_CONTROL_DEVICE_PATH *UartFlowControl;
+
+ ValueStr = GetNextParamStr (&TextDeviceNode);
+ UartFlowControl = (UART_FLOW_CONTROL_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (UART_FLOW_CONTROL_DEVICE_PATH)
+ );
+
+ CopyGuid (&UartFlowControl->Guid, &gEfiUartDevicePathGuid);
+ if (StrCmp (ValueStr, L"XonXoff") == 0) {
+ UartFlowControl->FlowControlMap = 2;
+ } else if (StrCmp (ValueStr, L"Hardware") == 0) {
+ UartFlowControl->FlowControlMap = 1;
+ } else {
+ UartFlowControl->FlowControlMap = 0;
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) UartFlowControl;
+}
+
+/**
+ Converts a text device path node to Serial Attached SCSI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Serial Attached SCSI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextSAS (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *AddressStr;
+ CHAR16 *LunStr;
+ CHAR16 *RTPStr;
+ CHAR16 *SASSATAStr;
+ CHAR16 *LocationStr;
+ CHAR16 *ConnectStr;
+ CHAR16 *DriveBayStr;
+ CHAR16 *ReservedStr;
+ UINT16 Info;
+ UINT16 Uint16;
+ SAS_DEVICE_PATH *Sas;
+
+ AddressStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ RTPStr = GetNextParamStr (&TextDeviceNode);
+ SASSATAStr = GetNextParamStr (&TextDeviceNode);
+ LocationStr = GetNextParamStr (&TextDeviceNode);
+ ConnectStr = GetNextParamStr (&TextDeviceNode);
+ DriveBayStr = GetNextParamStr (&TextDeviceNode);
+ ReservedStr = GetNextParamStr (&TextDeviceNode);
+ Sas = (SAS_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (SAS_DEVICE_PATH)
+ );
+
+ CopyGuid (&Sas->Guid, &gEfiSasDevicePathGuid);
+ Strtoi64 (AddressStr, &Sas->SasAddress);
+ Strtoi64 (LunStr, &Sas->Lun);
+ Sas->RelativeTargetPort = (UINT16) Strtoi (RTPStr);
+
+ if (StrCmp (SASSATAStr, L"NoTopology") == 0) {
+ Info = 0x0;
+
+ } else if ((StrCmp (SASSATAStr, L"SATA") == 0) || (StrCmp (SASSATAStr, L"SAS") == 0)) {
+
+ Uint16 = (UINT16) Strtoi (DriveBayStr);
+ if (Uint16 == 0) {
+ Info = 0x1;
+ } else {
+ Info = (UINT16) (0x2 | ((Uint16 - 1) << 8));
+ }
+
+ if (StrCmp (SASSATAStr, L"SATA") == 0) {
+ Info |= BIT4;
+ }
+
+ //
+ // Location is an integer between 0 and 1 or else
+ // the keyword Internal (0) or External (1).
+ //
+ if (StrCmp (LocationStr, L"External") == 0) {
+ Uint16 = 1;
+ } else if (StrCmp (LocationStr, L"Internal") == 0) {
+ Uint16 = 0;
+ } else {
+ Uint16 = ((UINT16) Strtoi (LocationStr) & BIT0);
+ }
+ Info |= (Uint16 << 5);
+
+ //
+ // Connect is an integer between 0 and 3 or else
+ // the keyword Direct (0) or Expanded (1).
+ //
+ if (StrCmp (ConnectStr, L"Expanded") == 0) {
+ Uint16 = 1;
+ } else if (StrCmp (ConnectStr, L"Direct") == 0) {
+ Uint16 = 0;
+ } else {
+ Uint16 = ((UINT16) Strtoi (ConnectStr) & (BIT0 | BIT1));
+ }
+ Info |= (Uint16 << 6);
+
+ } else {
+ Info = (UINT16) Strtoi (SASSATAStr);
+ }
+
+ Sas->DeviceTopology = Info;
+ Sas->Reserved = (UINT32) Strtoi (ReservedStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Sas;
+}
+
+/**
+ Converts a text device path node to Serial Attached SCSI Ex device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Serial Attached SCSI Ex device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextSasEx (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *AddressStr;
+ CHAR16 *LunStr;
+ CHAR16 *RTPStr;
+ CHAR16 *SASSATAStr;
+ CHAR16 *LocationStr;
+ CHAR16 *ConnectStr;
+ CHAR16 *DriveBayStr;
+ UINT16 Info;
+ UINT16 Uint16;
+ UINT64 SasAddress;
+ UINT64 Lun;
+ SASEX_DEVICE_PATH *SasEx;
+
+ AddressStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ RTPStr = GetNextParamStr (&TextDeviceNode);
+ SASSATAStr = GetNextParamStr (&TextDeviceNode);
+ LocationStr = GetNextParamStr (&TextDeviceNode);
+ ConnectStr = GetNextParamStr (&TextDeviceNode);
+ DriveBayStr = GetNextParamStr (&TextDeviceNode);
+ SasEx = (SASEX_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_SASEX_DP,
+ (UINT16) sizeof (SASEX_DEVICE_PATH)
+ );
+
+ Strtoi64 (AddressStr, &SasAddress);
+ Strtoi64 (LunStr, &Lun);
+ WriteUnaligned64 ((UINT64 *) &SasEx->SasAddress, SwapBytes64 (SasAddress));
+ WriteUnaligned64 ((UINT64 *) &SasEx->Lun, SwapBytes64 (Lun));
+ SasEx->RelativeTargetPort = (UINT16) Strtoi (RTPStr);
+
+ if (StrCmp (SASSATAStr, L"NoTopology") == 0) {
+ Info = 0x0;
+
+ } else if ((StrCmp (SASSATAStr, L"SATA") == 0) || (StrCmp (SASSATAStr, L"SAS") == 0)) {
+
+ Uint16 = (UINT16) Strtoi (DriveBayStr);
+ if (Uint16 == 0) {
+ Info = 0x1;
+ } else {
+ Info = (UINT16) (0x2 | ((Uint16 - 1) << 8));
+ }
+
+ if (StrCmp (SASSATAStr, L"SATA") == 0) {
+ Info |= BIT4;
+ }
+
+ //
+ // Location is an integer between 0 and 1 or else
+ // the keyword Internal (0) or External (1).
+ //
+ if (StrCmp (LocationStr, L"External") == 0) {
+ Uint16 = 1;
+ } else if (StrCmp (LocationStr, L"Internal") == 0) {
+ Uint16 = 0;
+ } else {
+ Uint16 = ((UINT16) Strtoi (LocationStr) & BIT0);
+ }
+ Info |= (Uint16 << 5);
+
+ //
+ // Connect is an integer between 0 and 3 or else
+ // the keyword Direct (0) or Expanded (1).
+ //
+ if (StrCmp (ConnectStr, L"Expanded") == 0) {
+ Uint16 = 1;
+ } else if (StrCmp (ConnectStr, L"Direct") == 0) {
+ Uint16 = 0;
+ } else {
+ Uint16 = ((UINT16) Strtoi (ConnectStr) & (BIT0 | BIT1));
+ }
+ Info |= (Uint16 << 6);
+
+ } else {
+ Info = (UINT16) Strtoi (SASSATAStr);
+ }
+
+ SasEx->DeviceTopology = Info;
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) SasEx;
+}
+
+/**
+ Converts a text device path node to NVM Express Namespace device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created NVM Express Namespace device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextNVMe (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *NamespaceIdStr;
+ CHAR16 *NamespaceUuidStr;
+ NVME_NAMESPACE_DEVICE_PATH *Nvme;
+ UINT8 *Uuid;
+ UINTN Index;
+
+ NamespaceIdStr = GetNextParamStr (&TextDeviceNode);
+ NamespaceUuidStr = GetNextParamStr (&TextDeviceNode);
+ Nvme = (NVME_NAMESPACE_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_NVME_NAMESPACE_DP,
+ (UINT16) sizeof (NVME_NAMESPACE_DEVICE_PATH)
+ );
+
+ Nvme->NamespaceId = (UINT32) Strtoi (NamespaceIdStr);
+ Uuid = (UINT8 *) &Nvme->NamespaceUuid;
+
+ Index = sizeof (Nvme->NamespaceUuid) / sizeof (UINT8);
+ while (Index-- != 0) {
+ Uuid[Index] = (UINT8) StrHexToUintn (SplitStr (&NamespaceUuidStr, L'-'));
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Nvme;
+}
+
+/**
+ Converts a text device path node to UFS device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created UFS device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUfs (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *PunStr;
+ CHAR16 *LunStr;
+ UFS_DEVICE_PATH *Ufs;
+
+ PunStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ Ufs = (UFS_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_UFS_DP,
+ (UINT16) sizeof (UFS_DEVICE_PATH)
+ );
+
+ Ufs->Pun = (UINT8) Strtoi (PunStr);
+ Ufs->Lun = (UINT8) Strtoi (LunStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Ufs;
+}
+
+/**
+ Converts a text device path node to SD (Secure Digital) device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created SD device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextSd (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *SlotNumberStr;
+ SD_DEVICE_PATH *Sd;
+
+ SlotNumberStr = GetNextParamStr (&TextDeviceNode);
+ Sd = (SD_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_SD_DP,
+ (UINT16) sizeof (SD_DEVICE_PATH)
+ );
+
+ Sd->SlotNumber = (UINT8) Strtoi (SlotNumberStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Sd;
+}
+
+/**
+ Converts a text device path node to EMMC (Embedded MMC) device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created EMMC device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextEmmc (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *SlotNumberStr;
+ EMMC_DEVICE_PATH *Emmc;
+
+ SlotNumberStr = GetNextParamStr (&TextDeviceNode);
+ Emmc = (EMMC_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_EMMC_DP,
+ (UINT16) sizeof (EMMC_DEVICE_PATH)
+ );
+
+ Emmc->SlotNumber = (UINT8) Strtoi (SlotNumberStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Emmc;
+}
+
+/**
+ Converts a text device path node to Debug Port device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Debug Port device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextDebugPort (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ VENDOR_DEVICE_PATH *Vend;
+
+ Vend = (VENDOR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VENDOR_DP,
+ (UINT16) sizeof (VENDOR_DEVICE_PATH)
+ );
+
+ CopyGuid (&Vend->Guid, &gEfiDebugPortProtocolGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vend;
+}
+
+/**
+ Converts a text device path node to MAC device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created MAC device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextMAC (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *AddressStr;
+ CHAR16 *IfTypeStr;
+ UINTN Length;
+ MAC_ADDR_DEVICE_PATH *MACDevPath;
+
+ AddressStr = GetNextParamStr (&TextDeviceNode);
+ IfTypeStr = GetNextParamStr (&TextDeviceNode);
+ MACDevPath = (MAC_ADDR_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_MAC_ADDR_DP,
+ (UINT16) sizeof (MAC_ADDR_DEVICE_PATH)
+ );
+
+ MACDevPath->IfType = (UINT8) Strtoi (IfTypeStr);
+
+ Length = sizeof (EFI_MAC_ADDRESS);
+ if (MACDevPath->IfType == 0x01 || MACDevPath->IfType == 0x00) {
+ Length = 6;
+ }
+
+ StrHexToBytes (AddressStr, Length * 2, MACDevPath->MacAddress.Addr, Length);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) MACDevPath;
+}
+
+
+/**
+ Converts a text format to the network protocol ID.
+
+ @param Text String of protocol field.
+
+ @return Network protocol ID .
+
+**/
+UINTN
+NetworkProtocolFromText (
+ IN CHAR16 *Text
+ )
+{
+ if (StrCmp (Text, L"UDP") == 0) {
+ return RFC_1700_UDP_PROTOCOL;
+ }
+
+ if (StrCmp (Text, L"TCP") == 0) {
+ return RFC_1700_TCP_PROTOCOL;
+ }
+
+ return Strtoi (Text);
+}
+
+
+/**
+ Converts a text device path node to IPV4 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created IPV4 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextIPv4 (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *RemoteIPStr;
+ CHAR16 *ProtocolStr;
+ CHAR16 *TypeStr;
+ CHAR16 *LocalIPStr;
+ CHAR16 *GatewayIPStr;
+ CHAR16 *SubnetMaskStr;
+ IPv4_DEVICE_PATH *IPv4;
+
+ RemoteIPStr = GetNextParamStr (&TextDeviceNode);
+ ProtocolStr = GetNextParamStr (&TextDeviceNode);
+ TypeStr = GetNextParamStr (&TextDeviceNode);
+ LocalIPStr = GetNextParamStr (&TextDeviceNode);
+ GatewayIPStr = GetNextParamStr (&TextDeviceNode);
+ SubnetMaskStr = GetNextParamStr (&TextDeviceNode);
+ IPv4 = (IPv4_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_IPv4_DP,
+ (UINT16) sizeof (IPv4_DEVICE_PATH)
+ );
+
+ StrToIpv4Address (RemoteIPStr, NULL, &IPv4->RemoteIpAddress, NULL);
+ IPv4->Protocol = (UINT16) NetworkProtocolFromText (ProtocolStr);
+ if (StrCmp (TypeStr, L"Static") == 0) {
+ IPv4->StaticIpAddress = TRUE;
+ } else {
+ IPv4->StaticIpAddress = FALSE;
+ }
+
+ StrToIpv4Address (LocalIPStr, NULL, &IPv4->LocalIpAddress, NULL);
+ if (!IS_NULL (*GatewayIPStr) && !IS_NULL (*SubnetMaskStr)) {
+ StrToIpv4Address (GatewayIPStr, NULL, &IPv4->GatewayIpAddress, NULL);
+ StrToIpv4Address (SubnetMaskStr, NULL, &IPv4->SubnetMask, NULL);
+ } else {
+ ZeroMem (&IPv4->GatewayIpAddress, sizeof (IPv4->GatewayIpAddress));
+ ZeroMem (&IPv4->SubnetMask, sizeof (IPv4->SubnetMask));
+ }
+
+ IPv4->LocalPort = 0;
+ IPv4->RemotePort = 0;
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) IPv4;
+}
+
+/**
+ Converts a text device path node to IPV6 device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created IPV6 device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextIPv6 (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *RemoteIPStr;
+ CHAR16 *ProtocolStr;
+ CHAR16 *TypeStr;
+ CHAR16 *LocalIPStr;
+ CHAR16 *GatewayIPStr;
+ CHAR16 *PrefixLengthStr;
+ IPv6_DEVICE_PATH *IPv6;
+
+ RemoteIPStr = GetNextParamStr (&TextDeviceNode);
+ ProtocolStr = GetNextParamStr (&TextDeviceNode);
+ TypeStr = GetNextParamStr (&TextDeviceNode);
+ LocalIPStr = GetNextParamStr (&TextDeviceNode);
+ PrefixLengthStr = GetNextParamStr (&TextDeviceNode);
+ GatewayIPStr = GetNextParamStr (&TextDeviceNode);
+ IPv6 = (IPv6_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_IPv6_DP,
+ (UINT16) sizeof (IPv6_DEVICE_PATH)
+ );
+
+ StrToIpv6Address (RemoteIPStr, NULL, &IPv6->RemoteIpAddress, NULL);
+ IPv6->Protocol = (UINT16) NetworkProtocolFromText (ProtocolStr);
+ if (StrCmp (TypeStr, L"Static") == 0) {
+ IPv6->IpAddressOrigin = 0;
+ } else if (StrCmp (TypeStr, L"StatelessAutoConfigure") == 0) {
+ IPv6->IpAddressOrigin = 1;
+ } else {
+ IPv6->IpAddressOrigin = 2;
+ }
+
+ StrToIpv6Address (LocalIPStr, NULL, &IPv6->LocalIpAddress, NULL);
+ if (!IS_NULL (*GatewayIPStr) && !IS_NULL (*PrefixLengthStr)) {
+ StrToIpv6Address (GatewayIPStr, NULL, &IPv6->GatewayIpAddress, NULL);
+ IPv6->PrefixLength = (UINT8) Strtoi (PrefixLengthStr);
+ } else {
+ ZeroMem (&IPv6->GatewayIpAddress, sizeof (IPv6->GatewayIpAddress));
+ IPv6->PrefixLength = 0;
+ }
+
+ IPv6->LocalPort = 0;
+ IPv6->RemotePort = 0;
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) IPv6;
+}
+
+/**
+ Converts a text device path node to UART device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created UART device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUart (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *BaudStr;
+ CHAR16 *DataBitsStr;
+ CHAR16 *ParityStr;
+ CHAR16 *StopBitsStr;
+ UART_DEVICE_PATH *Uart;
+
+ BaudStr = GetNextParamStr (&TextDeviceNode);
+ DataBitsStr = GetNextParamStr (&TextDeviceNode);
+ ParityStr = GetNextParamStr (&TextDeviceNode);
+ StopBitsStr = GetNextParamStr (&TextDeviceNode);
+ Uart = (UART_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_UART_DP,
+ (UINT16) sizeof (UART_DEVICE_PATH)
+ );
+
+ if (StrCmp (BaudStr, L"DEFAULT") == 0) {
+ Uart->BaudRate = 115200;
+ } else {
+ Strtoi64 (BaudStr, &Uart->BaudRate);
+ }
+ Uart->DataBits = (UINT8) ((StrCmp (DataBitsStr, L"DEFAULT") == 0) ? 8 : Strtoi (DataBitsStr));
+ switch (*ParityStr) {
+ case L'D':
+ Uart->Parity = 0;
+ break;
+
+ case L'N':
+ Uart->Parity = 1;
+ break;
+
+ case L'E':
+ Uart->Parity = 2;
+ break;
+
+ case L'O':
+ Uart->Parity = 3;
+ break;
+
+ case L'M':
+ Uart->Parity = 4;
+ break;
+
+ case L'S':
+ Uart->Parity = 5;
+ break;
+
+ default:
+ Uart->Parity = (UINT8) Strtoi (ParityStr);
+ break;
+ }
+
+ if (StrCmp (StopBitsStr, L"D") == 0) {
+ Uart->StopBits = (UINT8) 0;
+ } else if (StrCmp (StopBitsStr, L"1") == 0) {
+ Uart->StopBits = (UINT8) 1;
+ } else if (StrCmp (StopBitsStr, L"1.5") == 0) {
+ Uart->StopBits = (UINT8) 2;
+ } else if (StrCmp (StopBitsStr, L"2") == 0) {
+ Uart->StopBits = (UINT8) 3;
+ } else {
+ Uart->StopBits = (UINT8) Strtoi (StopBitsStr);
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Uart;
+}
+
+/**
+ Converts a text device path node to USB class device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+ @param UsbClassText A pointer to USB_CLASS_TEXT structure to be integrated to USB Class Text.
+
+ @return A pointer to the newly-created USB class device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+ConvertFromTextUsbClass (
+ IN CHAR16 *TextDeviceNode,
+ IN USB_CLASS_TEXT *UsbClassText
+ )
+{
+ CHAR16 *VIDStr;
+ CHAR16 *PIDStr;
+ CHAR16 *ClassStr;
+ CHAR16 *SubClassStr;
+ CHAR16 *ProtocolStr;
+ USB_CLASS_DEVICE_PATH *UsbClass;
+
+ UsbClass = (USB_CLASS_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_USB_CLASS_DP,
+ (UINT16) sizeof (USB_CLASS_DEVICE_PATH)
+ );
+
+ VIDStr = GetNextParamStr (&TextDeviceNode);
+ PIDStr = GetNextParamStr (&TextDeviceNode);
+ if (UsbClassText->ClassExist) {
+ ClassStr = GetNextParamStr (&TextDeviceNode);
+ if (*ClassStr == L'\0') {
+ UsbClass->DeviceClass = 0xFF;
+ } else {
+ UsbClass->DeviceClass = (UINT8) Strtoi (ClassStr);
+ }
+ } else {
+ UsbClass->DeviceClass = UsbClassText->Class;
+ }
+ if (UsbClassText->SubClassExist) {
+ SubClassStr = GetNextParamStr (&TextDeviceNode);
+ if (*SubClassStr == L'\0') {
+ UsbClass->DeviceSubClass = 0xFF;
+ } else {
+ UsbClass->DeviceSubClass = (UINT8) Strtoi (SubClassStr);
+ }
+ } else {
+ UsbClass->DeviceSubClass = UsbClassText->SubClass;
+ }
+
+ ProtocolStr = GetNextParamStr (&TextDeviceNode);
+
+ if (*VIDStr == L'\0') {
+ UsbClass->VendorId = 0xFFFF;
+ } else {
+ UsbClass->VendorId = (UINT16) Strtoi (VIDStr);
+ }
+ if (*PIDStr == L'\0') {
+ UsbClass->ProductId = 0xFFFF;
+ } else {
+ UsbClass->ProductId = (UINT16) Strtoi (PIDStr);
+ }
+ if (*ProtocolStr == L'\0') {
+ UsbClass->DeviceProtocol = 0xFF;
+ } else {
+ UsbClass->DeviceProtocol = (UINT8) Strtoi (ProtocolStr);
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) UsbClass;
+}
+
+
+/**
+ Converts a text device path node to USB class device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB class device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbClass (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = TRUE;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB audio device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB audio device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbAudio (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_AUDIO;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB CDC Control device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB CDC Control device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbCDCControl (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_CDCCONTROL;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB HID device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB HID device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbHID (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_HID;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB Image device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB Image device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbImage (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_IMAGE;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB Print device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB Print device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbPrinter (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_PRINTER;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB mass storage device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB mass storage device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbMassStorage (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_MASS_STORAGE;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB HUB device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB HUB device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbHub (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_HUB;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB CDC data device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB CDC data device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbCDCData (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_CDCDATA;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB smart card device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB smart card device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbSmartCard (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_SMART_CARD;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB video device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB video device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbVideo (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_VIDEO;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB diagnostic device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB diagnostic device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbDiagnostic (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_DIAGNOSTIC;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB wireless device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB wireless device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbWireless (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_WIRELESS;
+ UsbClassText.SubClassExist = TRUE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB device firmware update device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB device firmware update device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbDeviceFirmwareUpdate (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_RESERVE;
+ UsbClassText.SubClassExist = FALSE;
+ UsbClassText.SubClass = USB_SUBCLASS_FW_UPDATE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB IRDA bridge device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB IRDA bridge device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbIrdaBridge (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_RESERVE;
+ UsbClassText.SubClassExist = FALSE;
+ UsbClassText.SubClass = USB_SUBCLASS_IRDA_BRIDGE;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB text and measurement device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB text and measurement device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbTestAndMeasurement (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ USB_CLASS_TEXT UsbClassText;
+
+ UsbClassText.ClassExist = FALSE;
+ UsbClassText.Class = USB_CLASS_RESERVE;
+ UsbClassText.SubClassExist = FALSE;
+ UsbClassText.SubClass = USB_SUBCLASS_TEST;
+
+ return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText);
+}
+
+/**
+ Converts a text device path node to USB WWID device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created USB WWID device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUsbWwid (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *VIDStr;
+ CHAR16 *PIDStr;
+ CHAR16 *InterfaceNumStr;
+ CHAR16 *SerialNumberStr;
+ USB_WWID_DEVICE_PATH *UsbWwid;
+ UINTN SerialNumberStrLen;
+
+ VIDStr = GetNextParamStr (&TextDeviceNode);
+ PIDStr = GetNextParamStr (&TextDeviceNode);
+ InterfaceNumStr = GetNextParamStr (&TextDeviceNode);
+ SerialNumberStr = GetNextParamStr (&TextDeviceNode);
+ SerialNumberStrLen = StrLen (SerialNumberStr);
+ if (SerialNumberStrLen >= 2 &&
+ SerialNumberStr[0] == L'\"' &&
+ SerialNumberStr[SerialNumberStrLen - 1] == L'\"'
+ ) {
+ SerialNumberStr[SerialNumberStrLen - 1] = L'\0';
+ SerialNumberStr++;
+ SerialNumberStrLen -= 2;
+ }
+ UsbWwid = (USB_WWID_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_USB_WWID_DP,
+ (UINT16) (sizeof (USB_WWID_DEVICE_PATH) + SerialNumberStrLen * sizeof (CHAR16))
+ );
+ UsbWwid->VendorId = (UINT16) Strtoi (VIDStr);
+ UsbWwid->ProductId = (UINT16) Strtoi (PIDStr);
+ UsbWwid->InterfaceNumber = (UINT16) Strtoi (InterfaceNumStr);
+
+ //
+ // There is no memory allocated in UsbWwid for the '\0' in SerialNumberStr.
+ // Therefore, the '\0' will not be copied.
+ //
+ CopyMem (
+ (UINT8 *) UsbWwid + sizeof (USB_WWID_DEVICE_PATH),
+ SerialNumberStr,
+ SerialNumberStrLen * sizeof (CHAR16)
+ );
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) UsbWwid;
+}
+
+/**
+ Converts a text device path node to Logic Unit device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Logic Unit device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUnit (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *LunStr;
+ DEVICE_LOGICAL_UNIT_DEVICE_PATH *LogicalUnit;
+
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ LogicalUnit = (DEVICE_LOGICAL_UNIT_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_DEVICE_LOGICAL_UNIT_DP,
+ (UINT16) sizeof (DEVICE_LOGICAL_UNIT_DEVICE_PATH)
+ );
+
+ LogicalUnit->Lun = (UINT8) Strtoi (LunStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) LogicalUnit;
+}
+
+/**
+ Converts a text device path node to iSCSI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created iSCSI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextiSCSI (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ UINT16 Options;
+ CHAR16 *NameStr;
+ CHAR16 *PortalGroupStr;
+ CHAR16 *LunStr;
+ CHAR16 *HeaderDigestStr;
+ CHAR16 *DataDigestStr;
+ CHAR16 *AuthenticationStr;
+ CHAR16 *ProtocolStr;
+ CHAR8 *AsciiStr;
+ ISCSI_DEVICE_PATH_WITH_NAME *ISCSIDevPath;
+ UINT64 Lun;
+
+ NameStr = GetNextParamStr (&TextDeviceNode);
+ PortalGroupStr = GetNextParamStr (&TextDeviceNode);
+ LunStr = GetNextParamStr (&TextDeviceNode);
+ HeaderDigestStr = GetNextParamStr (&TextDeviceNode);
+ DataDigestStr = GetNextParamStr (&TextDeviceNode);
+ AuthenticationStr = GetNextParamStr (&TextDeviceNode);
+ ProtocolStr = GetNextParamStr (&TextDeviceNode);
+ ISCSIDevPath = (ISCSI_DEVICE_PATH_WITH_NAME *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_ISCSI_DP,
+ (UINT16) (sizeof (ISCSI_DEVICE_PATH_WITH_NAME) + StrLen (NameStr))
+ );
+
+ AsciiStr = ISCSIDevPath->TargetName;
+ StrToAscii (NameStr, &AsciiStr);
+
+ ISCSIDevPath->TargetPortalGroupTag = (UINT16) Strtoi (PortalGroupStr);
+ Strtoi64 (LunStr, &Lun);
+ WriteUnaligned64 ((UINT64 *) &ISCSIDevPath->Lun, SwapBytes64 (Lun));
+
+ Options = 0x0000;
+ if (StrCmp (HeaderDigestStr, L"CRC32C") == 0) {
+ Options |= 0x0002;
+ }
+
+ if (StrCmp (DataDigestStr, L"CRC32C") == 0) {
+ Options |= 0x0008;
+ }
+
+ if (StrCmp (AuthenticationStr, L"None") == 0) {
+ Options |= 0x0800;
+ }
+
+ if (StrCmp (AuthenticationStr, L"CHAP_UNI") == 0) {
+ Options |= 0x1000;
+ }
+
+ ISCSIDevPath->LoginOption = (UINT16) Options;
+
+ if (IS_NULL (*ProtocolStr) || (StrCmp (ProtocolStr, L"TCP") == 0)) {
+ ISCSIDevPath->NetworkProtocol = 0;
+ } else {
+ //
+ // Undefined and reserved.
+ //
+ ISCSIDevPath->NetworkProtocol = 1;
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) ISCSIDevPath;
+}
+
+/**
+ Converts a text device path node to VLAN device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created VLAN device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVlan (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *VlanStr;
+ VLAN_DEVICE_PATH *Vlan;
+
+ VlanStr = GetNextParamStr (&TextDeviceNode);
+ Vlan = (VLAN_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_VLAN_DP,
+ (UINT16) sizeof (VLAN_DEVICE_PATH)
+ );
+
+ Vlan->VlanId = (UINT16) Strtoi (VlanStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Vlan;
+}
+
+/**
+ Converts a text device path node to Bluetooth device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Bluetooth device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextBluetooth (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *BluetoothStr;
+ BLUETOOTH_DEVICE_PATH *BluetoothDp;
+
+ BluetoothStr = GetNextParamStr (&TextDeviceNode);
+ BluetoothDp = (BLUETOOTH_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_BLUETOOTH_DP,
+ (UINT16) sizeof (BLUETOOTH_DEVICE_PATH)
+ );
+ StrHexToBytes (
+ BluetoothStr,
+ sizeof (BLUETOOTH_ADDRESS) * 2,
+ BluetoothDp->BD_ADDR.Address,
+ sizeof (BLUETOOTH_ADDRESS)
+ );
+ return (EFI_DEVICE_PATH_PROTOCOL *) BluetoothDp;
+}
+
+/**
+ Converts a text device path node to Wi-Fi device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Wi-Fi device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextWiFi (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *SSIdStr;
+ CHAR8 AsciiStr[33];
+ UINTN DataLen;
+ WIFI_DEVICE_PATH *WiFiDp;
+
+ SSIdStr = GetNextParamStr (&TextDeviceNode);
+ WiFiDp = (WIFI_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_WIFI_DP,
+ (UINT16) sizeof (WIFI_DEVICE_PATH)
+ );
+
+ if (NULL != SSIdStr) {
+ DataLen = StrLen (SSIdStr);
+ if (StrLen (SSIdStr) > 32) {
+ SSIdStr[32] = L'\0';
+ DataLen = 32;
+ }
+
+ UnicodeStrToAsciiStrS (SSIdStr, AsciiStr, sizeof (AsciiStr));
+ CopyMem (WiFiDp->SSId, AsciiStr, DataLen);
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) WiFiDp;
+}
+
+/**
+ Converts a text device path node to Bluetooth LE device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Bluetooth LE device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextBluetoothLE (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *BluetoothLeAddrStr;
+ CHAR16 *BluetoothLeAddrTypeStr;
+ BLUETOOTH_LE_DEVICE_PATH *BluetoothLeDp;
+
+ BluetoothLeAddrStr = GetNextParamStr (&TextDeviceNode);
+ BluetoothLeAddrTypeStr = GetNextParamStr (&TextDeviceNode);
+ BluetoothLeDp = (BLUETOOTH_LE_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_BLUETOOTH_LE_DP,
+ (UINT16) sizeof (BLUETOOTH_LE_DEVICE_PATH)
+ );
+
+ BluetoothLeDp->Address.Type = (UINT8) Strtoi (BluetoothLeAddrTypeStr);
+ StrHexToBytes (
+ BluetoothLeAddrStr, sizeof (BluetoothLeDp->Address.Address) * 2,
+ BluetoothLeDp->Address.Address, sizeof (BluetoothLeDp->Address.Address)
+ );
+ return (EFI_DEVICE_PATH_PROTOCOL *) BluetoothLeDp;
+}
+
+/**
+ Converts a text device path node to DNS device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created DNS device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextDns (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *DeviceNodeStr;
+ CHAR16 *DeviceNodeStrPtr;
+ UINT32 DnsServerIpCount;
+ UINT16 DnsDeviceNodeLength;
+ DNS_DEVICE_PATH *DnsDeviceNode;
+ UINT32 DnsServerIpIndex;
+ CHAR16 *DnsServerIp;
+
+
+ //
+ // Count the DNS server address number.
+ //
+ DeviceNodeStr = UefiDevicePathLibStrDuplicate (TextDeviceNode);
+ if (DeviceNodeStr == NULL) {
+ return NULL;
+ }
+
+ DeviceNodeStrPtr = DeviceNodeStr;
+
+ DnsServerIpCount = 0;
+ while (DeviceNodeStrPtr != NULL && *DeviceNodeStrPtr != L'\0') {
+ GetNextParamStr (&DeviceNodeStrPtr);
+ DnsServerIpCount ++;
+ }
+
+ FreePool (DeviceNodeStr);
+ DeviceNodeStr = NULL;
+
+ //
+ // One or more instances of the DNS server address in EFI_IP_ADDRESS,
+ // otherwise, NULL will be returned.
+ //
+ if (DnsServerIpCount == 0) {
+ return NULL;
+ }
+
+ //
+ // Create the DNS DeviceNode.
+ //
+ DnsDeviceNodeLength = (UINT16) (sizeof (EFI_DEVICE_PATH_PROTOCOL) + sizeof (UINT8) + DnsServerIpCount * sizeof (EFI_IP_ADDRESS));
+ DnsDeviceNode = (DNS_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_DNS_DP,
+ DnsDeviceNodeLength
+ );
+ if (DnsDeviceNode == NULL) {
+ return NULL;
+ }
+
+ //
+ // Confirm the DNS server address is IPv4 or IPv6 type.
+ //
+ DeviceNodeStrPtr = TextDeviceNode;
+ while (!IS_NULL (*DeviceNodeStrPtr)) {
+ if (*DeviceNodeStrPtr == L'.') {
+ DnsDeviceNode->IsIPv6 = 0x00;
+ break;
+ }
+
+ if (*DeviceNodeStrPtr == L':') {
+ DnsDeviceNode->IsIPv6 = 0x01;
+ break;
+ }
+
+ DeviceNodeStrPtr++;
+ }
+
+ for (DnsServerIpIndex = 0; DnsServerIpIndex < DnsServerIpCount; DnsServerIpIndex++) {
+ DnsServerIp = GetNextParamStr (&TextDeviceNode);
+ if (DnsDeviceNode->IsIPv6 == 0x00) {
+ StrToIpv4Address (DnsServerIp, NULL, &(DnsDeviceNode->DnsServerIp[DnsServerIpIndex].v4), NULL);
+ } else {
+ StrToIpv6Address (DnsServerIp, NULL, &(DnsDeviceNode->DnsServerIp[DnsServerIpIndex].v6), NULL);
+ }
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) DnsDeviceNode;
+}
+
+/**
+ Converts a text device path node to URI device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created URI device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextUri (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *UriStr;
+ UINTN UriLength;
+ URI_DEVICE_PATH *Uri;
+
+ UriStr = GetNextParamStr (&TextDeviceNode);
+ UriLength = StrnLenS (UriStr, MAX_UINT16 - sizeof (URI_DEVICE_PATH));
+ Uri = (URI_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_URI_DP,
+ (UINT16) (sizeof (URI_DEVICE_PATH) + UriLength)
+ );
+
+ while (UriLength-- != 0) {
+ Uri->Uri[UriLength] = (CHAR8) UriStr[UriLength];
+ }
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Uri;
+}
+
+/**
+ Converts a media text device path node to media device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to media device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextMediaPath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return DevPathFromTextGenericPath (MEDIA_DEVICE_PATH, TextDeviceNode);
+}
+
+/**
+ Converts a text device path node to HD device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created HD device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextHD (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *PartitionStr;
+ CHAR16 *TypeStr;
+ CHAR16 *SignatureStr;
+ CHAR16 *StartStr;
+ CHAR16 *SizeStr;
+ UINT32 Signature32;
+ HARDDRIVE_DEVICE_PATH *Hd;
+
+ PartitionStr = GetNextParamStr (&TextDeviceNode);
+ TypeStr = GetNextParamStr (&TextDeviceNode);
+ SignatureStr = GetNextParamStr (&TextDeviceNode);
+ StartStr = GetNextParamStr (&TextDeviceNode);
+ SizeStr = GetNextParamStr (&TextDeviceNode);
+ Hd = (HARDDRIVE_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_HARDDRIVE_DP,
+ (UINT16) sizeof (HARDDRIVE_DEVICE_PATH)
+ );
+
+ Hd->PartitionNumber = (UINT32) Strtoi (PartitionStr);
+
+ ZeroMem (Hd->Signature, 16);
+ Hd->MBRType = (UINT8) 0;
+
+ if (StrCmp (TypeStr, L"MBR") == 0) {
+ Hd->SignatureType = SIGNATURE_TYPE_MBR;
+ Hd->MBRType = 0x01;
+
+ Signature32 = (UINT32) Strtoi (SignatureStr);
+ CopyMem (Hd->Signature, &Signature32, sizeof (UINT32));
+ } else if (StrCmp (TypeStr, L"GPT") == 0) {
+ Hd->SignatureType = SIGNATURE_TYPE_GUID;
+ Hd->MBRType = 0x02;
+
+ StrToGuid (SignatureStr, (EFI_GUID *) Hd->Signature);
+ } else {
+ Hd->SignatureType = (UINT8) Strtoi (TypeStr);
+ }
+
+ Strtoi64 (StartStr, &Hd->PartitionStart);
+ Strtoi64 (SizeStr, &Hd->PartitionSize);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Hd;
+}
+
+/**
+ Converts a text device path node to CDROM device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created CDROM device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextCDROM (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *EntryStr;
+ CHAR16 *StartStr;
+ CHAR16 *SizeStr;
+ CDROM_DEVICE_PATH *CDROMDevPath;
+
+ EntryStr = GetNextParamStr (&TextDeviceNode);
+ StartStr = GetNextParamStr (&TextDeviceNode);
+ SizeStr = GetNextParamStr (&TextDeviceNode);
+ CDROMDevPath = (CDROM_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_CDROM_DP,
+ (UINT16) sizeof (CDROM_DEVICE_PATH)
+ );
+
+ CDROMDevPath->BootEntry = (UINT32) Strtoi (EntryStr);
+ Strtoi64 (StartStr, &CDROMDevPath->PartitionStart);
+ Strtoi64 (SizeStr, &CDROMDevPath->PartitionSize);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) CDROMDevPath;
+}
+
+/**
+ Converts a text device path node to Vendor-defined media device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Vendor-defined media device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVenMedia (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return ConvertFromTextVendor (
+ TextDeviceNode,
+ MEDIA_DEVICE_PATH,
+ MEDIA_VENDOR_DP
+ );
+}
+
+/**
+ Converts a text device path node to File device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created File device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFilePath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ FILEPATH_DEVICE_PATH *File;
+
+ File = (FILEPATH_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_FILEPATH_DP,
+ (UINT16) (sizeof (FILEPATH_DEVICE_PATH) + StrLen (TextDeviceNode) * 2)
+ );
+
+ StrCpyS (File->PathName, StrLen (TextDeviceNode) + 1, TextDeviceNode);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) File;
+}
+
+/**
+ Converts a text device path node to Media protocol device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Media protocol device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextMedia (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *GuidStr;
+ MEDIA_PROTOCOL_DEVICE_PATH *Media;
+
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+ Media = (MEDIA_PROTOCOL_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_PROTOCOL_DP,
+ (UINT16) sizeof (MEDIA_PROTOCOL_DEVICE_PATH)
+ );
+
+ StrToGuid (GuidStr, &Media->Protocol);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Media;
+}
+
+/**
+ Converts a text device path node to firmware volume device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created firmware volume device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFv (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *GuidStr;
+ MEDIA_FW_VOL_DEVICE_PATH *Fv;
+
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+ Fv = (MEDIA_FW_VOL_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_PIWG_FW_VOL_DP,
+ (UINT16) sizeof (MEDIA_FW_VOL_DEVICE_PATH)
+ );
+
+ StrToGuid (GuidStr, &Fv->FvName);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Fv;
+}
+
+/**
+ Converts a text device path node to firmware file device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created firmware file device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextFvFile (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *GuidStr;
+ MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvFile;
+
+ GuidStr = GetNextParamStr (&TextDeviceNode);
+ FvFile = (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_PIWG_FW_FILE_DP,
+ (UINT16) sizeof (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH)
+ );
+
+ StrToGuid (GuidStr, &FvFile->FvFileName);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) FvFile;
+}
+
+/**
+ Converts a text device path node to text relative offset device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextRelativeOffsetRange (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingOffsetStr;
+ CHAR16 *EndingOffsetStr;
+ MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH *Offset;
+
+ StartingOffsetStr = GetNextParamStr (&TextDeviceNode);
+ EndingOffsetStr = GetNextParamStr (&TextDeviceNode);
+ Offset = (MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RELATIVE_OFFSET_RANGE_DP,
+ (UINT16) sizeof (MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingOffsetStr, &Offset->StartingOffset);
+ Strtoi64 (EndingOffsetStr, &Offset->EndingOffset);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Offset;
+}
+
+/**
+ Converts a text device path node to text ram disk device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextRamDisk (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingAddrStr;
+ CHAR16 *EndingAddrStr;
+ CHAR16 *TypeGuidStr;
+ CHAR16 *InstanceStr;
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+ UINT64 StartingAddr;
+ UINT64 EndingAddr;
+
+ StartingAddrStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddrStr = GetNextParamStr (&TextDeviceNode);
+ InstanceStr = GetNextParamStr (&TextDeviceNode);
+ TypeGuidStr = GetNextParamStr (&TextDeviceNode);
+ RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RAM_DISK_DP,
+ (UINT16) sizeof (MEDIA_RAM_DISK_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingAddrStr, &StartingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->StartingAddr[0]), StartingAddr);
+ Strtoi64 (EndingAddrStr, &EndingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->EndingAddr[0]), EndingAddr);
+ RamDisk->Instance = (UINT16) Strtoi (InstanceStr);
+ StrToGuid (TypeGuidStr, &RamDisk->TypeGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) RamDisk;
+}
+
+/**
+ Converts a text device path node to text virtual disk device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVirtualDisk (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingAddrStr;
+ CHAR16 *EndingAddrStr;
+ CHAR16 *InstanceStr;
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+ UINT64 StartingAddr;
+ UINT64 EndingAddr;
+
+ StartingAddrStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddrStr = GetNextParamStr (&TextDeviceNode);
+ InstanceStr = GetNextParamStr (&TextDeviceNode);
+
+ RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RAM_DISK_DP,
+ (UINT16) sizeof (MEDIA_RAM_DISK_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingAddrStr, &StartingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->StartingAddr[0]), StartingAddr);
+ Strtoi64 (EndingAddrStr, &EndingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->EndingAddr[0]), EndingAddr);
+ RamDisk->Instance = (UINT16) Strtoi (InstanceStr);
+ CopyGuid (&RamDisk->TypeGuid, &gEfiVirtualDiskGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) RamDisk;
+}
+
+/**
+ Converts a text device path node to text virtual cd device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextVirtualCd (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingAddrStr;
+ CHAR16 *EndingAddrStr;
+ CHAR16 *InstanceStr;
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+ UINT64 StartingAddr;
+ UINT64 EndingAddr;
+
+ StartingAddrStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddrStr = GetNextParamStr (&TextDeviceNode);
+ InstanceStr = GetNextParamStr (&TextDeviceNode);
+
+ RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RAM_DISK_DP,
+ (UINT16) sizeof (MEDIA_RAM_DISK_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingAddrStr, &StartingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->StartingAddr[0]), StartingAddr);
+ Strtoi64 (EndingAddrStr, &EndingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->EndingAddr[0]), EndingAddr);
+ RamDisk->Instance = (UINT16) Strtoi (InstanceStr);
+ CopyGuid (&RamDisk->TypeGuid, &gEfiVirtualCdGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) RamDisk;
+}
+
+/**
+ Converts a text device path node to text persistent virtual disk device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPersistentVirtualDisk (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingAddrStr;
+ CHAR16 *EndingAddrStr;
+ CHAR16 *InstanceStr;
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+ UINT64 StartingAddr;
+ UINT64 EndingAddr;
+
+ StartingAddrStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddrStr = GetNextParamStr (&TextDeviceNode);
+ InstanceStr = GetNextParamStr (&TextDeviceNode);
+
+ RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RAM_DISK_DP,
+ (UINT16) sizeof (MEDIA_RAM_DISK_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingAddrStr, &StartingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->StartingAddr[0]), StartingAddr);
+ Strtoi64 (EndingAddrStr, &EndingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->EndingAddr[0]), EndingAddr);
+ RamDisk->Instance = (UINT16) Strtoi (InstanceStr);
+ CopyGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualDiskGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) RamDisk;
+}
+
+/**
+ Converts a text device path node to text persistent virtual cd device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created Text device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextPersistentVirtualCd (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *StartingAddrStr;
+ CHAR16 *EndingAddrStr;
+ CHAR16 *InstanceStr;
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+ UINT64 StartingAddr;
+ UINT64 EndingAddr;
+
+ StartingAddrStr = GetNextParamStr (&TextDeviceNode);
+ EndingAddrStr = GetNextParamStr (&TextDeviceNode);
+ InstanceStr = GetNextParamStr (&TextDeviceNode);
+
+ RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *) CreateDeviceNode (
+ MEDIA_DEVICE_PATH,
+ MEDIA_RAM_DISK_DP,
+ (UINT16) sizeof (MEDIA_RAM_DISK_DEVICE_PATH)
+ );
+
+ Strtoi64 (StartingAddrStr, &StartingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->StartingAddr[0]), StartingAddr);
+ Strtoi64 (EndingAddrStr, &EndingAddr);
+ WriteUnaligned64 ((UINT64 *) &(RamDisk->EndingAddr[0]), EndingAddr);
+ RamDisk->Instance = (UINT16) Strtoi (InstanceStr);
+ CopyGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualCdGuid);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) RamDisk;
+}
+
+/**
+ Converts a BBS text device path node to BBS device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to BBS device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextBbsPath (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ return DevPathFromTextGenericPath (BBS_DEVICE_PATH, TextDeviceNode);
+}
+
+/**
+ Converts a text device path node to BIOS Boot Specification device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created BIOS Boot Specification device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextBBS (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ CHAR16 *TypeStr;
+ CHAR16 *IdStr;
+ CHAR16 *FlagsStr;
+ CHAR8 *AsciiStr;
+ BBS_BBS_DEVICE_PATH *Bbs;
+
+ TypeStr = GetNextParamStr (&TextDeviceNode);
+ IdStr = GetNextParamStr (&TextDeviceNode);
+ FlagsStr = GetNextParamStr (&TextDeviceNode);
+ Bbs = (BBS_BBS_DEVICE_PATH *) CreateDeviceNode (
+ BBS_DEVICE_PATH,
+ BBS_BBS_DP,
+ (UINT16) (sizeof (BBS_BBS_DEVICE_PATH) + StrLen (IdStr))
+ );
+
+ if (StrCmp (TypeStr, L"Floppy") == 0) {
+ Bbs->DeviceType = BBS_TYPE_FLOPPY;
+ } else if (StrCmp (TypeStr, L"HD") == 0) {
+ Bbs->DeviceType = BBS_TYPE_HARDDRIVE;
+ } else if (StrCmp (TypeStr, L"CDROM") == 0) {
+ Bbs->DeviceType = BBS_TYPE_CDROM;
+ } else if (StrCmp (TypeStr, L"PCMCIA") == 0) {
+ Bbs->DeviceType = BBS_TYPE_PCMCIA;
+ } else if (StrCmp (TypeStr, L"USB") == 0) {
+ Bbs->DeviceType = BBS_TYPE_USB;
+ } else if (StrCmp (TypeStr, L"Network") == 0) {
+ Bbs->DeviceType = BBS_TYPE_EMBEDDED_NETWORK;
+ } else {
+ Bbs->DeviceType = (UINT16) Strtoi (TypeStr);
+ }
+
+ AsciiStr = Bbs->String;
+ StrToAscii (IdStr, &AsciiStr);
+
+ Bbs->StatusFlag = (UINT16) Strtoi (FlagsStr);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Bbs;
+}
+
+/**
+ Converts a text device path node to SATA device path structure.
+
+ @param TextDeviceNode The input Text device path node.
+
+ @return A pointer to the newly-created SATA device path structure.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+DevPathFromTextSata (
+ IN CHAR16 *TextDeviceNode
+ )
+{
+ SATA_DEVICE_PATH *Sata;
+ CHAR16 *Param1;
+ CHAR16 *Param2;
+ CHAR16 *Param3;
+
+ Param1 = GetNextParamStr (&TextDeviceNode);
+ Param2 = GetNextParamStr (&TextDeviceNode);
+ Param3 = GetNextParamStr (&TextDeviceNode);
+
+ Sata = (SATA_DEVICE_PATH *) CreateDeviceNode (
+ MESSAGING_DEVICE_PATH,
+ MSG_SATA_DP,
+ (UINT16) sizeof (SATA_DEVICE_PATH)
+ );
+ Sata->HBAPortNumber = (UINT16) Strtoi (Param1);
+
+ //
+ // According to UEFI spec, if PMPN is not provided, the default is 0xFFFF
+ //
+ if (*Param2 == L'\0' ) {
+ Sata->PortMultiplierPortNumber = 0xFFFF;
+ } else {
+ Sata->PortMultiplierPortNumber = (UINT16) Strtoi (Param2);
+ }
+ Sata->Lun = (UINT16) Strtoi (Param3);
+
+ return (EFI_DEVICE_PATH_PROTOCOL *) Sata;
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED DEVICE_PATH_FROM_TEXT_TABLE mUefiDevicePathLibDevPathFromTextTable[] = {
+ {L"Path", DevPathFromTextPath },
+
+ {L"HardwarePath", DevPathFromTextHardwarePath },
+ {L"Pci", DevPathFromTextPci },
+ {L"PcCard", DevPathFromTextPcCard },
+ {L"MemoryMapped", DevPathFromTextMemoryMapped },
+ {L"VenHw", DevPathFromTextVenHw },
+ {L"Ctrl", DevPathFromTextCtrl },
+ {L"BMC", DevPathFromTextBmc },
+
+ {L"AcpiPath", DevPathFromTextAcpiPath },
+ {L"Acpi", DevPathFromTextAcpi },
+ {L"PciRoot", DevPathFromTextPciRoot },
+ {L"PcieRoot", DevPathFromTextPcieRoot },
+ {L"Floppy", DevPathFromTextFloppy },
+ {L"Keyboard", DevPathFromTextKeyboard },
+ {L"Serial", DevPathFromTextSerial },
+ {L"ParallelPort", DevPathFromTextParallelPort },
+ {L"AcpiEx", DevPathFromTextAcpiEx },
+ {L"AcpiExp", DevPathFromTextAcpiExp },
+ {L"AcpiAdr", DevPathFromTextAcpiAdr },
+
+ {L"Msg", DevPathFromTextMsg },
+ {L"Ata", DevPathFromTextAta },
+ {L"Scsi", DevPathFromTextScsi },
+ {L"Fibre", DevPathFromTextFibre },
+ {L"FibreEx", DevPathFromTextFibreEx },
+ {L"I1394", DevPathFromText1394 },
+ {L"USB", DevPathFromTextUsb },
+ {L"I2O", DevPathFromTextI2O },
+ {L"Infiniband", DevPathFromTextInfiniband },
+ {L"VenMsg", DevPathFromTextVenMsg },
+ {L"VenPcAnsi", DevPathFromTextVenPcAnsi },
+ {L"VenVt100", DevPathFromTextVenVt100 },
+ {L"VenVt100Plus", DevPathFromTextVenVt100Plus },
+ {L"VenUtf8", DevPathFromTextVenUtf8 },
+ {L"UartFlowCtrl", DevPathFromTextUartFlowCtrl },
+ {L"SAS", DevPathFromTextSAS },
+ {L"SasEx", DevPathFromTextSasEx },
+ {L"NVMe", DevPathFromTextNVMe },
+ {L"UFS", DevPathFromTextUfs },
+ {L"SD", DevPathFromTextSd },
+ {L"eMMC", DevPathFromTextEmmc },
+ {L"DebugPort", DevPathFromTextDebugPort },
+ {L"MAC", DevPathFromTextMAC },
+ {L"IPv4", DevPathFromTextIPv4 },
+ {L"IPv6", DevPathFromTextIPv6 },
+ {L"Uart", DevPathFromTextUart },
+ {L"UsbClass", DevPathFromTextUsbClass },
+ {L"UsbAudio", DevPathFromTextUsbAudio },
+ {L"UsbCDCControl", DevPathFromTextUsbCDCControl },
+ {L"UsbHID", DevPathFromTextUsbHID },
+ {L"UsbImage", DevPathFromTextUsbImage },
+ {L"UsbPrinter", DevPathFromTextUsbPrinter },
+ {L"UsbMassStorage", DevPathFromTextUsbMassStorage },
+ {L"UsbHub", DevPathFromTextUsbHub },
+ {L"UsbCDCData", DevPathFromTextUsbCDCData },
+ {L"UsbSmartCard", DevPathFromTextUsbSmartCard },
+ {L"UsbVideo", DevPathFromTextUsbVideo },
+ {L"UsbDiagnostic", DevPathFromTextUsbDiagnostic },
+ {L"UsbWireless", DevPathFromTextUsbWireless },
+ {L"UsbDeviceFirmwareUpdate", DevPathFromTextUsbDeviceFirmwareUpdate },
+ {L"UsbIrdaBridge", DevPathFromTextUsbIrdaBridge },
+ {L"UsbTestAndMeasurement", DevPathFromTextUsbTestAndMeasurement },
+ {L"UsbWwid", DevPathFromTextUsbWwid },
+ {L"Unit", DevPathFromTextUnit },
+ {L"iSCSI", DevPathFromTextiSCSI },
+ {L"Vlan", DevPathFromTextVlan },
+ {L"Dns", DevPathFromTextDns },
+ {L"Uri", DevPathFromTextUri },
+ {L"Bluetooth", DevPathFromTextBluetooth },
+ {L"Wi-Fi", DevPathFromTextWiFi },
+ {L"BluetoothLE", DevPathFromTextBluetoothLE },
+ {L"MediaPath", DevPathFromTextMediaPath },
+ {L"HD", DevPathFromTextHD },
+ {L"CDROM", DevPathFromTextCDROM },
+ {L"VenMedia", DevPathFromTextVenMedia },
+ {L"Media", DevPathFromTextMedia },
+ {L"Fv", DevPathFromTextFv },
+ {L"FvFile", DevPathFromTextFvFile },
+ {L"Offset", DevPathFromTextRelativeOffsetRange },
+ {L"RamDisk", DevPathFromTextRamDisk },
+ {L"VirtualDisk", DevPathFromTextVirtualDisk },
+ {L"VirtualCD", DevPathFromTextVirtualCd },
+ {L"PersistentVirtualDisk", DevPathFromTextPersistentVirtualDisk },
+ {L"PersistentVirtualCD", DevPathFromTextPersistentVirtualCd },
+
+ {L"BbsPath", DevPathFromTextBbsPath },
+ {L"BBS", DevPathFromTextBBS },
+ {L"Sata", DevPathFromTextSata },
+ {NULL, NULL}
+};
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was
+ insufficient memory or text unsupported.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibConvertTextToDeviceNode (
+ IN CONST CHAR16 *TextDeviceNode
+ )
+{
+ DEVICE_PATH_FROM_TEXT FromText;
+ CHAR16 *ParamStr;
+ EFI_DEVICE_PATH_PROTOCOL *DeviceNode;
+ CHAR16 *DeviceNodeStr;
+ UINTN Index;
+
+ if ((TextDeviceNode == NULL) || (IS_NULL (*TextDeviceNode))) {
+ return NULL;
+ }
+
+ ParamStr = NULL;
+ FromText = NULL;
+ DeviceNodeStr = UefiDevicePathLibStrDuplicate (TextDeviceNode);
+ ASSERT (DeviceNodeStr != NULL);
+
+ for (Index = 0; mUefiDevicePathLibDevPathFromTextTable[Index].Function != NULL; Index++) {
+ ParamStr = GetParamByNodeName (DeviceNodeStr, mUefiDevicePathLibDevPathFromTextTable[Index].DevicePathNodeText);
+ if (ParamStr != NULL) {
+ FromText = mUefiDevicePathLibDevPathFromTextTable[Index].Function;
+ break;
+ }
+ }
+
+ if (FromText == NULL) {
+ //
+ // A file path
+ //
+ FromText = DevPathFromTextFilePath;
+ DeviceNode = FromText (DeviceNodeStr);
+ } else {
+ DeviceNode = FromText (ParamStr);
+ FreePool (ParamStr);
+ }
+
+ FreePool (DeviceNodeStr);
+
+ return DeviceNode;
+}
+
+/**
+ Convert text to the binary representation of a device path.
+
+
+ @param TextDevicePath TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or
+ there was insufficient memory.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibConvertTextToDevicePath (
+ IN CONST CHAR16 *TextDevicePath
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *DeviceNode;
+ EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
+ CHAR16 *DevicePathStr;
+ CHAR16 *Str;
+ CHAR16 *DeviceNodeStr;
+ BOOLEAN IsInstanceEnd;
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath;
+
+ if ((TextDevicePath == NULL) || (IS_NULL (*TextDevicePath))) {
+ return NULL;
+ }
+
+ DevicePath = (EFI_DEVICE_PATH_PROTOCOL *) AllocatePool (END_DEVICE_PATH_LENGTH);
+ ASSERT (DevicePath != NULL);
+ SetDevicePathEndNode (DevicePath);
+
+ DevicePathStr = UefiDevicePathLibStrDuplicate (TextDevicePath);
+
+ Str = DevicePathStr;
+ while ((DeviceNodeStr = GetNextDeviceNodeStr (&Str, &IsInstanceEnd)) != NULL) {
+ DeviceNode = UefiDevicePathLibConvertTextToDeviceNode (DeviceNodeStr);
+
+ NewDevicePath = AppendDevicePathNode (DevicePath, DeviceNode);
+ FreePool (DevicePath);
+ FreePool (DeviceNode);
+ DevicePath = NewDevicePath;
+
+ if (IsInstanceEnd) {
+ DeviceNode = (EFI_DEVICE_PATH_PROTOCOL *) AllocatePool (END_DEVICE_PATH_LENGTH);
+ ASSERT (DeviceNode != NULL);
+ SetDevicePathEndNode (DeviceNode);
+ DeviceNode->SubType = END_INSTANCE_DEVICE_PATH_SUBTYPE;
+
+ NewDevicePath = AppendDevicePathNode (DevicePath, DeviceNode);
+ FreePool (DevicePath);
+ FreePool (DeviceNode);
+ DevicePath = NewDevicePath;
+ }
+ }
+
+ FreePool (DevicePathStr);
+ return DevicePath;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathToText.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathToText.c
new file mode 100644
index 0000000..fb65ebd
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathToText.c
@@ -0,0 +1,2455 @@
+/** @file
+ DevicePathToText protocol as defined in the UEFI 2.0 specification.
+
+ (C) Copyright 2015 Hewlett-Packard Development Company, L.P.<BR>
+Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiDevicePathLib.h"
+
+/**
+ Concatenates a formatted unicode string to allocated pool. The caller must
+ free the resulting buffer.
+
+ @param Str Tracks the allocated pool, size in use, and
+ amount of pool allocated.
+ @param Fmt The format string
+ @param ... Variable arguments based on the format string.
+
+ @return Allocated buffer with the formatted string printed in it.
+ The caller must free the allocated buffer. The buffer
+ allocation is not packed.
+
+**/
+CHAR16 *
+EFIAPI
+UefiDevicePathLibCatPrint (
+ IN OUT POOL_PRINT *Str,
+ IN CHAR16 *Fmt,
+ ...
+ )
+{
+ UINTN Count;
+ VA_LIST Args;
+
+ VA_START (Args, Fmt);
+ Count = SPrintLength (Fmt, Args);
+ VA_END(Args);
+
+ if ((Str->Count + (Count + 1)) * sizeof (CHAR16) > Str->Capacity) {
+ Str->Capacity = (Str->Count + (Count + 1) * 2) * sizeof (CHAR16);
+ Str->Str = ReallocatePool (
+ Str->Count * sizeof (CHAR16),
+ Str->Capacity,
+ Str->Str
+ );
+ ASSERT (Str->Str != NULL);
+ }
+ VA_START (Args, Fmt);
+ UnicodeVSPrint (&Str->Str[Str->Count], Str->Capacity - Str->Count * sizeof (CHAR16), Fmt, Args);
+ Str->Count += Count;
+
+ VA_END (Args);
+ return Str->Str;
+}
+
+/**
+ Converts a PCI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextPci (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ PCI_DEVICE_PATH *Pci;
+
+ Pci = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Pci(0x%x,0x%x)", Pci->Device, Pci->Function);
+}
+
+/**
+ Converts a PC Card device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextPccard (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ PCCARD_DEVICE_PATH *Pccard;
+
+ Pccard = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"PcCard(0x%x)", Pccard->FunctionNumber);
+}
+
+/**
+ Converts a Memory Map device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextMemMap (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEMMAP_DEVICE_PATH *MemMap;
+
+ MemMap = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"MemoryMapped(0x%x,0x%lx,0x%lx)",
+ MemMap->MemoryType,
+ MemMap->StartingAddress,
+ MemMap->EndingAddress
+ );
+}
+
+/**
+ Converts a Vendor device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextVendor (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ VENDOR_DEVICE_PATH *Vendor;
+ CHAR16 *Type;
+ UINTN Index;
+ UINTN DataLength;
+ UINT32 FlowControlMap;
+ UINT16 Info;
+
+ Vendor = (VENDOR_DEVICE_PATH *) DevPath;
+ switch (DevicePathType (&Vendor->Header)) {
+ case HARDWARE_DEVICE_PATH:
+ Type = L"Hw";
+ break;
+
+ case MESSAGING_DEVICE_PATH:
+ Type = L"Msg";
+ if (AllowShortcuts) {
+ if (CompareGuid (&Vendor->Guid, &gEfiPcAnsiGuid)) {
+ UefiDevicePathLibCatPrint (Str, L"VenPcAnsi()");
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiVT100Guid)) {
+ UefiDevicePathLibCatPrint (Str, L"VenVt100()");
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiVT100PlusGuid)) {
+ UefiDevicePathLibCatPrint (Str, L"VenVt100Plus()");
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiVTUTF8Guid)) {
+ UefiDevicePathLibCatPrint (Str, L"VenUtf8()");
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiUartDevicePathGuid)) {
+ FlowControlMap = (((UART_FLOW_CONTROL_DEVICE_PATH *) Vendor)->FlowControlMap);
+ switch (FlowControlMap & 0x00000003) {
+ case 0:
+ UefiDevicePathLibCatPrint (Str, L"UartFlowCtrl(%s)", L"None");
+ break;
+
+ case 1:
+ UefiDevicePathLibCatPrint (Str, L"UartFlowCtrl(%s)", L"Hardware");
+ break;
+
+ case 2:
+ UefiDevicePathLibCatPrint (Str, L"UartFlowCtrl(%s)", L"XonXoff");
+ break;
+
+ default:
+ break;
+ }
+
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiSasDevicePathGuid)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"SAS(0x%lx,0x%lx,0x%x,",
+ ((SAS_DEVICE_PATH *) Vendor)->SasAddress,
+ ((SAS_DEVICE_PATH *) Vendor)->Lun,
+ ((SAS_DEVICE_PATH *) Vendor)->RelativeTargetPort
+ );
+ Info = (((SAS_DEVICE_PATH *) Vendor)->DeviceTopology);
+ if (((Info & 0x0f) == 0) && ((Info & BIT7) == 0)) {
+ UefiDevicePathLibCatPrint (Str, L"NoTopology,0,0,0,");
+ } else if (((Info & 0x0f) <= 2) && ((Info & BIT7) == 0)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"%s,%s,%s,",
+ ((Info & BIT4) != 0) ? L"SATA" : L"SAS",
+ ((Info & BIT5) != 0) ? L"External" : L"Internal",
+ ((Info & BIT6) != 0) ? L"Expanded" : L"Direct"
+ );
+ if ((Info & 0x0f) == 1) {
+ UefiDevicePathLibCatPrint (Str, L"0,");
+ } else {
+ //
+ // Value 0x0 thru 0xFF -> Drive 1 thru Drive 256
+ //
+ UefiDevicePathLibCatPrint (Str, L"0x%x,", ((Info >> 8) & 0xff) + 1);
+ }
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"0x%x,0,0,0,", Info);
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"0x%x)", ((SAS_DEVICE_PATH *) Vendor)->Reserved);
+ return ;
+ } else if (CompareGuid (&Vendor->Guid, &gEfiDebugPortProtocolGuid)) {
+ UefiDevicePathLibCatPrint (Str, L"DebugPort()");
+ return ;
+ }
+ }
+ break;
+
+ case MEDIA_DEVICE_PATH:
+ Type = L"Media";
+ break;
+
+ default:
+ Type = L"?";
+ break;
+ }
+
+ DataLength = DevicePathNodeLength (&Vendor->Header) - sizeof (VENDOR_DEVICE_PATH);
+ UefiDevicePathLibCatPrint (Str, L"Ven%s(%g", Type, &Vendor->Guid);
+ if (DataLength != 0) {
+ UefiDevicePathLibCatPrint (Str, L",");
+ for (Index = 0; Index < DataLength; Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", ((VENDOR_DEVICE_PATH_WITH_DATA *) Vendor)->VendorDefinedData[Index]);
+ }
+ }
+
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts a Controller device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextController (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ CONTROLLER_DEVICE_PATH *Controller;
+
+ Controller = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Ctrl(0x%x)",
+ Controller->ControllerNumber
+ );
+}
+
+/**
+ Converts a BMC device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextBmc (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ BMC_DEVICE_PATH *Bmc;
+
+ Bmc = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"BMC(0x%x,0x%lx)",
+ Bmc->InterfaceType,
+ ReadUnaligned64 ((UINT64 *) (&Bmc->BaseAddress))
+ );
+}
+
+/**
+ Converts a ACPI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextAcpi (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ ACPI_HID_DEVICE_PATH *Acpi;
+
+ Acpi = DevPath;
+ if ((Acpi->HID & PNP_EISA_ID_MASK) == PNP_EISA_ID_CONST) {
+ switch (EISA_ID_TO_NUM (Acpi->HID)) {
+ case 0x0a03:
+ UefiDevicePathLibCatPrint (Str, L"PciRoot(0x%x)", Acpi->UID);
+ break;
+
+ case 0x0a08:
+ UefiDevicePathLibCatPrint (Str, L"PcieRoot(0x%x)", Acpi->UID);
+ break;
+
+ case 0x0604:
+ UefiDevicePathLibCatPrint (Str, L"Floppy(0x%x)", Acpi->UID);
+ break;
+
+ case 0x0301:
+ UefiDevicePathLibCatPrint (Str, L"Keyboard(0x%x)", Acpi->UID);
+ break;
+
+ case 0x0501:
+ UefiDevicePathLibCatPrint (Str, L"Serial(0x%x)", Acpi->UID);
+ break;
+
+ case 0x0401:
+ UefiDevicePathLibCatPrint (Str, L"ParallelPort(0x%x)", Acpi->UID);
+ break;
+
+ default:
+ UefiDevicePathLibCatPrint (Str, L"Acpi(PNP%04x,0x%x)", EISA_ID_TO_NUM (Acpi->HID), Acpi->UID);
+ break;
+ }
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"Acpi(0x%08x,0x%x)", Acpi->HID, Acpi->UID);
+ }
+}
+
+/**
+ Converts a ACPI extended HID device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextAcpiEx (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ ACPI_EXTENDED_HID_DEVICE_PATH *AcpiEx;
+ CHAR8 *HIDStr;
+ CHAR8 *UIDStr;
+ CHAR8 *CIDStr;
+ CHAR16 HIDText[11];
+ CHAR16 CIDText[11];
+
+ AcpiEx = DevPath;
+ HIDStr = (CHAR8 *) (((UINT8 *) AcpiEx) + sizeof (ACPI_EXTENDED_HID_DEVICE_PATH));
+ UIDStr = HIDStr + AsciiStrLen (HIDStr) + 1;
+ CIDStr = UIDStr + AsciiStrLen (UIDStr) + 1;
+
+ if (DisplayOnly) {
+ if ((EISA_ID_TO_NUM (AcpiEx->HID) == 0x0A03) ||
+ (EISA_ID_TO_NUM (AcpiEx->CID) == 0x0A03 && EISA_ID_TO_NUM (AcpiEx->HID) != 0x0A08)) {
+ if (AcpiEx->UID == 0) {
+ UefiDevicePathLibCatPrint (Str, L"PciRoot(%a)", UIDStr);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"PciRoot(0x%x)", AcpiEx->UID);
+ }
+ return;
+ }
+
+ if (EISA_ID_TO_NUM (AcpiEx->HID) == 0x0A08 || EISA_ID_TO_NUM (AcpiEx->CID) == 0x0A08) {
+ if (AcpiEx->UID == 0) {
+ UefiDevicePathLibCatPrint (Str, L"PcieRoot(%a)", UIDStr);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"PcieRoot(0x%x)", AcpiEx->UID);
+ }
+ return;
+ }
+ }
+
+ //
+ // Converts EISA identification to string.
+ //
+ UnicodeSPrint (
+ HIDText,
+ sizeof (HIDText),
+ L"%c%c%c%04X",
+ ((AcpiEx->HID >> 10) & 0x1f) + 'A' - 1,
+ ((AcpiEx->HID >> 5) & 0x1f) + 'A' - 1,
+ ((AcpiEx->HID >> 0) & 0x1f) + 'A' - 1,
+ (AcpiEx->HID >> 16) & 0xFFFF
+ );
+ UnicodeSPrint (
+ CIDText,
+ sizeof (CIDText),
+ L"%c%c%c%04X",
+ ((AcpiEx->CID >> 10) & 0x1f) + 'A' - 1,
+ ((AcpiEx->CID >> 5) & 0x1f) + 'A' - 1,
+ ((AcpiEx->CID >> 0) & 0x1f) + 'A' - 1,
+ (AcpiEx->CID >> 16) & 0xFFFF
+ );
+
+ if ((*HIDStr == '\0') && (*CIDStr == '\0') && (*UIDStr != '\0')) {
+ //
+ // use AcpiExp()
+ //
+ if (AcpiEx->CID == 0) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"AcpiExp(%s,0,%a)",
+ HIDText,
+ UIDStr
+ );
+ } else {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"AcpiExp(%s,%s,%a)",
+ HIDText,
+ CIDText,
+ UIDStr
+ );
+ }
+ } else {
+ if (DisplayOnly) {
+ //
+ // display only
+ //
+ if (AcpiEx->HID == 0) {
+ UefiDevicePathLibCatPrint (Str, L"AcpiEx(%a,", HIDStr);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"AcpiEx(%s,", HIDText);
+ }
+
+ if (AcpiEx->CID == 0) {
+ UefiDevicePathLibCatPrint (Str, L"%a,", CIDStr);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"%s,", CIDText);
+ }
+
+ if (AcpiEx->UID == 0) {
+ UefiDevicePathLibCatPrint (Str, L"%a)", UIDStr);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"0x%x)", AcpiEx->UID);
+ }
+ } else {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"AcpiEx(%s,%s,0x%x,%a,%a,%a)",
+ HIDText,
+ CIDText,
+ AcpiEx->UID,
+ HIDStr,
+ CIDStr,
+ UIDStr
+ );
+ }
+ }
+}
+
+/**
+ Converts a ACPI address device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextAcpiAdr (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ ACPI_ADR_DEVICE_PATH *AcpiAdr;
+ UINT16 Index;
+ UINT16 Length;
+ UINT16 AdditionalAdrCount;
+
+ AcpiAdr = DevPath;
+ Length = (UINT16) DevicePathNodeLength ((EFI_DEVICE_PATH_PROTOCOL *) AcpiAdr);
+ AdditionalAdrCount = (UINT16) ((Length - 8) / 4);
+
+ UefiDevicePathLibCatPrint (Str, L"AcpiAdr(0x%x", AcpiAdr->ADR);
+ for (Index = 0; Index < AdditionalAdrCount; Index++) {
+ UefiDevicePathLibCatPrint (Str, L",0x%x", *(UINT32 *) ((UINT8 *) AcpiAdr + 8 + Index * 4));
+ }
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts a ATAPI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextAtapi (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ ATAPI_DEVICE_PATH *Atapi;
+
+ Atapi = DevPath;
+
+ if (DisplayOnly) {
+ UefiDevicePathLibCatPrint (Str, L"Ata(0x%x)", Atapi->Lun);
+ } else {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Ata(%s,%s,0x%x)",
+ (Atapi->PrimarySecondary == 1) ? L"Secondary" : L"Primary",
+ (Atapi->SlaveMaster == 1) ? L"Slave" : L"Master",
+ Atapi->Lun
+ );
+ }
+}
+
+/**
+ Converts a SCSI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextScsi (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ SCSI_DEVICE_PATH *Scsi;
+
+ Scsi = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Scsi(0x%x,0x%x)", Scsi->Pun, Scsi->Lun);
+}
+
+/**
+ Converts a Fibre device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextFibre (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ FIBRECHANNEL_DEVICE_PATH *Fibre;
+
+ Fibre = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Fibre(0x%lx,0x%lx)", Fibre->WWN, Fibre->Lun);
+}
+
+/**
+ Converts a FibreEx device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextFibreEx (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ FIBRECHANNELEX_DEVICE_PATH *FibreEx;
+ UINTN Index;
+
+ FibreEx = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"FibreEx(0x");
+ for (Index = 0; Index < sizeof (FibreEx->WWN) / sizeof (FibreEx->WWN[0]); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", FibreEx->WWN[Index]);
+ }
+ UefiDevicePathLibCatPrint (Str, L",0x");
+ for (Index = 0; Index < sizeof (FibreEx->Lun) / sizeof (FibreEx->Lun[0]); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", FibreEx->Lun[Index]);
+ }
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts a Sas Ex device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextSasEx (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ SASEX_DEVICE_PATH *SasEx;
+ UINTN Index;
+
+ SasEx = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"SasEx(0x");
+
+ for (Index = 0; Index < sizeof (SasEx->SasAddress) / sizeof (SasEx->SasAddress[0]); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", SasEx->SasAddress[Index]);
+ }
+ UefiDevicePathLibCatPrint (Str, L",0x");
+ for (Index = 0; Index < sizeof (SasEx->Lun) / sizeof (SasEx->Lun[0]); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", SasEx->Lun[Index]);
+ }
+ UefiDevicePathLibCatPrint (Str, L",0x%x,", SasEx->RelativeTargetPort);
+
+ if (((SasEx->DeviceTopology & 0x0f) == 0) && ((SasEx->DeviceTopology & BIT7) == 0)) {
+ UefiDevicePathLibCatPrint (Str, L"NoTopology,0,0,0");
+ } else if (((SasEx->DeviceTopology & 0x0f) <= 2) && ((SasEx->DeviceTopology & BIT7) == 0)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"%s,%s,%s,",
+ ((SasEx->DeviceTopology & BIT4) != 0) ? L"SATA" : L"SAS",
+ ((SasEx->DeviceTopology & BIT5) != 0) ? L"External" : L"Internal",
+ ((SasEx->DeviceTopology & BIT6) != 0) ? L"Expanded" : L"Direct"
+ );
+ if ((SasEx->DeviceTopology & 0x0f) == 1) {
+ UefiDevicePathLibCatPrint (Str, L"0");
+ } else {
+ //
+ // Value 0x0 thru 0xFF -> Drive 1 thru Drive 256
+ //
+ UefiDevicePathLibCatPrint (Str, L"0x%x", ((SasEx->DeviceTopology >> 8) & 0xff) + 1);
+ }
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"0x%x,0,0,0", SasEx->DeviceTopology);
+ }
+
+ UefiDevicePathLibCatPrint (Str, L")");
+ return ;
+
+}
+
+/**
+ Converts a NVM Express Namespace device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextNVMe (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ NVME_NAMESPACE_DEVICE_PATH *Nvme;
+ UINT8 *Uuid;
+
+ Nvme = DevPath;
+ Uuid = (UINT8 *) &Nvme->NamespaceUuid;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"NVMe(0x%x,%02x-%02x-%02x-%02x-%02x-%02x-%02x-%02x)",
+ Nvme->NamespaceId,
+ Uuid[7], Uuid[6], Uuid[5], Uuid[4],
+ Uuid[3], Uuid[2], Uuid[1], Uuid[0]
+ );
+}
+
+/**
+ Converts a UFS device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUfs (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ UFS_DEVICE_PATH *Ufs;
+
+ Ufs = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"UFS(0x%x,0x%x)", Ufs->Pun, Ufs->Lun);
+}
+
+/**
+ Converts a SD (Secure Digital) device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextSd (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ SD_DEVICE_PATH *Sd;
+
+ Sd = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"SD(0x%x)",
+ Sd->SlotNumber
+ );
+}
+
+/**
+ Converts a EMMC (Embedded MMC) device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextEmmc (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ EMMC_DEVICE_PATH *Emmc;
+
+ Emmc = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"eMMC(0x%x)",
+ Emmc->SlotNumber
+ );
+}
+
+/**
+ Converts a 1394 device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToText1394 (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ F1394_DEVICE_PATH *F1394DevPath;
+
+ F1394DevPath = DevPath;
+ //
+ // Guid has format of IEEE-EUI64
+ //
+ UefiDevicePathLibCatPrint (Str, L"I1394(%016lx)", F1394DevPath->Guid);
+}
+
+/**
+ Converts a USB device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUsb (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ USB_DEVICE_PATH *Usb;
+
+ Usb = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"USB(0x%x,0x%x)", Usb->ParentPortNumber, Usb->InterfaceNumber);
+}
+
+/**
+ Converts a USB WWID device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUsbWWID (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ USB_WWID_DEVICE_PATH *UsbWWId;
+ CHAR16 *SerialNumberStr;
+ CHAR16 *NewStr;
+ UINT16 Length;
+
+ UsbWWId = DevPath;
+
+ SerialNumberStr = (CHAR16 *) ((UINT8 *) UsbWWId + sizeof (USB_WWID_DEVICE_PATH));
+ Length = (UINT16) ((DevicePathNodeLength ((EFI_DEVICE_PATH_PROTOCOL *) UsbWWId) - sizeof (USB_WWID_DEVICE_PATH)) / sizeof (CHAR16));
+ if (Length >= 1 && SerialNumberStr [Length - 1] != 0) {
+ //
+ // In case no NULL terminator in SerialNumber, create a new one with NULL terminator
+ //
+ NewStr = AllocateCopyPool ((Length + 1) * sizeof (CHAR16), SerialNumberStr);
+ ASSERT (NewStr != NULL);
+ NewStr [Length] = 0;
+ SerialNumberStr = NewStr;
+ }
+
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"UsbWwid(0x%x,0x%x,0x%x,\"%s\")",
+ UsbWWId->VendorId,
+ UsbWWId->ProductId,
+ UsbWWId->InterfaceNumber,
+ SerialNumberStr
+ );
+}
+
+/**
+ Converts a Logic Unit device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextLogicalUnit (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ DEVICE_LOGICAL_UNIT_DEVICE_PATH *LogicalUnit;
+
+ LogicalUnit = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Unit(0x%x)", LogicalUnit->Lun);
+}
+
+/**
+ Converts a USB class device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUsbClass (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ USB_CLASS_DEVICE_PATH *UsbClass;
+ BOOLEAN IsKnownSubClass;
+
+
+ UsbClass = DevPath;
+
+ IsKnownSubClass = TRUE;
+ switch (UsbClass->DeviceClass) {
+ case USB_CLASS_AUDIO:
+ UefiDevicePathLibCatPrint (Str, L"UsbAudio");
+ break;
+
+ case USB_CLASS_CDCCONTROL:
+ UefiDevicePathLibCatPrint (Str, L"UsbCDCControl");
+ break;
+
+ case USB_CLASS_HID:
+ UefiDevicePathLibCatPrint (Str, L"UsbHID");
+ break;
+
+ case USB_CLASS_IMAGE:
+ UefiDevicePathLibCatPrint (Str, L"UsbImage");
+ break;
+
+ case USB_CLASS_PRINTER:
+ UefiDevicePathLibCatPrint (Str, L"UsbPrinter");
+ break;
+
+ case USB_CLASS_MASS_STORAGE:
+ UefiDevicePathLibCatPrint (Str, L"UsbMassStorage");
+ break;
+
+ case USB_CLASS_HUB:
+ UefiDevicePathLibCatPrint (Str, L"UsbHub");
+ break;
+
+ case USB_CLASS_CDCDATA:
+ UefiDevicePathLibCatPrint (Str, L"UsbCDCData");
+ break;
+
+ case USB_CLASS_SMART_CARD:
+ UefiDevicePathLibCatPrint (Str, L"UsbSmartCard");
+ break;
+
+ case USB_CLASS_VIDEO:
+ UefiDevicePathLibCatPrint (Str, L"UsbVideo");
+ break;
+
+ case USB_CLASS_DIAGNOSTIC:
+ UefiDevicePathLibCatPrint (Str, L"UsbDiagnostic");
+ break;
+
+ case USB_CLASS_WIRELESS:
+ UefiDevicePathLibCatPrint (Str, L"UsbWireless");
+ break;
+
+ default:
+ IsKnownSubClass = FALSE;
+ break;
+ }
+
+ if (IsKnownSubClass) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"(0x%x,0x%x,0x%x,0x%x)",
+ UsbClass->VendorId,
+ UsbClass->ProductId,
+ UsbClass->DeviceSubClass,
+ UsbClass->DeviceProtocol
+ );
+ return;
+ }
+
+ if (UsbClass->DeviceClass == USB_CLASS_RESERVE) {
+ if (UsbClass->DeviceSubClass == USB_SUBCLASS_FW_UPDATE) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"UsbDeviceFirmwareUpdate(0x%x,0x%x,0x%x)",
+ UsbClass->VendorId,
+ UsbClass->ProductId,
+ UsbClass->DeviceProtocol
+ );
+ return;
+ } else if (UsbClass->DeviceSubClass == USB_SUBCLASS_IRDA_BRIDGE) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"UsbIrdaBridge(0x%x,0x%x,0x%x)",
+ UsbClass->VendorId,
+ UsbClass->ProductId,
+ UsbClass->DeviceProtocol
+ );
+ return;
+ } else if (UsbClass->DeviceSubClass == USB_SUBCLASS_TEST) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"UsbTestAndMeasurement(0x%x,0x%x,0x%x)",
+ UsbClass->VendorId,
+ UsbClass->ProductId,
+ UsbClass->DeviceProtocol
+ );
+ return;
+ }
+ }
+
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"UsbClass(0x%x,0x%x,0x%x,0x%x,0x%x)",
+ UsbClass->VendorId,
+ UsbClass->ProductId,
+ UsbClass->DeviceClass,
+ UsbClass->DeviceSubClass,
+ UsbClass->DeviceProtocol
+ );
+}
+
+/**
+ Converts a SATA device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextSata (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ SATA_DEVICE_PATH *Sata;
+
+ Sata = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Sata(0x%x,0x%x,0x%x)",
+ Sata->HBAPortNumber,
+ Sata->PortMultiplierPortNumber,
+ Sata->Lun
+ );
+}
+
+/**
+ Converts a I20 device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextI2O (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ I2O_DEVICE_PATH *I2ODevPath;
+
+ I2ODevPath = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"I2O(0x%x)", I2ODevPath->Tid);
+}
+
+/**
+ Converts a MAC address device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextMacAddr (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MAC_ADDR_DEVICE_PATH *MacDevPath;
+ UINTN HwAddressSize;
+ UINTN Index;
+
+ MacDevPath = DevPath;
+
+ HwAddressSize = sizeof (EFI_MAC_ADDRESS);
+ if (MacDevPath->IfType == 0x01 || MacDevPath->IfType == 0x00) {
+ HwAddressSize = 6;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"MAC(");
+
+ for (Index = 0; Index < HwAddressSize; Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", MacDevPath->MacAddress.Addr[Index]);
+ }
+
+ UefiDevicePathLibCatPrint (Str, L",0x%x)", MacDevPath->IfType);
+}
+
+/**
+ Converts network protocol string to its text representation.
+
+ @param Str The string representative of input device.
+ @param Protocol The network protocol ID.
+
+**/
+VOID
+CatNetworkProtocol (
+ IN OUT POOL_PRINT *Str,
+ IN UINT16 Protocol
+ )
+{
+ if (Protocol == RFC_1700_TCP_PROTOCOL) {
+ UefiDevicePathLibCatPrint (Str, L"TCP");
+ } else if (Protocol == RFC_1700_UDP_PROTOCOL) {
+ UefiDevicePathLibCatPrint (Str, L"UDP");
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"0x%x", Protocol);
+ }
+}
+
+/**
+ Converts IP v4 address to its text representation.
+
+ @param Str The string representative of input device.
+ @param Address The IP v4 address.
+**/
+VOID
+CatIPv4Address (
+ IN OUT POOL_PRINT *Str,
+ IN EFI_IPv4_ADDRESS *Address
+ )
+{
+ UefiDevicePathLibCatPrint (Str, L"%d.%d.%d.%d", Address->Addr[0], Address->Addr[1], Address->Addr[2], Address->Addr[3]);
+}
+
+/**
+ Converts IP v6 address to its text representation.
+
+ @param Str The string representative of input device.
+ @param Address The IP v6 address.
+**/
+VOID
+CatIPv6Address (
+ IN OUT POOL_PRINT *Str,
+ IN EFI_IPv6_ADDRESS *Address
+ )
+{
+ UefiDevicePathLibCatPrint (
+ Str, L"%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x",
+ Address->Addr[0], Address->Addr[1],
+ Address->Addr[2], Address->Addr[3],
+ Address->Addr[4], Address->Addr[5],
+ Address->Addr[6], Address->Addr[7],
+ Address->Addr[8], Address->Addr[9],
+ Address->Addr[10], Address->Addr[11],
+ Address->Addr[12], Address->Addr[13],
+ Address->Addr[14], Address->Addr[15]
+ );
+}
+
+/**
+ Converts a IPv4 device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextIPv4 (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ IPv4_DEVICE_PATH *IPDevPath;
+
+ IPDevPath = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"IPv4(");
+ CatIPv4Address (Str, &IPDevPath->RemoteIpAddress);
+
+ if (DisplayOnly) {
+ UefiDevicePathLibCatPrint (Str, L")");
+ return ;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L",");
+ CatNetworkProtocol (Str, IPDevPath->Protocol);
+
+ UefiDevicePathLibCatPrint (Str, L",%s,", IPDevPath->StaticIpAddress ? L"Static" : L"DHCP");
+ CatIPv4Address (Str, &IPDevPath->LocalIpAddress);
+ if (DevicePathNodeLength (IPDevPath) == sizeof (IPv4_DEVICE_PATH)) {
+ UefiDevicePathLibCatPrint (Str, L",");
+ CatIPv4Address (Str, &IPDevPath->GatewayIpAddress);
+ UefiDevicePathLibCatPrint (Str, L",");
+ CatIPv4Address (Str, &IPDevPath->SubnetMask);
+ }
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts a IPv6 device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextIPv6 (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ IPv6_DEVICE_PATH *IPDevPath;
+
+ IPDevPath = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"IPv6(");
+ CatIPv6Address (Str, &IPDevPath->RemoteIpAddress);
+ if (DisplayOnly) {
+ UefiDevicePathLibCatPrint (Str, L")");
+ return ;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L",");
+ CatNetworkProtocol (Str, IPDevPath->Protocol);
+
+ switch (IPDevPath->IpAddressOrigin) {
+ case 0:
+ UefiDevicePathLibCatPrint (Str, L",Static,");
+ break;
+ case 1:
+ UefiDevicePathLibCatPrint (Str, L",StatelessAutoConfigure,");
+ break;
+ default:
+ UefiDevicePathLibCatPrint (Str, L",StatefulAutoConfigure,");
+ break;
+ }
+
+ CatIPv6Address (Str, &IPDevPath->LocalIpAddress);
+
+ if (DevicePathNodeLength (IPDevPath) == sizeof (IPv6_DEVICE_PATH)) {
+ UefiDevicePathLibCatPrint (Str, L",0x%x,", IPDevPath->PrefixLength);
+ CatIPv6Address (Str, &IPDevPath->GatewayIpAddress);
+ }
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts an Infini Band device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextInfiniBand (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ INFINIBAND_DEVICE_PATH *InfiniBand;
+
+ InfiniBand = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Infiniband(0x%x,%g,0x%lx,0x%lx,0x%lx)",
+ InfiniBand->ResourceFlags,
+ InfiniBand->PortGid,
+ InfiniBand->ServiceId,
+ InfiniBand->TargetPortId,
+ InfiniBand->DeviceId
+ );
+}
+
+/**
+ Converts a UART device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUart (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ UART_DEVICE_PATH *Uart;
+ CHAR8 Parity;
+
+ Uart = DevPath;
+ switch (Uart->Parity) {
+ case 0:
+ Parity = 'D';
+ break;
+
+ case 1:
+ Parity = 'N';
+ break;
+
+ case 2:
+ Parity = 'E';
+ break;
+
+ case 3:
+ Parity = 'O';
+ break;
+
+ case 4:
+ Parity = 'M';
+ break;
+
+ case 5:
+ Parity = 'S';
+ break;
+
+ default:
+ Parity = 'x';
+ break;
+ }
+
+ if (Uart->BaudRate == 0) {
+ UefiDevicePathLibCatPrint (Str, L"Uart(DEFAULT,");
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"Uart(%ld,", Uart->BaudRate);
+ }
+
+ if (Uart->DataBits == 0) {
+ UefiDevicePathLibCatPrint (Str, L"DEFAULT,");
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"%d,", Uart->DataBits);
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"%c,", Parity);
+
+ switch (Uart->StopBits) {
+ case 0:
+ UefiDevicePathLibCatPrint (Str, L"D)");
+ break;
+
+ case 1:
+ UefiDevicePathLibCatPrint (Str, L"1)");
+ break;
+
+ case 2:
+ UefiDevicePathLibCatPrint (Str, L"1.5)");
+ break;
+
+ case 3:
+ UefiDevicePathLibCatPrint (Str, L"2)");
+ break;
+
+ default:
+ UefiDevicePathLibCatPrint (Str, L"x)");
+ break;
+ }
+}
+
+/**
+ Converts an iSCSI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextiSCSI (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ ISCSI_DEVICE_PATH_WITH_NAME *ISCSIDevPath;
+ UINT16 Options;
+ UINTN Index;
+
+ ISCSIDevPath = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"iSCSI(%a,0x%x,0x",
+ ISCSIDevPath->TargetName,
+ ISCSIDevPath->TargetPortalGroupTag
+ );
+ for (Index = 0; Index < sizeof (ISCSIDevPath->Lun) / sizeof (UINT8); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", ((UINT8 *)&ISCSIDevPath->Lun)[Index]);
+ }
+ Options = ISCSIDevPath->LoginOption;
+ UefiDevicePathLibCatPrint (Str, L",%s,", (((Options >> 1) & 0x0001) != 0) ? L"CRC32C" : L"None");
+ UefiDevicePathLibCatPrint (Str, L"%s,", (((Options >> 3) & 0x0001) != 0) ? L"CRC32C" : L"None");
+ if (((Options >> 11) & 0x0001) != 0) {
+ UefiDevicePathLibCatPrint (Str, L"%s,", L"None");
+ } else if (((Options >> 12) & 0x0001) != 0) {
+ UefiDevicePathLibCatPrint (Str, L"%s,", L"CHAP_UNI");
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"%s,", L"CHAP_BI");
+
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"%s)", (ISCSIDevPath->NetworkProtocol == 0) ? L"TCP" : L"reserved");
+}
+
+/**
+ Converts a VLAN device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextVlan (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ VLAN_DEVICE_PATH *Vlan;
+
+ Vlan = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Vlan(%d)", Vlan->VlanId);
+}
+
+/**
+ Converts a Bluetooth device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextBluetooth (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ BLUETOOTH_DEVICE_PATH *Bluetooth;
+
+ Bluetooth = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Bluetooth(%02x%02x%02x%02x%02x%02x)",
+ Bluetooth->BD_ADDR.Address[0],
+ Bluetooth->BD_ADDR.Address[1],
+ Bluetooth->BD_ADDR.Address[2],
+ Bluetooth->BD_ADDR.Address[3],
+ Bluetooth->BD_ADDR.Address[4],
+ Bluetooth->BD_ADDR.Address[5]
+ );
+}
+
+/**
+ Converts a Wi-Fi device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextWiFi (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ WIFI_DEVICE_PATH *WiFi;
+ UINT8 SSId[33];
+
+ WiFi = DevPath;
+
+ SSId[32] = '\0';
+ CopyMem (SSId, WiFi->SSId, 32);
+
+ UefiDevicePathLibCatPrint (Str, L"Wi-Fi(%a)", SSId);
+}
+
+/**
+ Converts a Bluetooth device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextBluetoothLE (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ BLUETOOTH_LE_DEVICE_PATH *BluetoothLE;
+
+ BluetoothLE = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"BluetoothLE(%02x%02x%02x%02x%02x%02x,0x%02x)",
+ BluetoothLE->Address.Address[0],
+ BluetoothLE->Address.Address[1],
+ BluetoothLE->Address.Address[2],
+ BluetoothLE->Address.Address[3],
+ BluetoothLE->Address.Address[4],
+ BluetoothLE->Address.Address[5],
+ BluetoothLE->Address.Type
+ );
+}
+
+/**
+ Converts a DNS device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextDns (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ DNS_DEVICE_PATH *DnsDevPath;
+ UINT32 DnsServerIpCount;
+ UINT32 DnsServerIpIndex;
+
+ DnsDevPath = DevPath;
+ DnsServerIpCount = (UINT32) (DevicePathNodeLength(DnsDevPath) - sizeof (EFI_DEVICE_PATH_PROTOCOL) - sizeof (DnsDevPath->IsIPv6)) / sizeof (EFI_IP_ADDRESS);
+
+ UefiDevicePathLibCatPrint (Str, L"Dns(");
+
+ for (DnsServerIpIndex = 0; DnsServerIpIndex < DnsServerIpCount; DnsServerIpIndex++) {
+ if (DnsDevPath->IsIPv6 == 0x00) {
+ CatIPv4Address (Str, &(DnsDevPath->DnsServerIp[DnsServerIpIndex].v4));
+ } else {
+ CatIPv6Address (Str, &(DnsDevPath->DnsServerIp[DnsServerIpIndex].v6));
+ }
+
+ if (DnsServerIpIndex < DnsServerIpCount - 1) {
+ UefiDevicePathLibCatPrint (Str, L",");
+ }
+ }
+
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+/**
+ Converts a URI device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextUri (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ URI_DEVICE_PATH *Uri;
+ UINTN UriLength;
+ CHAR8 *UriStr;
+
+ //
+ // Uri in the device path may not be null terminated.
+ //
+ Uri = DevPath;
+ UriLength = DevicePathNodeLength (Uri) - sizeof (URI_DEVICE_PATH);
+ UriStr = AllocatePool (UriLength + 1);
+ ASSERT (UriStr != NULL);
+
+ CopyMem (UriStr, Uri->Uri, UriLength);
+ UriStr[UriLength] = '\0';
+ UefiDevicePathLibCatPrint (Str, L"Uri(%a)", UriStr);
+ FreePool (UriStr);
+}
+
+/**
+ Converts a Hard drive device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextHardDrive (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ HARDDRIVE_DEVICE_PATH *Hd;
+
+ Hd = DevPath;
+ switch (Hd->SignatureType) {
+ case SIGNATURE_TYPE_MBR:
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"HD(%d,%s,0x%08x,",
+ Hd->PartitionNumber,
+ L"MBR",
+ *((UINT32 *) (&(Hd->Signature[0])))
+ );
+ break;
+
+ case SIGNATURE_TYPE_GUID:
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"HD(%d,%s,%g,",
+ Hd->PartitionNumber,
+ L"GPT",
+ (EFI_GUID *) &(Hd->Signature[0])
+ );
+ break;
+
+ default:
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"HD(%d,%d,0,",
+ Hd->PartitionNumber,
+ Hd->SignatureType
+ );
+ break;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"0x%lx,0x%lx)", Hd->PartitionStart, Hd->PartitionSize);
+}
+
+/**
+ Converts a CDROM device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextCDROM (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ CDROM_DEVICE_PATH *Cd;
+
+ Cd = DevPath;
+ if (DisplayOnly) {
+ UefiDevicePathLibCatPrint (Str, L"CDROM(0x%x)", Cd->BootEntry);
+ return ;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L"CDROM(0x%x,0x%lx,0x%lx)", Cd->BootEntry, Cd->PartitionStart, Cd->PartitionSize);
+}
+
+/**
+ Converts a File device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextFilePath (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ FILEPATH_DEVICE_PATH *Fp;
+
+ Fp = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"%s", Fp->PathName);
+}
+
+/**
+ Converts a Media protocol device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextMediaProtocol (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEDIA_PROTOCOL_DEVICE_PATH *MediaProt;
+
+ MediaProt = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Media(%g)", &MediaProt->Protocol);
+}
+
+/**
+ Converts a Firmware Volume device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextFv (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEDIA_FW_VOL_DEVICE_PATH *Fv;
+
+ Fv = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"Fv(%g)", &Fv->FvName);
+}
+
+/**
+ Converts a Firmware Volume File device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextFvFile (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvFile;
+
+ FvFile = DevPath;
+ UefiDevicePathLibCatPrint (Str, L"FvFile(%g)", &FvFile->FvFileName);
+}
+
+/**
+ Converts a Relative Offset device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathRelativeOffsetRange (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH *Offset;
+
+ Offset = DevPath;
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"Offset(0x%lx,0x%lx)",
+ Offset->StartingOffset,
+ Offset->EndingOffset
+ );
+}
+
+/**
+ Converts a Ram Disk device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextRamDisk (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ MEDIA_RAM_DISK_DEVICE_PATH *RamDisk;
+
+ RamDisk = DevPath;
+
+ if (CompareGuid (&RamDisk->TypeGuid, &gEfiVirtualDiskGuid)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"VirtualDisk(0x%lx,0x%lx,%d)",
+ LShiftU64 ((UINT64)RamDisk->StartingAddr[1], 32) | RamDisk->StartingAddr[0],
+ LShiftU64 ((UINT64)RamDisk->EndingAddr[1], 32) | RamDisk->EndingAddr[0],
+ RamDisk->Instance
+ );
+ } else if (CompareGuid (&RamDisk->TypeGuid, &gEfiVirtualCdGuid)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"VirtualCD(0x%lx,0x%lx,%d)",
+ LShiftU64 ((UINT64)RamDisk->StartingAddr[1], 32) | RamDisk->StartingAddr[0],
+ LShiftU64 ((UINT64)RamDisk->EndingAddr[1], 32) | RamDisk->EndingAddr[0],
+ RamDisk->Instance
+ );
+ } else if (CompareGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualDiskGuid)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"PersistentVirtualDisk(0x%lx,0x%lx,%d)",
+ LShiftU64 ((UINT64)RamDisk->StartingAddr[1], 32) | RamDisk->StartingAddr[0],
+ LShiftU64 ((UINT64)RamDisk->EndingAddr[1], 32) | RamDisk->EndingAddr[0],
+ RamDisk->Instance
+ );
+ } else if (CompareGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualCdGuid)) {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"PersistentVirtualCD(0x%lx,0x%lx,%d)",
+ LShiftU64 ((UINT64)RamDisk->StartingAddr[1], 32) | RamDisk->StartingAddr[0],
+ LShiftU64 ((UINT64)RamDisk->EndingAddr[1], 32) | RamDisk->EndingAddr[0],
+ RamDisk->Instance
+ );
+ } else {
+ UefiDevicePathLibCatPrint (
+ Str,
+ L"RamDisk(0x%lx,0x%lx,%d,%g)",
+ LShiftU64 ((UINT64)RamDisk->StartingAddr[1], 32) | RamDisk->StartingAddr[0],
+ LShiftU64 ((UINT64)RamDisk->EndingAddr[1], 32) | RamDisk->EndingAddr[0],
+ RamDisk->Instance,
+ &RamDisk->TypeGuid
+ );
+ }
+}
+
+/**
+ Converts a BIOS Boot Specification device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextBBS (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ BBS_BBS_DEVICE_PATH *Bbs;
+ CHAR16 *Type;
+
+ Bbs = DevPath;
+ switch (Bbs->DeviceType) {
+ case BBS_TYPE_FLOPPY:
+ Type = L"Floppy";
+ break;
+
+ case BBS_TYPE_HARDDRIVE:
+ Type = L"HD";
+ break;
+
+ case BBS_TYPE_CDROM:
+ Type = L"CDROM";
+ break;
+
+ case BBS_TYPE_PCMCIA:
+ Type = L"PCMCIA";
+ break;
+
+ case BBS_TYPE_USB:
+ Type = L"USB";
+ break;
+
+ case BBS_TYPE_EMBEDDED_NETWORK:
+ Type = L"Network";
+ break;
+
+ default:
+ Type = NULL;
+ break;
+ }
+
+ if (Type != NULL) {
+ UefiDevicePathLibCatPrint (Str, L"BBS(%s,%a", Type, Bbs->String);
+ } else {
+ UefiDevicePathLibCatPrint (Str, L"BBS(0x%x,%a", Bbs->DeviceType, Bbs->String);
+ }
+
+ if (DisplayOnly) {
+ UefiDevicePathLibCatPrint (Str, L")");
+ return ;
+ }
+
+ UefiDevicePathLibCatPrint (Str, L",0x%x)", Bbs->StatusFlag);
+}
+
+/**
+ Converts an End-of-Device-Path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextEndInstance (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ UefiDevicePathLibCatPrint (Str, L",");
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED const DEVICE_PATH_TO_TEXT_GENERIC_TABLE mUefiDevicePathLibToTextTableGeneric[] = {
+ {HARDWARE_DEVICE_PATH, L"HardwarePath" },
+ {ACPI_DEVICE_PATH, L"AcpiPath" },
+ {MESSAGING_DEVICE_PATH, L"Msg" },
+ {MEDIA_DEVICE_PATH, L"MediaPath" },
+ {BBS_DEVICE_PATH, L"BbsPath" },
+ {0, NULL}
+};
+
+/**
+ Converts an unknown device path structure to its string representative.
+
+ @param Str The string representative of input device.
+ @param DevPath The input device path structure.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+**/
+VOID
+DevPathToTextNodeGeneric (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevPath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *Node;
+ UINTN Index;
+
+ Node = DevPath;
+
+ for (Index = 0; mUefiDevicePathLibToTextTableGeneric[Index].Text != NULL; Index++) {
+ if (DevicePathType (Node) == mUefiDevicePathLibToTextTableGeneric[Index].Type) {
+ break;
+ }
+ }
+
+ if (mUefiDevicePathLibToTextTableGeneric[Index].Text == NULL) {
+ //
+ // It's a node whose type cannot be recognized
+ //
+ UefiDevicePathLibCatPrint (Str, L"Path(%d,%d", DevicePathType (Node), DevicePathSubType (Node));
+ } else {
+ //
+ // It's a node whose type can be recognized
+ //
+ UefiDevicePathLibCatPrint (Str, L"%s(%d", mUefiDevicePathLibToTextTableGeneric[Index].Text, DevicePathSubType (Node));
+ }
+
+ Index = sizeof (EFI_DEVICE_PATH_PROTOCOL);
+ if (Index < DevicePathNodeLength (Node)) {
+ UefiDevicePathLibCatPrint (Str, L",");
+ for (; Index < DevicePathNodeLength (Node); Index++) {
+ UefiDevicePathLibCatPrint (Str, L"%02x", ((UINT8 *) Node)[Index]);
+ }
+ }
+
+ UefiDevicePathLibCatPrint (Str, L")");
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED const DEVICE_PATH_TO_TEXT_TABLE mUefiDevicePathLibToTextTable[] = {
+ {HARDWARE_DEVICE_PATH, HW_PCI_DP, DevPathToTextPci },
+ {HARDWARE_DEVICE_PATH, HW_PCCARD_DP, DevPathToTextPccard },
+ {HARDWARE_DEVICE_PATH, HW_MEMMAP_DP, DevPathToTextMemMap },
+ {HARDWARE_DEVICE_PATH, HW_VENDOR_DP, DevPathToTextVendor },
+ {HARDWARE_DEVICE_PATH, HW_CONTROLLER_DP, DevPathToTextController },
+ {HARDWARE_DEVICE_PATH, HW_BMC_DP, DevPathToTextBmc },
+ {ACPI_DEVICE_PATH, ACPI_DP, DevPathToTextAcpi },
+ {ACPI_DEVICE_PATH, ACPI_EXTENDED_DP, DevPathToTextAcpiEx },
+ {ACPI_DEVICE_PATH, ACPI_ADR_DP, DevPathToTextAcpiAdr },
+ {MESSAGING_DEVICE_PATH, MSG_ATAPI_DP, DevPathToTextAtapi },
+ {MESSAGING_DEVICE_PATH, MSG_SCSI_DP, DevPathToTextScsi },
+ {MESSAGING_DEVICE_PATH, MSG_FIBRECHANNEL_DP, DevPathToTextFibre },
+ {MESSAGING_DEVICE_PATH, MSG_FIBRECHANNELEX_DP, DevPathToTextFibreEx },
+ {MESSAGING_DEVICE_PATH, MSG_SASEX_DP, DevPathToTextSasEx },
+ {MESSAGING_DEVICE_PATH, MSG_NVME_NAMESPACE_DP, DevPathToTextNVMe },
+ {MESSAGING_DEVICE_PATH, MSG_UFS_DP, DevPathToTextUfs },
+ {MESSAGING_DEVICE_PATH, MSG_SD_DP, DevPathToTextSd },
+ {MESSAGING_DEVICE_PATH, MSG_EMMC_DP, DevPathToTextEmmc },
+ {MESSAGING_DEVICE_PATH, MSG_1394_DP, DevPathToText1394 },
+ {MESSAGING_DEVICE_PATH, MSG_USB_DP, DevPathToTextUsb },
+ {MESSAGING_DEVICE_PATH, MSG_USB_WWID_DP, DevPathToTextUsbWWID },
+ {MESSAGING_DEVICE_PATH, MSG_DEVICE_LOGICAL_UNIT_DP, DevPathToTextLogicalUnit },
+ {MESSAGING_DEVICE_PATH, MSG_USB_CLASS_DP, DevPathToTextUsbClass },
+ {MESSAGING_DEVICE_PATH, MSG_SATA_DP, DevPathToTextSata },
+ {MESSAGING_DEVICE_PATH, MSG_I2O_DP, DevPathToTextI2O },
+ {MESSAGING_DEVICE_PATH, MSG_MAC_ADDR_DP, DevPathToTextMacAddr },
+ {MESSAGING_DEVICE_PATH, MSG_IPv4_DP, DevPathToTextIPv4 },
+ {MESSAGING_DEVICE_PATH, MSG_IPv6_DP, DevPathToTextIPv6 },
+ {MESSAGING_DEVICE_PATH, MSG_INFINIBAND_DP, DevPathToTextInfiniBand },
+ {MESSAGING_DEVICE_PATH, MSG_UART_DP, DevPathToTextUart },
+ {MESSAGING_DEVICE_PATH, MSG_VENDOR_DP, DevPathToTextVendor },
+ {MESSAGING_DEVICE_PATH, MSG_ISCSI_DP, DevPathToTextiSCSI },
+ {MESSAGING_DEVICE_PATH, MSG_VLAN_DP, DevPathToTextVlan },
+ {MESSAGING_DEVICE_PATH, MSG_DNS_DP, DevPathToTextDns },
+ {MESSAGING_DEVICE_PATH, MSG_URI_DP, DevPathToTextUri },
+ {MESSAGING_DEVICE_PATH, MSG_BLUETOOTH_DP, DevPathToTextBluetooth },
+ {MESSAGING_DEVICE_PATH, MSG_WIFI_DP, DevPathToTextWiFi },
+ {MESSAGING_DEVICE_PATH, MSG_BLUETOOTH_LE_DP, DevPathToTextBluetoothLE },
+ {MEDIA_DEVICE_PATH, MEDIA_HARDDRIVE_DP, DevPathToTextHardDrive },
+ {MEDIA_DEVICE_PATH, MEDIA_CDROM_DP, DevPathToTextCDROM },
+ {MEDIA_DEVICE_PATH, MEDIA_VENDOR_DP, DevPathToTextVendor },
+ {MEDIA_DEVICE_PATH, MEDIA_PROTOCOL_DP, DevPathToTextMediaProtocol },
+ {MEDIA_DEVICE_PATH, MEDIA_FILEPATH_DP, DevPathToTextFilePath },
+ {MEDIA_DEVICE_PATH, MEDIA_PIWG_FW_VOL_DP, DevPathToTextFv },
+ {MEDIA_DEVICE_PATH, MEDIA_PIWG_FW_FILE_DP, DevPathToTextFvFile },
+ {MEDIA_DEVICE_PATH, MEDIA_RELATIVE_OFFSET_RANGE_DP, DevPathRelativeOffsetRange },
+ {MEDIA_DEVICE_PATH, MEDIA_RAM_DISK_DP, DevPathToTextRamDisk },
+ {BBS_DEVICE_PATH, BBS_BBS_DP, DevPathToTextBBS },
+ {END_DEVICE_PATH_TYPE, END_INSTANCE_DEVICE_PATH_SUBTYPE, DevPathToTextEndInstance },
+ {0, 0, NULL}
+};
+
+/**
+ Converts a device node to its string representation.
+
+ @param DeviceNode A Pointer to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device node or NULL if DeviceNode
+ is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+UefiDevicePathLibConvertDeviceNodeToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ POOL_PRINT Str;
+ UINTN Index;
+ DEVICE_PATH_TO_TEXT ToText;
+
+ if (DeviceNode == NULL) {
+ return NULL;
+ }
+
+ ZeroMem (&Str, sizeof (Str));
+
+ //
+ // Process the device path node
+ // If not found, use a generic function
+ //
+ ToText = DevPathToTextNodeGeneric;
+ for (Index = 0; mUefiDevicePathLibToTextTable[Index].Function != NULL; Index++) {
+ if (DevicePathType (DeviceNode) == mUefiDevicePathLibToTextTable[Index].Type &&
+ DevicePathSubType (DeviceNode) == mUefiDevicePathLibToTextTable[Index].SubType
+ ) {
+ ToText = mUefiDevicePathLibToTextTable[Index].Function;
+ break;
+ }
+ }
+
+ //
+ // Print this node
+ //
+ ToText (&Str, (VOID *) DeviceNode, DisplayOnly, AllowShortcuts);
+
+ ASSERT (Str.Str != NULL);
+ return Str.Str;
+}
+
+/**
+ Converts a device path to its text representation.
+
+ @param DevicePath A Pointer to the device to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device path or
+ NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+UefiDevicePathLibConvertDevicePathToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ POOL_PRINT Str;
+ EFI_DEVICE_PATH_PROTOCOL *Node;
+ EFI_DEVICE_PATH_PROTOCOL *AlignedNode;
+ UINTN Index;
+ DEVICE_PATH_TO_TEXT ToText;
+
+ if (DevicePath == NULL) {
+ return NULL;
+ }
+
+ ZeroMem (&Str, sizeof (Str));
+
+ //
+ // Process each device path node
+ //
+ Node = (EFI_DEVICE_PATH_PROTOCOL *) DevicePath;
+ while (!IsDevicePathEnd (Node)) {
+ //
+ // Find the handler to dump this device path node
+ // If not found, use a generic function
+ //
+ ToText = DevPathToTextNodeGeneric;
+ for (Index = 0; mUefiDevicePathLibToTextTable[Index].Function != NULL; Index += 1) {
+
+ if (DevicePathType (Node) == mUefiDevicePathLibToTextTable[Index].Type &&
+ DevicePathSubType (Node) == mUefiDevicePathLibToTextTable[Index].SubType
+ ) {
+ ToText = mUefiDevicePathLibToTextTable[Index].Function;
+ break;
+ }
+ }
+ //
+ // Put a path separator in if needed
+ //
+ if ((Str.Count != 0) && (ToText != DevPathToTextEndInstance)) {
+ if (Str.Str[Str.Count] != L',') {
+ UefiDevicePathLibCatPrint (&Str, L"/");
+ }
+ }
+
+ AlignedNode = AllocateCopyPool (DevicePathNodeLength (Node), Node);
+ //
+ // Print this node of the device path
+ //
+ ToText (&Str, AlignedNode, DisplayOnly, AllowShortcuts);
+ FreePool (AlignedNode);
+
+ //
+ // Next device path node
+ //
+ Node = NextDevicePathNode (Node);
+ }
+
+ if (Str.Str == NULL) {
+ return AllocateZeroPool (sizeof (CHAR16));
+ } else {
+ return Str.Str;
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilities.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilities.c
new file mode 100644
index 0000000..3295654
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilities.c
@@ -0,0 +1,865 @@
+/** @file
+ Device Path services. The thing to remember is device paths are built out of
+ nodes. The device path is terminated by an end node that is length
+ sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
+ all over this file.
+
+ The only place where multi-instance device paths are supported is in
+ environment varibles. Multi-instance device paths should never be placed
+ on a Handle.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiDevicePathLib.h"
+#include "Efi_Defs.h"
+
+//
+// Template for an end-of-device path node.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED CONST EFI_DEVICE_PATH_PROTOCOL mUefiDevicePathLibEndDevicePath = {
+ END_DEVICE_PATH_TYPE,
+ END_ENTIRE_DEVICE_PATH_SUBTYPE,
+ {
+ END_DEVICE_PATH_LENGTH,
+ 0
+ }
+};
+
+/**
+ Determine whether a given device path is valid.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param MaxSize The maximum size of the device path data structure.
+
+ @retval TRUE DevicePath is valid.
+ @retval FALSE DevicePath is NULL.
+ @retval FALSE Maxsize is less than sizeof(EFI_DEVICE_PATH_PROTOCOL).
+ @retval FALSE The length of any node node in the DevicePath is less
+ than sizeof (EFI_DEVICE_PATH_PROTOCOL).
+ @retval FALSE If MaxSize is not zero, the size of the DevicePath
+ exceeds MaxSize.
+ @retval FALSE If PcdMaximumDevicePathNodeCount is not zero, the node
+ count of the DevicePath exceeds PcdMaximumDevicePathNodeCount.
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathValid (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN UINTN MaxSize
+ )
+{
+ UINTN Count;
+ UINTN Size;
+ UINTN NodeLength;
+
+ //
+ //Validate the input whether exists and its size big enough to touch the first node
+ //
+ if (DevicePath == NULL || (MaxSize > 0 && MaxSize < END_DEVICE_PATH_LENGTH)) {
+ return FALSE;
+ }
+
+ if (MaxSize == 0) {
+ MaxSize = MAX_UINTN;
+ }
+
+ for (Count = 0, Size = 0; !IsDevicePathEnd (DevicePath); DevicePath = NextDevicePathNode (DevicePath)) {
+ NodeLength = DevicePathNodeLength (DevicePath);
+ if (NodeLength < sizeof (EFI_DEVICE_PATH_PROTOCOL)) {
+ return FALSE;
+ }
+
+ if (NodeLength > MAX_UINTN - Size) {
+ return FALSE;
+ }
+ Size += NodeLength;
+
+ //
+ // Validate next node before touch it.
+ //
+ if (Size > MaxSize - END_DEVICE_PATH_LENGTH ) {
+ return FALSE;
+ }
+
+ if (PcdGet32 (PcdMaximumDevicePathNodeCount) > 0) {
+ Count++;
+ if (Count >= PcdGet32 (PcdMaximumDevicePathNodeCount)) {
+ return FALSE;
+ }
+ }
+
+ //
+ // FilePath must be a NULL-terminated string.
+ //
+ if (DevicePathType (DevicePath) == MEDIA_DEVICE_PATH &&
+ DevicePathSubType (DevicePath) == MEDIA_FILEPATH_DP &&
+ *(CHAR16 *)((UINT8 *)DevicePath + NodeLength - 2) != 0) {
+ return FALSE;
+ }
+ }
+
+ //
+ // Only return TRUE when the End Device Path node is valid.
+ //
+ return (BOOLEAN) (DevicePathNodeLength (DevicePath) == END_DEVICE_PATH_LENGTH);
+}
+
+
+/**
+ Returns the Type field of a device path node.
+
+ Returns the Type field of the device path node specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The Type field of the device path node specified by Node.
+
+**/
+UINT8
+EFIAPI
+DevicePathType (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return ((EFI_DEVICE_PATH_PROTOCOL *)(Node))->Type;
+}
+
+/**
+ Returns the SubType field of a device path node.
+
+ Returns the SubType field of the device path node specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The SubType field of the device path node specified by Node.
+
+**/
+UINT8
+EFIAPI
+DevicePathSubType (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return ((EFI_DEVICE_PATH_PROTOCOL *)(Node))->SubType;
+}
+
+/**
+ Returns the 16-bit Length field of a device path node.
+
+ Returns the 16-bit Length field of the device path node specified by Node.
+ Node is not required to be aligned on a 16-bit boundary, so it is recommended
+ that a function such as ReadUnaligned16() be used to extract the contents of
+ the Length field.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return The 16-bit Length field of the device path node specified by Node.
+
+**/
+UINTN
+EFIAPI
+DevicePathNodeLength (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return ReadUnaligned16 ((UINT16 *)&((EFI_DEVICE_PATH_PROTOCOL *)(Node))->Length[0]);
+}
+
+/**
+ Returns a pointer to the next node in a device path.
+
+ Returns a pointer to the device path node that follows the device path node
+ specified by Node.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @return a pointer to the device path node that follows the device path node
+ specified by Node.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+NextDevicePathNode (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return (EFI_DEVICE_PATH_PROTOCOL *)((UINT8 *)(Node) + DevicePathNodeLength(Node));
+}
+
+/**
+ Determines if a device path node is an end node of a device path.
+ This includes nodes that are the end of a device path instance and nodes that
+ are the end of an entire device path.
+
+ Determines if the device path node specified by Node is an end node of a device path.
+ This includes nodes that are the end of a device path instance and nodes that are the
+ end of an entire device path. If Node represents an end node of a device path,
+ then TRUE is returned. Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is an end node of a
+ device path.
+ @retval FALSE The device path node specified by Node is not an end node of
+ a device path.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEndType (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return (BOOLEAN) (DevicePathType (Node) == END_DEVICE_PATH_TYPE);
+}
+
+/**
+ Determines if a device path node is an end node of an entire device path.
+
+ Determines if a device path node specified by Node is an end node of an entire
+ device path. If Node represents the end of an entire device path, then TRUE is
+ returned. Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is the end of an entire
+ device path.
+ @retval FALSE The device path node specified by Node is not the end of an
+ entire device path.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEnd (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return (BOOLEAN) (IsDevicePathEndType (Node) && DevicePathSubType(Node) == END_ENTIRE_DEVICE_PATH_SUBTYPE);
+}
+
+/**
+ Determines if a device path node is an end node of a device path instance.
+
+ Determines if a device path node specified by Node is an end node of a device
+ path instance. If Node represents the end of a device path instance, then TRUE
+ is returned. Otherwise, FALSE is returned.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+ @retval TRUE The device path node specified by Node is the end of a device
+ path instance.
+ @retval FALSE The device path node specified by Node is not the end of a
+ device path instance.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathEndInstance (
+ IN CONST VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ return (BOOLEAN) (IsDevicePathEndType (Node) && DevicePathSubType(Node) == END_INSTANCE_DEVICE_PATH_SUBTYPE);
+}
+
+/**
+ Sets the length, in bytes, of a device path node.
+
+ Sets the length of the device path node specified by Node to the value specified
+ by NodeLength. NodeLength is returned. Node is not required to be aligned on
+ a 16-bit boundary, so it is recommended that a function such as WriteUnaligned16()
+ be used to set the contents of the Length field.
+
+ If Node is NULL, then ASSERT().
+ If NodeLength >= SIZE_64KB, then ASSERT().
+ If NodeLength < sizeof (EFI_DEVICE_PATH_PROTOCOL), then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+ @param Length The length, in bytes, of the device path node.
+
+ @return Length
+
+**/
+UINT16
+EFIAPI
+SetDevicePathNodeLength (
+ IN OUT VOID *Node,
+ IN UINTN Length
+ )
+{
+ ASSERT (Node != NULL);
+ ASSERT ((Length >= sizeof (EFI_DEVICE_PATH_PROTOCOL)) && (Length < SIZE_64KB));
+ return WriteUnaligned16 ((UINT16 *)&((EFI_DEVICE_PATH_PROTOCOL *)(Node))->Length[0], (UINT16)(Length));
+}
+
+/**
+ Fills in all the fields of a device path node that is the end of an entire device path.
+
+ Fills in all the fields of a device path node specified by Node so Node represents
+ the end of an entire device path. The Type field of Node is set to
+ END_DEVICE_PATH_TYPE, the SubType field of Node is set to
+ END_ENTIRE_DEVICE_PATH_SUBTYPE, and the Length field of Node is set to
+ END_DEVICE_PATH_LENGTH. Node is not required to be aligned on a 16-bit boundary,
+ so it is recommended that a function such as WriteUnaligned16() be used to set
+ the contents of the Length field.
+
+ If Node is NULL, then ASSERT().
+
+ @param Node A pointer to a device path node data structure.
+
+**/
+VOID
+EFIAPI
+SetDevicePathEndNode (
+ OUT VOID *Node
+ )
+{
+ ASSERT (Node != NULL);
+ CopyMem (Node, &mUefiDevicePathLibEndDevicePath, sizeof (mUefiDevicePathLibEndDevicePath));
+}
+
+/**
+ Returns the size of a device path in bytes.
+
+ This function returns the size, in bytes, of the device path data structure
+ specified by DevicePath including the end of device path node.
+ If DevicePath is NULL or invalid, then 0 is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval 0 If DevicePath is NULL or invalid.
+ @retval Others The size of a device path in bytes.
+
+**/
+UINTN
+EFIAPI
+UefiDevicePathLibGetDevicePathSize (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ CONST EFI_DEVICE_PATH_PROTOCOL *Start;
+
+ if (DevicePath == NULL) {
+ return 0;
+ }
+
+ if (!IsDevicePathValid (DevicePath, 0)) {
+ return 0;
+ }
+
+ //
+ // Search for the end of the device path structure
+ //
+ Start = DevicePath;
+ while (!IsDevicePathEnd (DevicePath)) {
+ DevicePath = NextDevicePathNode (DevicePath);
+ }
+
+ //
+ // Compute the size and add back in the size of the end device path structure
+ //
+ return ((UINTN) DevicePath - (UINTN) Start) + DevicePathNodeLength (DevicePath);
+}
+
+/**
+ Creates a new copy of an existing device path.
+
+ This function allocates space for a new copy of the device path specified by DevicePath.
+ If DevicePath is NULL, then NULL is returned. If the memory is successfully
+ allocated, then the contents of DevicePath are copied to the newly allocated
+ buffer, and a pointer to that buffer is returned. Otherwise, NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval NULL DevicePath is NULL or invalid.
+ @retval Others A pointer to the duplicated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibDuplicateDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ UINTN Size;
+
+ //
+ // Compute the size
+ //
+ Size = GetDevicePathSize (DevicePath);
+ if (Size == 0) {
+ return NULL;
+ }
+
+ //
+ // Allocate space for duplicate device path
+ //
+
+ return AllocateCopyPool (Size, DevicePath);
+}
+
+/**
+ Creates a new device path by appending a second device path to a first device path.
+
+ This function creates a new device path by appending a copy of SecondDevicePath
+ to a copy of FirstDevicePath in a newly allocated buffer. Only the end-of-device-path
+ device node from SecondDevicePath is retained. The newly created device path is
+ returned. If FirstDevicePath is NULL, then it is ignored, and a duplicate of
+ SecondDevicePath is returned. If SecondDevicePath is NULL, then it is ignored,
+ and a duplicate of FirstDevicePath is returned. If both FirstDevicePath and
+ SecondDevicePath are NULL, then a copy of an end-of-device-path is returned.
+
+ If there is not enough memory for the newly allocated buffer, then NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param FirstDevicePath A pointer to a device path data structure.
+ @param SecondDevicePath A pointer to a device path data structure.
+
+ @retval NULL If there is not enough memory for the newly allocated buffer.
+ @retval NULL If FirstDevicePath or SecondDevicePath is invalid.
+ @retval Others A pointer to the new device path if success.
+ Or a copy an end-of-device-path if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *FirstDevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath OPTIONAL
+ )
+{
+ UINTN Size;
+ UINTN Size1;
+ UINTN Size2;
+ EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath2;
+
+ //
+ // If there's only 1 path, just duplicate it.
+ //
+ if (FirstDevicePath == NULL) {
+ return DuplicateDevicePath ((SecondDevicePath != NULL) ? SecondDevicePath : &mUefiDevicePathLibEndDevicePath);
+ }
+
+ if (SecondDevicePath == NULL) {
+ return DuplicateDevicePath (FirstDevicePath);
+ }
+
+ if (!IsDevicePathValid (FirstDevicePath, 0) || !IsDevicePathValid (SecondDevicePath, 0)) {
+ return NULL;
+ }
+
+ //
+ // Allocate space for the combined device path. It only has one end node of
+ // length EFI_DEVICE_PATH_PROTOCOL.
+ //
+ Size1 = GetDevicePathSize (FirstDevicePath);
+ Size2 = GetDevicePathSize (SecondDevicePath);
+ Size = Size1 + Size2 - END_DEVICE_PATH_LENGTH;
+
+ NewDevicePath = AllocatePool (Size);
+
+ if (NewDevicePath != NULL) {
+ NewDevicePath = CopyMem (NewDevicePath, FirstDevicePath, Size1);
+ //
+ // Over write FirstDevicePath EndNode and do the copy
+ //
+ DevicePath2 = (EFI_DEVICE_PATH_PROTOCOL *) ((CHAR8 *) NewDevicePath +
+ (Size1 - END_DEVICE_PATH_LENGTH));
+ CopyMem (DevicePath2, SecondDevicePath, Size2);
+ }
+
+ return NewDevicePath;
+}
+
+/**
+ Creates a new path by appending the device node to the device path.
+
+ This function creates a new device path by appending a copy of the device node
+ specified by DevicePathNode to a copy of the device path specified by DevicePath
+ in an allocated buffer. The end-of-device-path device node is moved after the
+ end of the appended device node.
+ If DevicePathNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DevicePathNode, followed by an end-of-device
+ path device node is returned.
+ If both DevicePathNode and DevicePath are NULL then a copy of an end-of-device-path
+ device node is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathNode A pointer to a single device path node.
+
+ @retval NULL If there is not enough memory for the new device path.
+ @retval Others A pointer to the new device path if success.
+ A copy of DevicePathNode followed by an end-of-device-path node
+ if both FirstDevicePath and SecondDevicePath are NULL.
+ A copy of an end-of-device-path node if both FirstDevicePath
+ and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePathNode (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *TempDevicePath;
+ EFI_DEVICE_PATH_PROTOCOL *NextNode;
+ EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
+ UINTN NodeLength;
+
+ if (DevicePathNode == NULL) {
+ return DuplicateDevicePath ((DevicePath != NULL) ? DevicePath : &mUefiDevicePathLibEndDevicePath);
+ }
+ //
+ // Build a Node that has a terminator on it
+ //
+ NodeLength = DevicePathNodeLength (DevicePathNode);
+
+ TempDevicePath = AllocatePool (NodeLength + END_DEVICE_PATH_LENGTH);
+ if (TempDevicePath == NULL) {
+ return NULL;
+ }
+ TempDevicePath = CopyMem (TempDevicePath, DevicePathNode, NodeLength);
+ //
+ // Add and end device path node to convert Node to device path
+ //
+ NextNode = NextDevicePathNode (TempDevicePath);
+ SetDevicePathEndNode (NextNode);
+ //
+ // Append device paths
+ //
+ NewDevicePath = AppendDevicePath (DevicePath, TempDevicePath);
+
+ FreePool (TempDevicePath);
+
+ return NewDevicePath;
+}
+
+/**
+ Creates a new device path by appending the specified device path instance to the specified device
+ path.
+
+ This function creates a new device path by appending a copy of the device path
+ instance specified by DevicePathInstance to a copy of the device path specified
+ by DevicePath in a allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device
+ path instance and a new end-of-device-path-instance node is inserted between.
+ If DevicePath is NULL, then a copy if DevicePathInstance is returned.
+ If DevicePathInstance is NULL, then NULL is returned.
+ If DevicePath or DevicePathInstance is invalid, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathInstance A pointer to a device path instance.
+
+ @return A pointer to the new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePathInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance OPTIONAL
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
+ EFI_DEVICE_PATH_PROTOCOL *TempDevicePath;
+ UINTN SrcSize;
+ UINTN InstanceSize;
+
+ if (DevicePath == NULL) {
+ return DuplicateDevicePath (DevicePathInstance);
+ }
+
+ if (DevicePathInstance == NULL) {
+ return NULL;
+ }
+
+ if (!IsDevicePathValid (DevicePath, 0) || !IsDevicePathValid (DevicePathInstance, 0)) {
+ return NULL;
+ }
+
+ SrcSize = GetDevicePathSize (DevicePath);
+ InstanceSize = GetDevicePathSize (DevicePathInstance);
+
+ NewDevicePath = AllocatePool (SrcSize + InstanceSize);
+ if (NewDevicePath != NULL) {
+
+ TempDevicePath = CopyMem (NewDevicePath, DevicePath, SrcSize);;
+
+ while (!IsDevicePathEnd (TempDevicePath)) {
+ TempDevicePath = NextDevicePathNode (TempDevicePath);
+ }
+
+ TempDevicePath->SubType = END_INSTANCE_DEVICE_PATH_SUBTYPE;
+ TempDevicePath = NextDevicePathNode (TempDevicePath);
+ CopyMem (TempDevicePath, DevicePathInstance, InstanceSize);
+ }
+
+ return NewDevicePath;
+}
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ This function creates a copy of the current device path instance. It also updates
+ DevicePath to point to the next device path instance in the device path (or NULL
+ if no more) and updates Size to hold the size of the device path instance copy.
+ If DevicePath is NULL, then NULL is returned.
+ If DevicePath points to a invalid device path, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+ If Size is NULL, then ASSERT().
+
+ @param DevicePath On input, this holds the pointer to the current
+ device path instance. On output, this holds
+ the pointer to the next device path instance
+ or NULL if there are no more device path
+ instances in the device path pointer to a
+ device path data structure.
+ @param Size On output, this holds the size of the device
+ path instance, in bytes or zero, if DevicePath
+ is NULL.
+
+ @return A pointer to the current device path instance.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibGetNextDevicePathInstance (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
+ OUT UINTN *Size
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *DevPath;
+ EFI_DEVICE_PATH_PROTOCOL *ReturnValue;
+ UINT8 Temp;
+
+ ASSERT (Size != NULL);
+
+ if (DevicePath == NULL || *DevicePath == NULL) {
+ *Size = 0;
+ return NULL;
+ }
+
+ if (!IsDevicePathValid (*DevicePath, 0)) {
+ return NULL;
+ }
+
+ //
+ // Find the end of the device path instance
+ //
+ DevPath = *DevicePath;
+ while (!IsDevicePathEndType (DevPath)) {
+ DevPath = NextDevicePathNode (DevPath);
+ }
+
+ //
+ // Compute the size of the device path instance
+ //
+ *Size = ((UINTN) DevPath - (UINTN) (*DevicePath)) + sizeof (EFI_DEVICE_PATH_PROTOCOL);
+
+ //
+ // Make a copy and return the device path instance
+ //
+ Temp = DevPath->SubType;
+ DevPath->SubType = END_ENTIRE_DEVICE_PATH_SUBTYPE;
+ ReturnValue = DuplicateDevicePath (*DevicePath);
+ DevPath->SubType = Temp;
+
+ //
+ // If DevPath is the end of an entire device path, then another instance
+ // does not follow, so *DevicePath is set to NULL.
+ //
+ if (DevicePathSubType (DevPath) == END_ENTIRE_DEVICE_PATH_SUBTYPE) {
+ *DevicePath = NULL;
+ } else {
+ *DevicePath = NextDevicePathNode (DevPath);
+ }
+
+ return ReturnValue;
+}
+
+/**
+ Creates a device node.
+
+ This function creates a new device node in a newly allocated buffer of size
+ NodeLength and initializes the device path node header with NodeType and NodeSubType.
+ The new device path node is returned.
+ If NodeLength is smaller than a device path header, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param NodeType The device node type for the new device node.
+ @param NodeSubType The device node sub-type for the new device node.
+ @param NodeLength The length of the new device node.
+
+ @return The new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibCreateDeviceNode (
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath;
+
+ if (NodeLength < sizeof (EFI_DEVICE_PATH_PROTOCOL)) {
+ //
+ // NodeLength is less than the size of the header.
+ //
+ return NULL;
+ }
+
+ DevicePath = AllocateZeroPool (NodeLength);
+ if (DevicePath != NULL) {
+ DevicePath->Type = NodeType;
+ DevicePath->SubType = NodeSubType;
+ SetDevicePathNodeLength (DevicePath, NodeLength);
+ }
+
+ return DevicePath;
+}
+
+/**
+ Determines if a device path is single or multi-instance.
+
+ This function returns TRUE if the device path specified by DevicePath is
+ multi-instance.
+ Otherwise, FALSE is returned.
+ If DevicePath is NULL or invalid, then FALSE is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval TRUE DevicePath is multi-instance.
+ @retval FALSE DevicePath is not multi-instance, or DevicePath
+ is NULL or invalid.
+
+**/
+BOOLEAN
+EFIAPI
+UefiDevicePathLibIsDevicePathMultiInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ CONST EFI_DEVICE_PATH_PROTOCOL *Node;
+
+ if (DevicePath == NULL) {
+ return FALSE;
+ }
+
+ if (!IsDevicePathValid (DevicePath, 0)) {
+ return FALSE;
+ }
+
+ Node = DevicePath;
+ while (!IsDevicePathEnd (Node)) {
+ if (IsDevicePathEndInstance (Node)) {
+ return TRUE;
+ }
+
+ Node = NextDevicePathNode (Node);
+ }
+
+ return FALSE;
+}
+
+
+/**
+ Allocates a device path for a file and appends it to an existing device path.
+
+ If Device is a valid device handle that contains a device path protocol, then a device path for
+ the file specified by FileName is allocated and appended to the device path associated with the
+ handle Device. The allocated device path is returned. If Device is NULL or Device is a handle
+ that does not support the device path protocol, then a device path containing a single device
+ path node for the file specified by FileName is allocated and returned.
+ The memory for the new device path is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ If FileName is NULL, then ASSERT().
+ If FileName is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param Device A pointer to a device handle. This parameter
+ is optional and may be NULL.
+ @param FileName A pointer to a Null-terminated Unicode string.
+
+ @return The allocated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+FileDevicePath (
+ IN EFI_HANDLE Device, OPTIONAL
+ IN CONST CHAR16 *FileName
+ )
+{
+ UINTN Size;
+ FILEPATH_DEVICE_PATH *FilePath;
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath;
+ EFI_DEVICE_PATH_PROTOCOL *FileDevicePath;
+
+ DevicePath = NULL;
+
+ Size = StrSize (FileName);
+ FileDevicePath = AllocatePool (Size + SIZE_OF_FILEPATH_DEVICE_PATH + END_DEVICE_PATH_LENGTH);
+ if (FileDevicePath != NULL) {
+ FilePath = (FILEPATH_DEVICE_PATH *) FileDevicePath;
+ FilePath->Header.Type = MEDIA_DEVICE_PATH;
+ FilePath->Header.SubType = MEDIA_FILEPATH_DP;
+ CopyMem (&FilePath->PathName, FileName, Size);
+ SetDevicePathNodeLength (&FilePath->Header, Size + SIZE_OF_FILEPATH_DEVICE_PATH);
+ SetDevicePathEndNode (NextDevicePathNode (&FilePath->Header));
+
+ if (Device != NULL) {
+ DevicePath = DevicePathFromHandle (Device);
+ }
+
+ DevicePath = AppendDevicePath (DevicePath, FileDevicePath);
+ FreePool (FileDevicePath);
+ }
+
+ return DevicePath;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesDxeSmm.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesDxeSmm.c
new file mode 100644
index 0000000..7f3b607
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesDxeSmm.c
@@ -0,0 +1,51 @@
+/** @file
+ Device Path services. The thing to remember is device paths are built out of
+ nodes. The device path is terminated by an end node that is length
+ sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
+ all over this file.
+
+ The only place where multi-instance device paths are supported is in
+ environment varibles. Multi-instance device paths should never be placed
+ on a Handle.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ Copyright (c) Microsoft Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiDevicePathLib.h"
+
+
+/**
+ Retrieves the device path protocol from a handle.
+
+ This function returns the device path protocol from the handle specified by Handle.
+ If Handle is NULL or Handle does not contain a device path protocol, then NULL
+ is returned.
+
+ @param Handle The handle from which to retrieve the device
+ path protocol.
+
+ @return The device path protocol from the handle specified by Handle.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DevicePathFromHandle (
+ IN EFI_HANDLE Handle
+ )
+{
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath;
+ EFI_STATUS Status;
+
+ Status = gBS->HandleProtocol (
+ Handle,
+ &gEfiDevicePathProtocolGuid,
+ (VOID *) &DevicePath
+ );
+ if (EFI_ERROR (Status)) {
+ DevicePath = NULL;
+ }
+ return DevicePath;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesStandaloneMm.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesStandaloneMm.c
new file mode 100644
index 0000000..930e778
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/DevicePathUtilitiesStandaloneMm.c
@@ -0,0 +1,40 @@
+/** @file
+ Device Path services. The thing to remember is device paths are built out of
+ nodes. The device path is terminated by an end node that is length
+ sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
+ all over this file.
+
+ The only place where multi-instance device paths are supported is in
+ environment varibles. Multi-instance device paths should never be placed
+ on a Handle.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ Copyright (c) Microsoft Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiDevicePathLib.h"
+
+
+/**
+ Retrieves the device path protocol from a handle.
+
+ This function returns the device path protocol from the handle specified by Handle.
+ If Handle is NULL or Handle does not contain a device path protocol, then NULL
+ is returned.
+
+ @param Handle The handle from which to retrieve the device
+ path protocol.
+
+ @return The device path protocol from the handle specified by Handle.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DevicePathFromHandle (
+ IN EFI_HANDLE Handle
+ )
+{
+ return NULL;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.c
new file mode 100644
index 0000000..aac7686
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.c
@@ -0,0 +1,354 @@
+/** @file
+ Device Path services. The thing to remember is device paths are built out of
+ nodes. The device path is terminated by an end node that is length
+ sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
+ all over this file.
+
+ The only place where multi-instance device paths are supported is in
+ environment varibles. Multi-instance device paths should never be placed
+ on a Handle.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "UefiDevicePathLib.h"
+
+/**
+ Returns the size of a device path in bytes.
+
+ This function returns the size, in bytes, of the device path data structure
+ specified by DevicePath including the end of device path node.
+ If DevicePath is NULL or invalid, then 0 is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval 0 If DevicePath is NULL or invalid.
+ @retval Others The size of a device path in bytes.
+
+**/
+UINTN
+EFIAPI
+GetDevicePathSize (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ return UefiDevicePathLibGetDevicePathSize (DevicePath);
+}
+
+/**
+ Creates a new copy of an existing device path.
+
+ This function allocates space for a new copy of the device path specified by DevicePath.
+ If DevicePath is NULL, then NULL is returned. If the memory is successfully
+ allocated, then the contents of DevicePath are copied to the newly allocated
+ buffer, and a pointer to that buffer is returned. Otherwise, NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval NULL DevicePath is NULL or invalid.
+ @retval Others A pointer to the duplicated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DuplicateDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ return UefiDevicePathLibDuplicateDevicePath (DevicePath);
+}
+
+/**
+ Creates a new device path by appending a second device path to a first device path.
+
+ This function creates a new device path by appending a copy of SecondDevicePath
+ to a copy of FirstDevicePath in a newly allocated buffer. Only the end-of-device-path
+ device node from SecondDevicePath is retained. The newly created device path is
+ returned. If FirstDevicePath is NULL, then it is ignored, and a duplicate of
+ SecondDevicePath is returned. If SecondDevicePath is NULL, then it is ignored,
+ and a duplicate of FirstDevicePath is returned. If both FirstDevicePath and
+ SecondDevicePath are NULL, then a copy of an end-of-device-path is returned.
+
+ If there is not enough memory for the newly allocated buffer, then NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param FirstDevicePath A pointer to a device path data structure.
+ @param SecondDevicePath A pointer to a device path data structure.
+
+ @retval NULL If there is not enough memory for the newly allocated buffer.
+ @retval NULL If FirstDevicePath or SecondDevicePath is invalid.
+ @retval Others A pointer to the new device path if success.
+ Or a copy an end-of-device-path if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *FirstDevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath OPTIONAL
+ )
+{
+ return UefiDevicePathLibAppendDevicePath (FirstDevicePath, SecondDevicePath);
+}
+
+/**
+ Creates a new path by appending the device node to the device path.
+
+ This function creates a new device path by appending a copy of the device node
+ specified by DevicePathNode to a copy of the device path specified by DevicePath
+ in an allocated buffer. The end-of-device-path device node is moved after the
+ end of the appended device node.
+ If DevicePathNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DevicePathNode, followed by an end-of-device
+ path device node is returned.
+ If both DevicePathNode and DevicePath are NULL then a copy of an end-of-device-path
+ device node is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathNode A pointer to a single device path node.
+
+ @retval NULL If there is not enough memory for the new device path.
+ @retval Others A pointer to the new device path if success.
+ A copy of DevicePathNode followed by an end-of-device-path node
+ if both FirstDevicePath and SecondDevicePath are NULL.
+ A copy of an end-of-device-path node if both FirstDevicePath
+ and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathNode (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL
+ )
+{
+ return UefiDevicePathLibAppendDevicePathNode (DevicePath, DevicePathNode);
+}
+
+/**
+ Creates a new device path by appending the specified device path instance to the specified device
+ path.
+
+ This function creates a new device path by appending a copy of the device path
+ instance specified by DevicePathInstance to a copy of the device path specified
+ by DevicePath in a allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device
+ path instance and a new end-of-device-path-instance node is inserted between.
+ If DevicePath is NULL, then a copy if DevicePathInstance is returned.
+ If DevicePathInstance is NULL, then NULL is returned.
+ If DevicePath or DevicePathInstance is invalid, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathInstance A pointer to a device path instance.
+
+ @return A pointer to the new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance OPTIONAL
+ )
+{
+ return UefiDevicePathLibAppendDevicePathInstance (DevicePath, DevicePathInstance);
+}
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ This function creates a copy of the current device path instance. It also updates
+ DevicePath to point to the next device path instance in the device path (or NULL
+ if no more) and updates Size to hold the size of the device path instance copy.
+ If DevicePath is NULL, then NULL is returned.
+ If DevicePath points to a invalid device path, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+ If Size is NULL, then ASSERT().
+
+ @param DevicePath On input, this holds the pointer to the current
+ device path instance. On output, this holds
+ the pointer to the next device path instance
+ or NULL if there are no more device path
+ instances in the device path pointer to a
+ device path data structure.
+ @param Size On output, this holds the size of the device
+ path instance, in bytes or zero, if DevicePath
+ is NULL.
+
+ @return A pointer to the current device path instance.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+GetNextDevicePathInstance (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
+ OUT UINTN *Size
+ )
+{
+ return UefiDevicePathLibGetNextDevicePathInstance (DevicePath, Size);
+}
+
+/**
+ Creates a device node.
+
+ This function creates a new device node in a newly allocated buffer of size
+ NodeLength and initializes the device path node header with NodeType and NodeSubType.
+ The new device path node is returned.
+ If NodeLength is smaller than a device path header, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param NodeType The device node type for the new device node.
+ @param NodeSubType The device node sub-type for the new device node.
+ @param NodeLength The length of the new device node.
+
+ @return The new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+CreateDeviceNode (
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+ )
+{
+ return UefiDevicePathLibCreateDeviceNode (NodeType, NodeSubType, NodeLength);
+}
+
+/**
+ Determines if a device path is single or multi-instance.
+
+ This function returns TRUE if the device path specified by DevicePath is
+ multi-instance.
+ Otherwise, FALSE is returned.
+ If DevicePath is NULL or invalid, then FALSE is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval TRUE DevicePath is multi-instance.
+ @retval FALSE DevicePath is not multi-instance, or DevicePath
+ is NULL or invalid.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathMultiInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ return UefiDevicePathLibIsDevicePathMultiInstance (DevicePath);
+}
+
+/**
+ Converts a device node to its string representation.
+
+ @param DeviceNode A Pointer to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device node or NULL if DeviceNode
+ is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDeviceNodeToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ return UefiDevicePathLibConvertDeviceNodeToText (DeviceNode, DisplayOnly, AllowShortcuts);
+}
+
+/**
+ Converts a device path to its text representation.
+
+ @param DevicePath A Pointer to the device to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device path or
+ NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDevicePathToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ return UefiDevicePathLibConvertDevicePathToText (DevicePath, DisplayOnly, AllowShortcuts);
+}
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was
+ insufficient memory or text unsupported.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDeviceNode (
+ IN CONST CHAR16 *TextDeviceNode
+ )
+{
+ return UefiDevicePathLibConvertTextToDeviceNode (TextDeviceNode);
+}
+
+/**
+ Convert text to the binary representation of a device path.
+
+
+ @param TextDevicePath TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or
+ there was insufficient memory.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDevicePath (
+ IN CONST CHAR16 *TextDevicePath
+ )
+{
+ return UefiDevicePathLibConvertTextToDevicePath (TextDevicePath);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.h b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.h
new file mode 100644
index 0000000..9097c56
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLib.h
@@ -0,0 +1,451 @@
+/** @file
+ Definition for Device Path library.
+
+Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef _UEFI_DEVICE_PATH_LIB_H_
+#define _UEFI_DEVICE_PATH_LIB_H_
+#include <Uefi.h>
+#include <Protocol/DevicePathUtilities.h>
+#include <Protocol/DebugPort.h>
+#include <Protocol/DevicePathToText.h>
+#include <Protocol/DevicePathFromText.h>
+#include "Efi_Defs_GUID.h"
+#include <Library/DebugLib.h>
+#include <Library/PrintLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/PcdLib.h>
+#include <IndustryStandard/Bluetooth.h>
+
+#define IS_COMMA(a) ((a) == L',')
+#define IS_HYPHEN(a) ((a) == L'-')
+#define IS_DOT(a) ((a) == L'.')
+#define IS_LEFT_PARENTH(a) ((a) == L'(')
+#define IS_RIGHT_PARENTH(a) ((a) == L')')
+#define IS_SLASH(a) ((a) == L'/')
+#define IS_NULL(a) ((a) == L'\0')
+
+
+//
+// Private Data structure
+//
+typedef struct {
+ CHAR16 *Str;
+ UINTN Count;
+ UINTN Capacity;
+} POOL_PRINT;
+
+typedef
+EFI_DEVICE_PATH_PROTOCOL *
+(*DEVICE_PATH_FROM_TEXT) (
+ IN CHAR16 *Str
+ );
+
+typedef
+VOID
+(*DEVICE_PATH_TO_TEXT) (
+ IN OUT POOL_PRINT *Str,
+ IN VOID *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+typedef struct {
+ UINT8 Type;
+ UINT8 SubType;
+ DEVICE_PATH_TO_TEXT Function;
+} DEVICE_PATH_TO_TEXT_TABLE;
+
+typedef struct {
+ UINT8 Type;
+ CHAR16 *Text;
+} DEVICE_PATH_TO_TEXT_GENERIC_TABLE;
+
+typedef struct {
+ CHAR16 *DevicePathNodeText;
+ DEVICE_PATH_FROM_TEXT Function;
+} DEVICE_PATH_FROM_TEXT_TABLE;
+
+typedef struct {
+ BOOLEAN ClassExist;
+ UINT8 Class;
+ BOOLEAN SubClassExist;
+ UINT8 SubClass;
+} USB_CLASS_TEXT;
+
+#define USB_CLASS_AUDIO 1
+#define USB_CLASS_CDCCONTROL 2
+#define USB_CLASS_HID 3
+#define USB_CLASS_IMAGE 6
+#define USB_CLASS_PRINTER 7
+#define USB_CLASS_MASS_STORAGE 8
+#define USB_CLASS_HUB 9
+#define USB_CLASS_CDCDATA 10
+#define USB_CLASS_SMART_CARD 11
+#define USB_CLASS_VIDEO 14
+#define USB_CLASS_DIAGNOSTIC 220
+#define USB_CLASS_WIRELESS 224
+
+#define USB_CLASS_RESERVE 254
+#define USB_SUBCLASS_FW_UPDATE 1
+#define USB_SUBCLASS_IRDA_BRIDGE 2
+#define USB_SUBCLASS_TEST 3
+
+#define RFC_1700_UDP_PROTOCOL 17
+#define RFC_1700_TCP_PROTOCOL 6
+
+#pragma pack(1)
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ EFI_GUID Guid;
+ UINT8 VendorDefinedData[1];
+} VENDOR_DEFINED_HARDWARE_DEVICE_PATH;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ EFI_GUID Guid;
+ UINT8 VendorDefinedData[1];
+} VENDOR_DEFINED_MESSAGING_DEVICE_PATH;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ EFI_GUID Guid;
+ UINT8 VendorDefinedData[1];
+} VENDOR_DEFINED_MEDIA_DEVICE_PATH;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ UINT32 Hid;
+ UINT32 Uid;
+ UINT32 Cid;
+ CHAR8 HidUidCidStr[3];
+} ACPI_EXTENDED_HID_DEVICE_PATH_WITH_STR;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ UINT16 NetworkProtocol;
+ UINT16 LoginOption;
+ UINT64 Lun;
+ UINT16 TargetPortalGroupTag;
+ CHAR8 TargetName[1];
+} ISCSI_DEVICE_PATH_WITH_NAME;
+
+typedef struct {
+ EFI_DEVICE_PATH_PROTOCOL Header;
+ EFI_GUID Guid;
+ UINT8 VendorDefinedData[1];
+} VENDOR_DEVICE_PATH_WITH_DATA;
+
+#pragma pack()
+
+/**
+ Returns the size of a device path in bytes.
+
+ This function returns the size, in bytes, of the device path data structure
+ specified by DevicePath including the end of device path node.
+ If DevicePath is NULL or invalid, then 0 is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval 0 If DevicePath is NULL or invalid.
+ @retval Others The size of a device path in bytes.
+
+**/
+UINTN
+EFIAPI
+UefiDevicePathLibGetDevicePathSize (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Creates a new copy of an existing device path.
+
+ This function allocates space for a new copy of the device path specified by DevicePath.
+ If DevicePath is NULL, then NULL is returned. If the memory is successfully
+ allocated, then the contents of DevicePath are copied to the newly allocated
+ buffer, and a pointer to that buffer is returned. Otherwise, NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval NULL DevicePath is NULL or invalid.
+ @retval Others A pointer to the duplicated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibDuplicateDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+/**
+ Creates a new device path by appending a second device path to a first device path.
+
+ This function creates a new device path by appending a copy of SecondDevicePath
+ to a copy of FirstDevicePath in a newly allocated buffer. Only the end-of-device-path
+ device node from SecondDevicePath is retained. The newly created device path is
+ returned. If FirstDevicePath is NULL, then it is ignored, and a duplicate of
+ SecondDevicePath is returned. If SecondDevicePath is NULL, then it is ignored,
+ and a duplicate of FirstDevicePath is returned. If both FirstDevicePath and
+ SecondDevicePath are NULL, then a copy of an end-of-device-path is returned.
+
+ If there is not enough memory for the newly allocated buffer, then NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param FirstDevicePath A pointer to a device path data structure.
+ @param SecondDevicePath A pointer to a device path data structure.
+
+ @retval NULL If there is not enough memory for the newly allocated buffer.
+ @retval NULL If FirstDevicePath or SecondDevicePath is invalid.
+ @retval Others A pointer to the new device path if success.
+ Or a copy an end-of-device-path if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *FirstDevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath OPTIONAL
+ );
+
+/**
+ Creates a new path by appending the device node to the device path.
+
+ This function creates a new device path by appending a copy of the device node
+ specified by DevicePathNode to a copy of the device path specified by DevicePath
+ in an allocated buffer. The end-of-device-path device node is moved after the
+ end of the appended device node.
+ If DevicePathNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DevicePathNode, followed by an end-of-device
+ path device node is returned.
+ If both DevicePathNode and DevicePath are NULL then a copy of an end-of-device-path
+ device node is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathNode A pointer to a single device path node.
+
+ @retval NULL If there is not enough memory for the new device path.
+ @retval Others A pointer to the new device path if success.
+ A copy of DevicePathNode followed by an end-of-device-path node
+ if both FirstDevicePath and SecondDevicePath are NULL.
+ A copy of an end-of-device-path node if both FirstDevicePath
+ and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePathNode (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL
+ );
+
+/**
+ Creates a new device path by appending the specified device path instance to the specified device
+ path.
+
+ This function creates a new device path by appending a copy of the device path
+ instance specified by DevicePathInstance to a copy of the device path specified
+ by DevicePath in a allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device
+ path instance and a new end-of-device-path-instance node is inserted between.
+ If DevicePath is NULL, then a copy if DevicePathInstance is returned.
+ If DevicePathInstance is NULL, then NULL is returned.
+ If DevicePath or DevicePathInstance is invalid, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathInstance A pointer to a device path instance.
+
+ @return A pointer to the new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibAppendDevicePathInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance OPTIONAL
+ );
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ This function creates a copy of the current device path instance. It also updates
+ DevicePath to point to the next device path instance in the device path (or NULL
+ if no more) and updates Size to hold the size of the device path instance copy.
+ If DevicePath is NULL, then NULL is returned.
+ If DevicePath points to a invalid device path, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+ If Size is NULL, then ASSERT().
+
+ @param DevicePath On input, this holds the pointer to the current
+ device path instance. On output, this holds
+ the pointer to the next device path instance
+ or NULL if there are no more device path
+ instances in the device path pointer to a
+ device path data structure.
+ @param Size On output, this holds the size of the device
+ path instance, in bytes or zero, if DevicePath
+ is NULL.
+
+ @return A pointer to the current device path instance.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibGetNextDevicePathInstance (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
+ OUT UINTN *Size
+ );
+
+/**
+ Creates a device node.
+
+ This function creates a new device node in a newly allocated buffer of size
+ NodeLength and initializes the device path node header with NodeType and NodeSubType.
+ The new device path node is returned.
+ If NodeLength is smaller than a device path header, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param NodeType The device node type for the new device node.
+ @param NodeSubType The device node sub-type for the new device node.
+ @param NodeLength The length of the new device node.
+
+ @return The new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibCreateDeviceNode (
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+ );
+
+/**
+ Determines if a device path is single or multi-instance.
+
+ This function returns TRUE if the device path specified by DevicePath is
+ multi-instance.
+ Otherwise, FALSE is returned.
+ If DevicePath is NULL or invalid, then FALSE is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval TRUE DevicePath is multi-instance.
+ @retval FALSE DevicePath is not multi-instance, or DevicePath
+ is NULL or invalid.
+
+**/
+BOOLEAN
+EFIAPI
+UefiDevicePathLibIsDevicePathMultiInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ );
+
+
+/**
+ Converts a device path to its text representation.
+
+ @param DevicePath A Pointer to the device to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device path or
+ NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+UefiDevicePathLibConvertDevicePathToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+/**
+ Converts a device node to its string representation.
+
+ @param DeviceNode A Pointer to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device node or NULL if DeviceNode
+ is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+UefiDevicePathLibConvertDeviceNodeToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ );
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was
+ insufficient memory or text unsupported.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibConvertTextToDeviceNode (
+ IN CONST CHAR16 *TextDeviceNode
+ );
+
+/**
+ Convert text to the binary representation of a device path.
+
+
+ @param TextDevicePath TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or
+ there was insufficient memory.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+UefiDevicePathLibConvertTextToDevicePath (
+ IN CONST CHAR16 *TextDevicePath
+ );
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLibOptionalDevicePathProtocol.c b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLibOptionalDevicePathProtocol.c
new file mode 100644
index 0000000..106ff24
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiDevicePathLib/UefiDevicePathLibOptionalDevicePathProtocol.c
@@ -0,0 +1,478 @@
+/** @file
+ Device Path services. The thing to remember is device paths are built out of
+ nodes. The device path is terminated by an end node that is length
+ sizeof(EFI_DEVICE_PATH_PROTOCOL). That would be why there is sizeof(EFI_DEVICE_PATH_PROTOCOL)
+ all over this file.
+
+ The only place where multi-instance device paths are supported is in
+ environment varibles. Multi-instance device paths should never be placed
+ on a Handle.
+
+ Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "UefiDevicePathLib.h"
+
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_DEVICE_PATH_UTILITIES_PROTOCOL *mDevicePathLibDevicePathUtilities = NULL;
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_DEVICE_PATH_TO_TEXT_PROTOCOL *mDevicePathLibDevicePathToText = NULL;
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_DEVICE_PATH_FROM_TEXT_PROTOCOL *mDevicePathLibDevicePathFromText = NULL;
+
+/**
+ The constructor function caches the pointer to DevicePathUtilites protocol,
+ DevicePathToText protocol and DevicePathFromText protocol.
+
+ The constructor function locates these three protocols from protocol database.
+ It will caches the pointer to local protocol instance if that operation fails
+ and it will always return EFI_SUCCESS.
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The constructor always returns EFI_SUCCESS.
+
+**/
+EFI_STATUS
+EFIAPI
+UefiDevicePathLibOptionalDevicePathProtocolConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ Status = gBS->LocateProtocol (
+ &gEfiDevicePathUtilitiesProtocolGuid,
+ NULL,
+ (VOID**) &mDevicePathLibDevicePathUtilities
+ );
+ ASSERT_EFI_ERROR (Status);
+ ASSERT (mDevicePathLibDevicePathUtilities != NULL);
+ return Status;
+}
+
+/**
+ Returns the size of a device path in bytes.
+
+ This function returns the size, in bytes, of the device path data structure
+ specified by DevicePath including the end of device path node.
+ If DevicePath is NULL or invalid, then 0 is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval 0 If DevicePath is NULL or invalid.
+ @retval Others The size of a device path in bytes.
+
+**/
+UINTN
+EFIAPI
+GetDevicePathSize (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->GetDevicePathSize (DevicePath);
+ } else {
+ return UefiDevicePathLibGetDevicePathSize (DevicePath);
+ }
+}
+
+/**
+ Creates a new copy of an existing device path.
+
+ This function allocates space for a new copy of the device path specified by DevicePath.
+ If DevicePath is NULL, then NULL is returned. If the memory is successfully
+ allocated, then the contents of DevicePath are copied to the newly allocated
+ buffer, and a pointer to that buffer is returned. Otherwise, NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval NULL DevicePath is NULL or invalid.
+ @retval Others A pointer to the duplicated device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+DuplicateDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->DuplicateDevicePath (DevicePath);
+ } else {
+ return UefiDevicePathLibDuplicateDevicePath (DevicePath);
+ }
+}
+
+/**
+ Creates a new device path by appending a second device path to a first device path.
+
+ This function creates a new device path by appending a copy of SecondDevicePath
+ to a copy of FirstDevicePath in a newly allocated buffer. Only the end-of-device-path
+ device node from SecondDevicePath is retained. The newly created device path is
+ returned. If FirstDevicePath is NULL, then it is ignored, and a duplicate of
+ SecondDevicePath is returned. If SecondDevicePath is NULL, then it is ignored,
+ and a duplicate of FirstDevicePath is returned. If both FirstDevicePath and
+ SecondDevicePath are NULL, then a copy of an end-of-device-path is returned.
+
+ If there is not enough memory for the newly allocated buffer, then NULL is returned.
+ The memory for the new device path is allocated from EFI boot services memory.
+ It is the responsibility of the caller to free the memory allocated.
+
+ @param FirstDevicePath A pointer to a device path data structure.
+ @param SecondDevicePath A pointer to a device path data structure.
+
+ @retval NULL If there is not enough memory for the newly allocated buffer.
+ @retval NULL If FirstDevicePath or SecondDevicePath is invalid.
+ @retval Others A pointer to the new device path if success.
+ Or a copy an end-of-device-path if both FirstDevicePath and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePath (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *FirstDevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *SecondDevicePath OPTIONAL
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->AppendDevicePath (FirstDevicePath, SecondDevicePath);
+ } else {
+ return UefiDevicePathLibAppendDevicePath (FirstDevicePath, SecondDevicePath);
+ }
+}
+
+/**
+ Creates a new path by appending the device node to the device path.
+
+ This function creates a new device path by appending a copy of the device node
+ specified by DevicePathNode to a copy of the device path specified by DevicePath
+ in an allocated buffer. The end-of-device-path device node is moved after the
+ end of the appended device node.
+ If DevicePathNode is NULL then a copy of DevicePath is returned.
+ If DevicePath is NULL then a copy of DevicePathNode, followed by an end-of-device
+ path device node is returned.
+ If both DevicePathNode and DevicePath are NULL then a copy of an end-of-device-path
+ device node is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathNode A pointer to a single device path node.
+
+ @retval NULL If there is not enough memory for the new device path.
+ @retval Others A pointer to the new device path if success.
+ A copy of DevicePathNode followed by an end-of-device-path node
+ if both FirstDevicePath and SecondDevicePath are NULL.
+ A copy of an end-of-device-path node if both FirstDevicePath
+ and SecondDevicePath are NULL.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathNode (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->AppendDeviceNode (DevicePath, DevicePathNode);
+ } else {
+ return UefiDevicePathLibAppendDevicePathNode (DevicePath, DevicePathNode);
+ }
+}
+
+/**
+ Creates a new device path by appending the specified device path instance to the specified device
+ path.
+
+ This function creates a new device path by appending a copy of the device path
+ instance specified by DevicePathInstance to a copy of the device path specified
+ by DevicePath in a allocated buffer.
+ The end-of-device-path device node is moved after the end of the appended device
+ path instance and a new end-of-device-path-instance node is inserted between.
+ If DevicePath is NULL, then a copy if DevicePathInstance is returned.
+ If DevicePathInstance is NULL, then NULL is returned.
+ If DevicePath or DevicePathInstance is invalid, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param DevicePath A pointer to a device path data structure.
+ @param DevicePathInstance A pointer to a device path instance.
+
+ @return A pointer to the new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+AppendDevicePathInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath, OPTIONAL
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance OPTIONAL
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->AppendDevicePathInstance (DevicePath, DevicePathInstance);
+ } else {
+ return UefiDevicePathLibAppendDevicePathInstance (DevicePath, DevicePathInstance);
+ }
+}
+
+/**
+ Creates a copy of the current device path instance and returns a pointer to the next device path
+ instance.
+
+ This function creates a copy of the current device path instance. It also updates
+ DevicePath to point to the next device path instance in the device path (or NULL
+ if no more) and updates Size to hold the size of the device path instance copy.
+ If DevicePath is NULL, then NULL is returned.
+ If DevicePath points to a invalid device path, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+ If Size is NULL, then ASSERT().
+
+ @param DevicePath On input, this holds the pointer to the current
+ device path instance. On output, this holds
+ the pointer to the next device path instance
+ or NULL if there are no more device path
+ instances in the device path pointer to a
+ device path data structure.
+ @param Size On output, this holds the size of the device
+ path instance, in bytes or zero, if DevicePath
+ is NULL.
+
+ @return A pointer to the current device path instance.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+GetNextDevicePathInstance (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
+ OUT UINTN *Size
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->GetNextDevicePathInstance (DevicePath, Size);
+ } else {
+ return UefiDevicePathLibGetNextDevicePathInstance (DevicePath, Size);
+ }
+}
+
+/**
+ Creates a device node.
+
+ This function creates a new device node in a newly allocated buffer of size
+ NodeLength and initializes the device path node header with NodeType and NodeSubType.
+ The new device path node is returned.
+ If NodeLength is smaller than a device path header, then NULL is returned.
+ If there is not enough memory to allocate space for the new device path, then
+ NULL is returned.
+ The memory is allocated from EFI boot services memory. It is the responsibility
+ of the caller to free the memory allocated.
+
+ @param NodeType The device node type for the new device node.
+ @param NodeSubType The device node sub-type for the new device node.
+ @param NodeLength The length of the new device node.
+
+ @return The new device path.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+CreateDeviceNode (
+ IN UINT8 NodeType,
+ IN UINT8 NodeSubType,
+ IN UINT16 NodeLength
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->CreateDeviceNode (NodeType, NodeSubType, NodeLength);
+ } else {
+ return UefiDevicePathLibCreateDeviceNode (NodeType, NodeSubType, NodeLength);
+ }
+}
+
+/**
+ Determines if a device path is single or multi-instance.
+
+ This function returns TRUE if the device path specified by DevicePath is
+ multi-instance.
+ Otherwise, FALSE is returned.
+ If DevicePath is NULL or invalid, then FALSE is returned.
+
+ @param DevicePath A pointer to a device path data structure.
+
+ @retval TRUE DevicePath is multi-instance.
+ @retval FALSE DevicePath is not multi-instance, or DevicePath
+ is NULL or invalid.
+
+**/
+BOOLEAN
+EFIAPI
+IsDevicePathMultiInstance (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath
+ )
+{
+ if (mDevicePathLibDevicePathUtilities != NULL) {
+ return mDevicePathLibDevicePathUtilities->IsDevicePathMultiInstance (DevicePath);
+ } else {
+ return UefiDevicePathLibIsDevicePathMultiInstance (DevicePath);
+ }
+}
+
+/**
+ Locate and return the protocol instance identified by the ProtocolGuid.
+
+ @param ProtocolGuid The GUID of the protocol.
+
+ @return A pointer to the protocol instance or NULL when absent.
+**/
+VOID *
+UefiDevicePathLibLocateProtocol (
+ EFI_GUID *ProtocolGuid
+ )
+{
+ EFI_STATUS Status;
+ VOID *Protocol;
+ Status = gBS->LocateProtocol (
+ ProtocolGuid,
+ NULL,
+ (VOID**) &Protocol
+ );
+ if (EFI_ERROR (Status)) {
+ return NULL;
+ } else {
+ return Protocol;
+ }
+}
+
+/**
+ Converts a device node to its string representation.
+
+ @param DeviceNode A Pointer to the device node to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device node or NULL if DeviceNode
+ is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDeviceNodeToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DeviceNode,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ if (mDevicePathLibDevicePathToText == NULL) {
+ mDevicePathLibDevicePathToText = UefiDevicePathLibLocateProtocol (&gEfiDevicePathToTextProtocolGuid);
+ }
+ if (mDevicePathLibDevicePathToText != NULL) {
+ return mDevicePathLibDevicePathToText->ConvertDeviceNodeToText (DeviceNode, DisplayOnly, AllowShortcuts);
+ }
+
+ return UefiDevicePathLibConvertDeviceNodeToText (DeviceNode, DisplayOnly, AllowShortcuts);
+}
+
+/**
+ Converts a device path to its text representation.
+
+ @param DevicePath A Pointer to the device to be converted.
+ @param DisplayOnly If DisplayOnly is TRUE, then the shorter text representation
+ of the display node is used, where applicable. If DisplayOnly
+ is FALSE, then the longer text representation of the display node
+ is used.
+ @param AllowShortcuts If AllowShortcuts is TRUE, then the shortcut forms of text
+ representation for a device node can be used, where applicable.
+
+ @return A pointer to the allocated text representation of the device path or
+ NULL if DeviceNode is NULL or there was insufficient memory.
+
+**/
+CHAR16 *
+EFIAPI
+ConvertDevicePathToText (
+ IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath,
+ IN BOOLEAN DisplayOnly,
+ IN BOOLEAN AllowShortcuts
+ )
+{
+ if (mDevicePathLibDevicePathToText == NULL) {
+ mDevicePathLibDevicePathToText = UefiDevicePathLibLocateProtocol (&gEfiDevicePathToTextProtocolGuid);
+ }
+ if (mDevicePathLibDevicePathToText != NULL) {
+ return mDevicePathLibDevicePathToText->ConvertDevicePathToText (DevicePath, DisplayOnly, AllowShortcuts);
+ }
+
+ return UefiDevicePathLibConvertDevicePathToText (DevicePath, DisplayOnly, AllowShortcuts);
+}
+
+/**
+ Convert text to the binary representation of a device node.
+
+ @param TextDeviceNode TextDeviceNode points to the text representation of a device
+ node. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was
+ insufficient memory or text unsupported.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDeviceNode (
+ IN CONST CHAR16 *TextDeviceNode
+ )
+{
+ if (mDevicePathLibDevicePathFromText == NULL) {
+ mDevicePathLibDevicePathFromText = UefiDevicePathLibLocateProtocol (&gEfiDevicePathFromTextProtocolGuid);
+ }
+ if (mDevicePathLibDevicePathFromText != NULL) {
+ return mDevicePathLibDevicePathFromText->ConvertTextToDeviceNode (TextDeviceNode);
+ }
+
+ return UefiDevicePathLibConvertTextToDeviceNode (TextDeviceNode);
+}
+
+/**
+ Convert text to the binary representation of a device path.
+
+
+ @param TextDevicePath TextDevicePath points to the text representation of a device
+ path. Conversion starts with the first character and continues
+ until the first non-device node character.
+
+ @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or
+ there was insufficient memory.
+
+**/
+EFI_DEVICE_PATH_PROTOCOL *
+EFIAPI
+ConvertTextToDevicePath (
+ IN CONST CHAR16 *TextDevicePath
+ )
+{
+ if (mDevicePathLibDevicePathFromText == NULL) {
+ mDevicePathLibDevicePathFromText = UefiDevicePathLibLocateProtocol (&gEfiDevicePathFromTextProtocolGuid);
+ }
+ if (mDevicePathLibDevicePathFromText != NULL) {
+ return mDevicePathLibDevicePathFromText->ConvertTextToDevicePath (TextDevicePath);
+ }
+
+ return UefiDevicePathLibConvertTextToDevicePath (TextDevicePath);
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/Acpi.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/Acpi.c
new file mode 100644
index 0000000..ae0ad01
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/Acpi.c
@@ -0,0 +1,421 @@
+/** @file
+ This module provides help function for finding ACPI table.
+
+ Copyright (c) 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiLibInternal.h"
+#include <IndustryStandard/Acpi.h>
+
+/**
+ This function scans ACPI table in XSDT/RSDT.
+
+ @param Sdt ACPI XSDT/RSDT.
+ @param TablePointerSize Size of table pointer: 8(XSDT) or 4(RSDT).
+ @param Signature ACPI table signature.
+ @param PreviousTable Pointer to previous returned table to locate
+ next table, or NULL to locate first table.
+ @param PreviousTableLocated Pointer to the indicator about whether the
+ previous returned table could be located, or
+ NULL if PreviousTable is NULL.
+
+ If PreviousTable is NULL and PreviousTableLocated is not NULL, then ASSERT().
+ If PreviousTable is not NULL and PreviousTableLocated is NULL, then ASSERT().
+
+ @return ACPI table or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+ScanTableInSDT (
+ IN EFI_ACPI_DESCRIPTION_HEADER *Sdt,
+ IN UINTN TablePointerSize,
+ IN UINT32 Signature,
+ IN EFI_ACPI_COMMON_HEADER *PreviousTable, OPTIONAL
+ OUT BOOLEAN *PreviousTableLocated OPTIONAL
+ )
+{
+ UINTN Index;
+ UINTN EntryCount;
+ UINT64 EntryPtr;
+ UINTN BasePtr;
+ EFI_ACPI_COMMON_HEADER *Table;
+
+ if (PreviousTableLocated != NULL) {
+ ASSERT (PreviousTable != NULL);
+ *PreviousTableLocated = FALSE;
+ } else {
+ ASSERT (PreviousTable == NULL);
+ }
+
+ if (Sdt == NULL) {
+ return NULL;
+ }
+
+ EntryCount = (Sdt->Length - sizeof (EFI_ACPI_DESCRIPTION_HEADER)) / TablePointerSize;
+
+ BasePtr = (UINTN)(Sdt + 1);
+ for (Index = 0; Index < EntryCount; Index ++) {
+ EntryPtr = 0;
+ CopyMem (&EntryPtr, (VOID *)(BasePtr + Index * TablePointerSize), TablePointerSize);
+ Table = (EFI_ACPI_COMMON_HEADER *)((UINTN)(EntryPtr));
+ if ((Table != NULL) && (Table->Signature == Signature)) {
+ if (PreviousTable != NULL) {
+ if (Table == PreviousTable) {
+ *PreviousTableLocated = TRUE;
+ } else if (*PreviousTableLocated) {
+ //
+ // Return next table.
+ //
+ return Table;
+ }
+ } else {
+ //
+ // Return first table.
+ //
+ return Table;
+ }
+
+ }
+ }
+
+ return NULL;
+}
+
+/**
+ To locate FACS in FADT.
+
+ @param Fadt FADT table pointer.
+
+ @return FACS table pointer or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+LocateAcpiFacsFromFadt (
+ IN EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *Fadt
+ )
+{
+ EFI_ACPI_COMMON_HEADER *Facs;
+ UINT64 Data64;
+
+ if (Fadt == NULL) {
+ return NULL;
+ }
+
+ if (Fadt->Header.Revision < EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION) {
+ Facs = (EFI_ACPI_COMMON_HEADER *)(UINTN)Fadt->FirmwareCtrl;
+ } else {
+ CopyMem (&Data64, &Fadt->XFirmwareCtrl, sizeof(UINT64));
+ if (Data64 != 0) {
+ Facs = (EFI_ACPI_COMMON_HEADER *)(UINTN)Data64;
+ } else {
+ Facs = (EFI_ACPI_COMMON_HEADER *)(UINTN)Fadt->FirmwareCtrl;
+ }
+ }
+ return Facs;
+}
+
+/**
+ To locate DSDT in FADT.
+
+ @param Fadt FADT table pointer.
+
+ @return DSDT table pointer or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+LocateAcpiDsdtFromFadt (
+ IN EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *Fadt
+ )
+{
+ EFI_ACPI_COMMON_HEADER *Dsdt;
+ UINT64 Data64;
+
+ if (Fadt == NULL) {
+ return NULL;
+ }
+
+ if (Fadt->Header.Revision < EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_REVISION) {
+ Dsdt = (EFI_ACPI_COMMON_HEADER *)(UINTN)Fadt->Dsdt;
+ } else {
+ CopyMem (&Data64, &Fadt->XDsdt, sizeof(UINT64));
+ if (Data64 != 0) {
+ Dsdt = (EFI_ACPI_COMMON_HEADER *)(UINTN)Data64;
+ } else {
+ Dsdt = (EFI_ACPI_COMMON_HEADER *)(UINTN)Fadt->Dsdt;
+ }
+ }
+ return Dsdt;
+}
+
+/**
+ To locate ACPI table in ACPI ConfigurationTable.
+
+ @param AcpiGuid The GUID used to get ACPI ConfigurationTable.
+ @param Signature ACPI table signature.
+ @param PreviousTable Pointer to previous returned table to locate
+ next table, or NULL to locate first table.
+ @param PreviousTableLocated Pointer to the indicator to return whether the
+ previous returned table could be located or not,
+ or NULL if PreviousTable is NULL.
+
+ If PreviousTable is NULL and PreviousTableLocated is not NULL, then ASSERT().
+ If PreviousTable is not NULL and PreviousTableLocated is NULL, then ASSERT().
+ If AcpiGuid is NULL, then ASSERT().
+
+ @return ACPI table or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+LocateAcpiTableInAcpiConfigurationTable (
+ IN EFI_GUID *AcpiGuid,
+ IN UINT32 Signature,
+ IN EFI_ACPI_COMMON_HEADER *PreviousTable, OPTIONAL
+ OUT BOOLEAN *PreviousTableLocated OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ EFI_ACPI_COMMON_HEADER *Table;
+ EFI_ACPI_2_0_ROOT_SYSTEM_DESCRIPTION_POINTER *Rsdp;
+ EFI_ACPI_DESCRIPTION_HEADER *Rsdt;
+ EFI_ACPI_DESCRIPTION_HEADER *Xsdt;
+ EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *Fadt;
+
+ if (PreviousTableLocated != NULL) {
+ ASSERT (PreviousTable != NULL);
+ *PreviousTableLocated = FALSE;
+ } else {
+ ASSERT (PreviousTable == NULL);
+ }
+
+ Rsdp = NULL;
+ //
+ // Get ACPI ConfigurationTable (RSD_PTR)
+ //
+ Status = EfiGetSystemConfigurationTable(AcpiGuid, (VOID **)&Rsdp);
+ if (EFI_ERROR (Status) || (Rsdp == NULL)) {
+ return NULL;
+ }
+
+ Table = NULL;
+
+ //
+ // Search XSDT
+ //
+ if (Rsdp->Revision >= EFI_ACPI_2_0_ROOT_SYSTEM_DESCRIPTION_POINTER_REVISION) {
+ Xsdt = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN) Rsdp->XsdtAddress;
+ if (Signature == EFI_ACPI_2_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE) {
+ ASSERT (PreviousTable == NULL);
+ //
+ // It is to locate DSDT,
+ // need to locate FADT first.
+ //
+ Fadt = (EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *) ScanTableInSDT (
+ Xsdt,
+ sizeof (UINT64),
+ EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE,
+ NULL,
+ NULL
+ );
+ Table = LocateAcpiDsdtFromFadt (Fadt);
+ } else if (Signature == EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE) {
+ ASSERT (PreviousTable == NULL);
+ //
+ // It is to locate FACS,
+ // need to locate FADT first.
+ //
+ Fadt = (EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *) ScanTableInSDT (
+ Xsdt,
+ sizeof (UINT64),
+ EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE,
+ NULL,
+ NULL
+ );
+ Table = LocateAcpiFacsFromFadt (Fadt);
+ } else {
+ Table = ScanTableInSDT (
+ Xsdt,
+ sizeof (UINT64),
+ Signature,
+ PreviousTable,
+ PreviousTableLocated
+ );
+ }
+ }
+
+ if (Table != NULL) {
+ return Table;
+ } else if ((PreviousTableLocated != NULL) &&
+ *PreviousTableLocated) {
+ //
+ // PreviousTable could be located in XSDT,
+ // but next table could not be located in XSDT.
+ //
+ return NULL;
+ }
+
+ //
+ // Search RSDT
+ //
+ Rsdt = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN) Rsdp->RsdtAddress;
+ if (Signature == EFI_ACPI_2_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE) {
+ ASSERT (PreviousTable == NULL);
+ //
+ // It is to locate DSDT,
+ // need to locate FADT first.
+ //
+ Fadt = (EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *) ScanTableInSDT (
+ Rsdt,
+ sizeof (UINT32),
+ EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE,
+ NULL,
+ NULL
+ );
+ Table = LocateAcpiDsdtFromFadt (Fadt);
+ } else if (Signature == EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE) {
+ ASSERT (PreviousTable == NULL);
+ //
+ // It is to locate FACS,
+ // need to locate FADT first.
+ //
+ Fadt = (EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE *) ScanTableInSDT (
+ Rsdt,
+ sizeof (UINT32),
+ EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE,
+ NULL,
+ NULL
+ );
+ Table = LocateAcpiFacsFromFadt (Fadt);
+ } else {
+ Table = ScanTableInSDT (
+ Rsdt,
+ sizeof (UINT32),
+ Signature,
+ PreviousTable,
+ PreviousTableLocated
+ );
+ }
+
+ return Table;
+}
+
+/**
+ This function locates next ACPI table in XSDT/RSDT based on Signature and
+ previous returned Table.
+
+ If PreviousTable is NULL:
+ This function will locate the first ACPI table in XSDT/RSDT based on
+ Signature in gEfiAcpi20TableGuid system configuration table first, and then
+ gEfiAcpi10TableGuid system configuration table.
+ This function will locate in XSDT first, and then RSDT.
+ For DSDT, this function will locate XDsdt in FADT first, and then Dsdt in
+ FADT.
+ For FACS, this function will locate XFirmwareCtrl in FADT first, and then
+ FirmwareCtrl in FADT.
+
+ If PreviousTable is not NULL:
+ 1. If it could be located in XSDT in gEfiAcpi20TableGuid system configuration
+ table, then this function will just locate next table in XSDT in
+ gEfiAcpi20TableGuid system configuration table.
+ 2. If it could be located in RSDT in gEfiAcpi20TableGuid system configuration
+ table, then this function will just locate next table in RSDT in
+ gEfiAcpi20TableGuid system configuration table.
+ 3. If it could be located in RSDT in gEfiAcpi10TableGuid system configuration
+ table, then this function will just locate next table in RSDT in
+ gEfiAcpi10TableGuid system configuration table.
+
+ It's not supported that PreviousTable is not NULL but PreviousTable->Signature
+ is not same with Signature, NULL will be returned.
+
+ @param Signature ACPI table signature.
+ @param PreviousTable Pointer to previous returned table to locate next
+ table, or NULL to locate first table.
+
+ @return Next ACPI table or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+EFIAPI
+EfiLocateNextAcpiTable (
+ IN UINT32 Signature,
+ IN EFI_ACPI_COMMON_HEADER *PreviousTable OPTIONAL
+ )
+{
+ EFI_ACPI_COMMON_HEADER *Table;
+ BOOLEAN TempPreviousTableLocated;
+ BOOLEAN *PreviousTableLocated;
+
+ if (PreviousTable != NULL) {
+ if (PreviousTable->Signature != Signature) {
+ //
+ // PreviousTable->Signature is not same with Signature.
+ //
+ return NULL;
+ } else if ((Signature == EFI_ACPI_2_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) ||
+ (Signature == EFI_ACPI_2_0_DIFFERENTIATED_SYSTEM_DESCRIPTION_TABLE_SIGNATURE) ||
+ (Signature == EFI_ACPI_2_0_FIRMWARE_ACPI_CONTROL_STRUCTURE_SIGNATURE)) {
+ //
+ // There is only one FADT/DSDT/FACS table,
+ // so don't try to locate next one.
+ //
+ return NULL;
+ }
+
+ PreviousTableLocated = &TempPreviousTableLocated;
+ *PreviousTableLocated = FALSE;
+ } else {
+ PreviousTableLocated = NULL;
+ }
+
+ Table = LocateAcpiTableInAcpiConfigurationTable (
+ &gEfiAcpi20TableGuid,
+ Signature,
+ PreviousTable,
+ PreviousTableLocated
+ );
+ if (Table != NULL) {
+ return Table;
+ } else if ((PreviousTableLocated != NULL) &&
+ *PreviousTableLocated) {
+ //
+ // PreviousTable could be located in gEfiAcpi20TableGuid system
+ // configuration table, but next table could not be located in
+ // gEfiAcpi20TableGuid system configuration table.
+ //
+ return NULL;
+ }
+
+ return LocateAcpiTableInAcpiConfigurationTable (
+ &gEfiAcpi10TableGuid,
+ Signature,
+ PreviousTable,
+ PreviousTableLocated
+ );
+}
+
+/**
+ This function locates first ACPI table in XSDT/RSDT based on Signature.
+
+ This function will locate the first ACPI table in XSDT/RSDT based on
+ Signature in gEfiAcpi20TableGuid system configuration table first, and then
+ gEfiAcpi10TableGuid system configuration table.
+ This function will locate in XSDT first, and then RSDT.
+ For DSDT, this function will locate XDsdt in FADT first, and then Dsdt in
+ FADT.
+ For FACS, this function will locate XFirmwareCtrl in FADT first, and then
+ FirmwareCtrl in FADT.
+
+ @param Signature ACPI table signature.
+
+ @return First ACPI table or NULL if not found.
+
+**/
+EFI_ACPI_COMMON_HEADER *
+EFIAPI
+EfiLocateFirstAcpiTable (
+ IN UINT32 Signature
+ )
+{
+ return EfiLocateNextAcpiTable (Signature, NULL);
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/Console.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/Console.c
new file mode 100644
index 0000000..17ec31c
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/Console.c
@@ -0,0 +1,566 @@
+/** @file
+ This module provide help function for displaying unicode string.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+
+#include "UefiLibInternal.h"
+
+typedef struct {
+ CHAR16 WChar;
+ UINT32 Width;
+} UNICODE_WIDTH_ENTRY;
+
+#define NARROW_CHAR 0xFFF0
+#define WIDE_CHAR 0xFFF1
+
+GLOBAL_REMOVE_IF_UNREFERENCED CONST UNICODE_WIDTH_ENTRY mUnicodeWidthTable[] = {
+ //
+ // General script area
+ //
+ {(CHAR16)0x1FFF, 1},
+ /*
+ * Merge the blocks and replace them with the above entry as they fall to
+ * the same category and they are all narrow glyph. This will reduce search
+ * time and table size. The merge will omit the reserved code.
+ *
+ * Remove the above item if below is un-commented.
+ *
+ {(CHAR16)0x007F, 1}, // C0 controls and basic Latin. 0x0000-0x007F
+ {(CHAR16)0x00FF, 1}, // C1 controls and Latin-1 support. 0x0080-0x00FF
+ {(CHAR16)0x017F, 1}, // Latin extended-A. 0x0100-0x017F
+ {(CHAR16)0x024F, 1}, // Latin extended-B. 0x0180-0x024F
+ {(CHAR16)0x02AF, 1}, // IPA extensions. 0x0250-0x02AF
+ {(CHAR16)0x02FF, 1}, // Spacing modifier letters. 0x02B0-0x02FF
+ {(CHAR16)0x036F, 1}, // Combining diacritical marks. 0x0300-0x036F
+ {(CHAR16)0x03FF, 1}, // Greek. 0x0370-0x03FF
+ {(CHAR16)0x04FF, 1}, // Cyrillic. 0x0400-0x04FF
+ {(CHAR16)0x052F, 0}, // Unassigned. As Armenian in ver3.0. 0x0500-0x052F
+ {(CHAR16)0x058F, 1}, // Armenian. 0x0530-0x058F
+ {(CHAR16)0x05FF, 1}, // Hebrew. 0x0590-0x05FF
+ {(CHAR16)0x06FF, 1}, // Arabic. 0x0600-0x06FF
+ {(CHAR16)0x08FF, 0}, // Unassigned. 0x0700-0x08FF
+ {(CHAR16)0x097F, 1}, // Devanagari. 0x0900-0x097F
+ {(CHAR16)0x09FF, 1}, // Bengali. 0x0980-0x09FF
+ {(CHAR16)0x0A7F, 1}, // Gurmukhi. 0x0A00-0x0A7F
+ {(CHAR16)0x0AFF, 1}, // Gujarati. 0x0A80-0x0AFF
+ {(CHAR16)0x0B7F, 1}, // Oriya. 0x0B00-0x0B7F
+ {(CHAR16)0x0BFF, 1}, // Tamil. (See page 7-92). 0x0B80-0x0BFF
+ {(CHAR16)0x0C7F, 1}, // Telugu. 0x0C00-0x0C7F
+ {(CHAR16)0x0CFF, 1}, // Kannada. (See page 7-100). 0x0C80-0x0CFF
+ {(CHAR16)0x0D7F, 1}, // Malayalam (See page 7-104). 0x0D00-0x0D7F
+ {(CHAR16)0x0DFF, 0}, // Unassigned. 0x0D80-0x0DFF
+ {(CHAR16)0x0E7F, 1}, // Thai. 0x0E00-0x0E7F
+ {(CHAR16)0x0EFF, 1}, // Lao. 0x0E80-0x0EFF
+ {(CHAR16)0x0FBF, 1}, // Tibetan. 0x0F00-0x0FBF
+ {(CHAR16)0x109F, 0}, // Unassigned. 0x0FC0-0x109F
+ {(CHAR16)0x10FF, 1}, // Georgian. 0x10A0-0x10FF
+ {(CHAR16)0x11FF, 1}, // Hangul Jamo. 0x1100-0x11FF
+ {(CHAR16)0x1DFF, 0}, // Unassigned. 0x1200-0x1DFF
+ {(CHAR16)0x1EFF, 1}, // Latin extended additional. 0x1E00-0x1EFF
+ {(CHAR16)0x1FFF, 1}, // Greek extended. 0x1F00-0x1FFF
+ *
+ */
+
+ //
+ // Symbol area
+ //
+ {(CHAR16)0x2FFF, 1},
+ /*
+ * Merge the blocks and replace them with the above entry as they fall to
+ * the same category and they are all narrow glyph. This will reduce search
+ * time and table size. The merge will omit the reserved code.
+ *
+ * Remove the above item if below is un-commented.
+ *
+ {(CHAR16)0x206F, 1}, // General punctuation. (See page7-154). 0x200-0x206F
+ {(CHAR16)0x209F, 1}, // Superscripts and subscripts. 0x2070-0x209F
+ {(CHAR16)0x20CF, 1}, // Currency symbols. 0x20A0-0x20CF
+ {(CHAR16)0x20FF, 1}, // Combining diacritical marks for symbols. 0x20D0-0x20FF
+ {(CHAR16)0x214F, 1}, // Letterlike sympbols. 0x2100-0x214F
+ {(CHAR16)0x218F, 1}, // Number forms. 0x2150-0x218F
+ {(CHAR16)0x21FF, 1}, // Arrows. 0x2190-0x21FF
+ {(CHAR16)0x22FF, 1}, // Mathematical operators. 0x2200-0x22FF
+ {(CHAR16)0x23FF, 1}, // Miscellaneous technical. 0x2300-0x23FF
+ {(CHAR16)0x243F, 1}, // Control pictures. 0x2400-0x243F
+ {(CHAR16)0x245F, 1}, // Optical character recognition. 0x2440-0x245F
+ {(CHAR16)0x24FF, 1}, // Enclosed alphanumerics. 0x2460-0x24FF
+ {(CHAR16)0x257F, 1}, // Box drawing. 0x2500-0x257F
+ {(CHAR16)0x259F, 1}, // Block elements. 0x2580-0x259F
+ {(CHAR16)0x25FF, 1}, // Geometric shapes. 0x25A0-0x25FF
+ {(CHAR16)0x26FF, 1}, // Miscellaneous symbols. 0x2600-0x26FF
+ {(CHAR16)0x27BF, 1}, // Dingbats. 0x2700-0x27BF
+ {(CHAR16)0x2FFF, 0}, // Reserved. 0x27C0-0x2FFF
+ *
+ */
+
+ //
+ // CJK phonetics and symbol area
+ //
+ {(CHAR16)0x33FF, 2},
+ /*
+ * Merge the blocks and replace them with the above entry as they fall to
+ * the same category and they are all wide glyph. This will reduce search
+ * time and table size. The merge will omit the reserved code.
+ *
+ * Remove the above item if below is un-commented.
+ *
+ {(CHAR16)0x303F, 2}, // CJK symbols and punctuation. 0x3000-0x303F
+ {(CHAR16)0x309F, 2}, // Hiragana. 0x3040-0x309F
+ {(CHAR16)0x30FF, 2}, // Katakana. 0x30A0-0x30FF
+ {(CHAR16)0x312F, 2}, // Bopomofo. 0x3100-0x312F
+ {(CHAR16)0x318F, 2}, // Hangul compatibility jamo. 0x3130-0x318F
+ {(CHAR16)0x319F, 2}, // Kanbun. 0x3190-0x319F
+ {(CHAR16)0x31FF, 0}, // Reserved. As Bopomofo extended in ver3.0. 0x31A0-0x31FF
+ {(CHAR16)0x32FF, 2}, // Enclosed CJK letters and months. 0x3200-0x32FF
+ {(CHAR16)0x33FF, 2}, // CJK compatibility. 0x3300-0x33FF
+ *
+ */
+
+ //
+ // CJK ideograph area
+ //
+ {(CHAR16)0x9FFF, 2},
+ /*
+ * Merge the blocks and replace them with the above entry as they fall to
+ * the same category and they are all wide glyph. This will reduce search
+ * time and table size. The merge will omit the reserved code.
+ *
+ * Remove the above item if below is un-commented.
+ *
+ {(CHAR16)0x4DFF, 0}, // Reserved. 0x3400-0x4DBF as CJK unified ideographs
+ // extension A in ver3.0. 0x3400-0x4DFF
+ {(CHAR16)0x9FFF, 2}, // CJK unified ideographs. 0x4E00-0x9FFF
+ *
+ */
+
+ //
+ // Reserved
+ //
+ {(CHAR16)0xABFF, 0}, // Reserved. 0xA000-0xA490 as Yi syllables. 0xA490-0xA4D0
+ // as Yi radicals in ver3.0. 0xA000-0xABFF
+ //
+ // Hangul syllables
+ //
+ {(CHAR16)0xD7FF, 2},
+ /*
+ * Merge the blocks and replace them with the above entry as they fall to
+ * the same category and they are all wide glyph. This will reduce search
+ * time and table size. The merge will omit the reserved code.
+ *
+ * Remove the above item if below is un-commented.
+ *
+ {(CHAR16)0xD7A3, 2}, // Hangul syllables. 0xAC00-0xD7A3
+ {(CHAR16)0xD7FF, 0}, // Reserved. 0xD7A3-0xD7FF
+ *
+ */
+
+ //
+ // Surrogates area
+ //
+ {(CHAR16)0xDFFF, 0}, // Surrogates, not used now. 0xD800-0xDFFF
+
+ //
+ // Private use area
+ //
+ {(CHAR16)0xF8FF, 0}, // Private use area. 0xE000-0xF8FF
+
+ //
+ // Compatibility area and specials
+ //
+ {(CHAR16)0xFAFF, 2}, // CJK compatibility ideographs. 0xF900-0xFAFF
+ {(CHAR16)0xFB4F, 1}, // Alphabetic presentation forms. 0xFB00-0xFB4F
+ {(CHAR16)0xFDFF, 1}, // Arabic presentation forms-A. 0xFB50-0xFDFF
+ {(CHAR16)0xFE1F, 0}, // Reserved. As variation selectors in ver3.0. 0xFE00-0xFE1F
+ {(CHAR16)0xFE2F, 1}, // Combining half marks. 0xFE20-0xFE2F
+ {(CHAR16)0xFE4F, 2}, // CJK compatibility forms. 0xFE30-0xFE4F
+ {(CHAR16)0xFE6F, 1}, // Small Form Variants. 0xFE50-0xFE6F
+ {(CHAR16)0xFEFF, 1}, // Arabic presentation forms-B. 0xFE70-0xFEFF
+ {(CHAR16)0xFFEF, 1}, // Half width and full width forms. 0xFF00-0xFFEF
+ {(CHAR16)0xFFFF, 0}, // Speicials. 0xFFF0-0xFFFF
+};
+
+/**
+ Retrieves the width of a Unicode character.
+
+ This function computes and returns the width of the Unicode character specified
+ by UnicodeChar.
+
+ @param UnicodeChar A Unicode character.
+
+ @retval 0 The width if UnicodeChar could not be determined.
+ @retval 1 UnicodeChar is a narrow glyph.
+ @retval 2 UnicodeChar is a wide glyph.
+
+**/
+UINTN
+EFIAPI
+GetGlyphWidth (
+ IN CHAR16 UnicodeChar
+ )
+{
+ UINTN Index;
+ UINTN Low;
+ UINTN High;
+ CONST UNICODE_WIDTH_ENTRY *Item;
+
+ Item = NULL;
+ Low = 0;
+ High = (sizeof (mUnicodeWidthTable)) / (sizeof (UNICODE_WIDTH_ENTRY)) - 1;
+ while (Low <= High) {
+ Index = (Low + High) >> 1;
+ Item = &(mUnicodeWidthTable[Index]);
+ if (Index == 0) {
+ if (UnicodeChar <= Item->WChar) {
+ break;
+ }
+
+ return 0;
+ }
+
+ if (UnicodeChar > Item->WChar) {
+ Low = Index + 1;
+ } else if (UnicodeChar <= mUnicodeWidthTable[Index - 1].WChar) {
+ High = Index - 1;
+ } else {
+ //
+ // Index - 1 < UnicodeChar <= Index. Found
+ //
+ break;
+ }
+ }
+
+ if (Low <= High) {
+ return Item->Width;
+ }
+
+ return 0;
+}
+
+/**
+ Computes the display length of a Null-terminated Unicode String.
+
+ This function computes and returns the display length of the Null-terminated
+ Unicode string specified by String. If String is NULL then 0 is returned. If
+ any of the widths of the Unicode characters in String can not be determined,
+ then 0 is returned. The display width of String can be computed by summing the
+ display widths of each Unicode character in String. Unicode characters that
+ are narrow glyphs have a width of 1, and Unicode characters that are width glyphs
+ have a width of 2. If String is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param String A pointer to a Null-terminated Unicode string.
+
+ @return The display length of the Null-terminated Unicode string specified by String.
+
+**/
+UINTN
+EFIAPI
+UnicodeStringDisplayLength (
+ IN CONST CHAR16 *String
+ )
+{
+ UINTN Length;
+ UINTN Width;
+
+ if (String == NULL) {
+ return 0;
+ }
+
+ Length = 0;
+ while (*String != 0) {
+ Width = GetGlyphWidth (*String);
+ if (Width == 0) {
+ return 0;
+ }
+
+ Length += Width;
+ String++;
+ }
+
+ return Length;
+}
+
+/**
+ Count the storage space of a Unicode string.
+
+ This function handles the Unicode string with NARROW_CHAR
+ and WIDE_CHAR control characters. NARROW_HCAR and WIDE_CHAR
+ does not count in the resultant output. If a WIDE_CHAR is
+ hit, then 2 Unicode character will consume an output storage
+ space with size of CHAR16 till a NARROW_CHAR is hit.
+
+ @param String The input string to be counted.
+ @param LimitLen Whether need to limit the string length.
+ @param MaxWidth The max length this function supported.
+ @param Offset The max index of the string can be show out.
+
+ @return Storage space for the input string.
+
+**/
+UINTN
+UefiLibGetStringWidth (
+ IN CHAR16 *String,
+ IN BOOLEAN LimitLen,
+ IN UINTN MaxWidth,
+ OUT UINTN *Offset
+ )
+{
+ UINTN Index;
+ UINTN Count;
+ UINTN IncrementValue;
+
+ if (String == NULL) {
+ return 0;
+ }
+
+ Index = 0;
+ Count = 0;
+ IncrementValue = 1;
+
+ do {
+ //
+ // Advance to the null-terminator or to the first width directive
+ //
+ for (;(String[Index] != NARROW_CHAR) && (String[Index] != WIDE_CHAR) && (String[Index] != 0); Index++) {
+ Count = Count + IncrementValue;
+
+ if (LimitLen && Count > MaxWidth) {
+ break;
+ }
+ }
+
+ //
+ // We hit the null-terminator, we now have a count
+ //
+ if (String[Index] == 0) {
+ break;
+ }
+
+ if (LimitLen && Count > MaxWidth) {
+ *Offset = Index;
+ break;
+ }
+
+ //
+ // We encountered a narrow directive - strip it from the size calculation since it doesn't get printed
+ // and also set the flag that determines what we increment by.(if narrow, increment by 1, if wide increment by 2)
+ //
+ if (String[Index] == NARROW_CHAR) {
+ //
+ // Skip to the next character
+ //
+ Index++;
+ IncrementValue = 1;
+ } else {
+ //
+ // Skip to the next character
+ //
+ Index++;
+ IncrementValue = 2;
+ }
+ } while (String[Index] != 0);
+
+ return Count * sizeof (CHAR16);
+}
+
+/**
+ Draws a dialog box to the console output device specified by
+ ConOut defined in the EFI_SYSTEM_TABLE and waits for a keystroke
+ from the console input device specified by ConIn defined in the
+ EFI_SYSTEM_TABLE.
+
+ If there are no strings in the variable argument list, then ASSERT().
+ If all the strings in the variable argument list are empty, then ASSERT().
+
+ @param[in] Attribute Specifies the foreground and background color of the popup.
+ @param[out] Key A pointer to the EFI_KEY value of the key that was
+ pressed. This is an optional parameter that may be NULL.
+ If it is NULL then no wait for a keypress will be performed.
+ @param[in] ... The variable argument list that contains pointers to Null-
+ terminated Unicode strings to display in the dialog box.
+ The variable argument list is terminated by a NULL.
+
+**/
+VOID
+EFIAPI
+CreatePopUp (
+ IN UINTN Attribute,
+ OUT EFI_INPUT_KEY *Key, OPTIONAL
+ ...
+ )
+{
+ EFI_STATUS Status;
+ VA_LIST Args;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_MODE SavedConsoleMode;
+ UINTN Columns;
+ UINTN Rows;
+ UINTN Column;
+ UINTN Row;
+ UINTN NumberOfLines;
+ UINTN MaxLength;
+ CHAR16 *String;
+ UINTN Length;
+ CHAR16 *Line;
+ UINTN EventIndex;
+ CHAR16 *TmpString;
+
+ //
+ // Determine the length of the longest line in the popup and the the total
+ // number of lines in the popup
+ //
+ VA_START (Args, Key);
+ MaxLength = 0;
+ NumberOfLines = 0;
+ while ((String = VA_ARG (Args, CHAR16 *)) != NULL) {
+ MaxLength = MAX (MaxLength, UefiLibGetStringWidth (String, FALSE, 0, NULL) / 2);
+ NumberOfLines++;
+ }
+ VA_END (Args);
+
+ //
+ // If the total number of lines in the popup is zero, then ASSERT()
+ //
+ ASSERT (NumberOfLines != 0);
+
+ //
+ // If the maximum length of all the strings is zero, then ASSERT()
+ //
+ ASSERT (MaxLength != 0);
+
+ //
+ // Cache a pointer to the Simple Text Output Protocol in the EFI System Table
+ //
+ ConOut = gST->ConOut;
+
+ //
+ // Save the current console cursor position and attributes
+ //
+ CopyMem (&SavedConsoleMode, ConOut->Mode, sizeof (SavedConsoleMode));
+
+ //
+ // Retrieve the number of columns and rows in the current console mode
+ //
+ ConOut->QueryMode (ConOut, SavedConsoleMode.Mode, &Columns, &Rows);
+
+ //
+ // Disable cursor and set the foreground and background colors specified by Attribute
+ //
+ ConOut->EnableCursor (ConOut, FALSE);
+ ConOut->SetAttribute (ConOut, Attribute);
+
+ //
+ // Limit NumberOfLines to height of the screen minus 3 rows for the box itself
+ //
+ NumberOfLines = MIN (NumberOfLines, Rows - 3);
+
+ //
+ // Limit MaxLength to width of the screen minus 2 columns for the box itself
+ //
+ MaxLength = MIN (MaxLength, Columns - 2);
+
+ //
+ // Compute the starting row and starting column for the popup
+ //
+ Row = (Rows - (NumberOfLines + 3)) / 2;
+ Column = (Columns - (MaxLength + 2)) / 2;
+
+ //
+ // Allocate a buffer for a single line of the popup with borders and a Null-terminator
+ //
+ Line = AllocateZeroPool ((MaxLength + 3) * sizeof (CHAR16));
+ ASSERT (Line != NULL);
+
+ //
+ // Draw top of popup box
+ //
+ SetMem16 (Line, (MaxLength + 2) * 2, BOXDRAW_HORIZONTAL);
+ Line[0] = BOXDRAW_DOWN_RIGHT;
+ Line[MaxLength + 1] = BOXDRAW_DOWN_LEFT;
+ Line[MaxLength + 2] = L'\0';
+ ConOut->SetCursorPosition (ConOut, Column, Row++);
+ ConOut->OutputString (ConOut, Line);
+
+ //
+ // Draw middle of the popup with strings
+ //
+ VA_START (Args, Key);
+ while ((String = VA_ARG (Args, CHAR16 *)) != NULL && NumberOfLines > 0) {
+ SetMem16 (Line, (MaxLength + 2) * 2, L' ');
+ Line[0] = BOXDRAW_VERTICAL;
+ Line[MaxLength + 1] = BOXDRAW_VERTICAL;
+ Line[MaxLength + 2] = L'\0';
+ ConOut->SetCursorPosition (ConOut, Column, Row);
+ ConOut->OutputString (ConOut, Line);
+ Length = UefiLibGetStringWidth (String, FALSE, 0, NULL) / 2;
+ if (Length <= MaxLength) {
+ //
+ // Length <= MaxLength
+ //
+ ConOut->SetCursorPosition (ConOut, Column + 1 + (MaxLength - Length) / 2, Row++);
+ ConOut->OutputString (ConOut, String);
+ } else {
+ //
+ // Length > MaxLength
+ //
+ UefiLibGetStringWidth (String, TRUE, MaxLength, &Length);
+ TmpString = AllocateZeroPool ((Length + 1) * sizeof (CHAR16));
+ ASSERT (TmpString != NULL);
+ StrnCpyS (TmpString, Length + 1, String, Length - 3);
+ StrCatS (TmpString, Length + 1, L"...");
+
+ ConOut->SetCursorPosition (ConOut, Column + 1, Row++);
+ ConOut->OutputString (ConOut, TmpString);
+ FreePool (TmpString);
+ }
+ NumberOfLines--;
+ }
+ VA_END (Args);
+
+ //
+ // Draw bottom of popup box
+ //
+ SetMem16 (Line, (MaxLength + 2) * 2, BOXDRAW_HORIZONTAL);
+ Line[0] = BOXDRAW_UP_RIGHT;
+ Line[MaxLength + 1] = BOXDRAW_UP_LEFT;
+ Line[MaxLength + 2] = L'\0';
+ ConOut->SetCursorPosition (ConOut, Column, Row++);
+ ConOut->OutputString (ConOut, Line);
+
+ //
+ // Free the allocated line buffer
+ //
+ FreePool (Line);
+
+ //
+ // Restore the cursor visibility, position, and attributes
+ //
+ ConOut->EnableCursor (ConOut, SavedConsoleMode.CursorVisible);
+ ConOut->SetCursorPosition (ConOut, SavedConsoleMode.CursorColumn, SavedConsoleMode.CursorRow);
+ ConOut->SetAttribute (ConOut, SavedConsoleMode.Attribute);
+
+ //
+ // Wait for a keystroke
+ //
+ if (Key != NULL) {
+ while (TRUE) {
+ Status = gST->ConIn->ReadKeyStroke (gST->ConIn, Key);
+ if (!EFI_ERROR (Status)) {
+ break;
+ }
+
+ //
+ // If we encounter error, continue to read another key in.
+ //
+ if (Status != EFI_NOT_READY) {
+ continue;
+ }
+ gBS->WaitForEvent (1, &gST->ConIn->WaitForKey, &EventIndex);
+ }
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiDriverModel.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiDriverModel.c
new file mode 100644
index 0000000..391a913
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiDriverModel.c
@@ -0,0 +1,2021 @@
+/** @file
+ Library functions that abstract driver model protocols
+ installation and uninstallation.
+
+ Copyright (c) 2019, NVIDIA Corporation. All rights reserved.
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "UefiLibInternal.h"
+#include "Efi_Defs.h"
+
+/**
+ Installs and completes the initialization of a Driver Binding Protocol instance.
+
+ Installs the Driver Binding Protocol specified by DriverBinding onto the handle
+ specified by DriverBindingHandle. If DriverBindingHandle is NULL, then DriverBinding
+ is installed onto a newly created handle. DriverBindingHandle is typically the same
+ as the driver's ImageHandle, but it can be different if the driver produces multiple
+ Driver Binding Protocols.
+ If DriverBinding is NULL, then ASSERT().
+ If DriverBinding can not be installed onto a handle, then ASSERT().
+
+ @param ImageHandle The image handle of the driver.
+ @param SystemTable The EFI System Table that was passed to the driver's entry point.
+ @param DriverBinding A Driver Binding Protocol instance that this driver is producing.
+ @param DriverBindingHandle The handle that DriverBinding is to be installed onto. If this
+ parameter is NULL, then a new handle is created.
+
+ @retval EFI_SUCCESS The protocol installation successfully completed.
+ @retval EFI_OUT_OF_RESOURCES There was not enough system resources to install the protocol.
+ @retval Others Status from gBS->InstallMultipleProtocolInterfaces().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibInstallDriverBinding (
+ IN CONST EFI_HANDLE ImageHandle,
+ IN CONST EFI_SYSTEM_TABLE *SystemTable,
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN EFI_HANDLE DriverBindingHandle
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ //
+ // Update the ImageHandle and DriverBindingHandle fields of the Driver Binding Protocol
+ //
+ DriverBinding->ImageHandle = ImageHandle;
+ DriverBinding->DriverBindingHandle = DriverBindingHandle;
+
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ //
+ // ASSERT if the call to InstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Uninstalls a Driver Binding Protocol instance.
+
+ If DriverBinding is NULL, then ASSERT().
+ If DriverBinding can not be uninstalled, then ASSERT().
+
+ @param DriverBinding A Driver Binding Protocol instance that this driver produced.
+
+ @retval EFI_SUCCESS The protocol uninstallation successfully completed.
+ @retval Others Status from gBS->UninstallMultipleProtocolInterfaces().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibUninstallDriverBinding (
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ //
+ // ASSERT if the call to UninstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Installs and completes the initialization of a Driver Binding Protocol instance and
+ optionally installs the Component Name, Driver Configuration and Driver Diagnostics Protocols.
+
+ Initializes a driver by installing the Driver Binding Protocol together with the
+ optional Component Name, optional Driver Configure and optional Driver Diagnostic
+ Protocols onto the driver's DriverBindingHandle. If DriverBindingHandle is NULL,
+ then the protocols are installed onto a newly created handle. DriverBindingHandle
+ is typically the same as the driver's ImageHandle, but it can be different if the
+ driver produces multiple Driver Binding Protocols.
+ If DriverBinding is NULL, then ASSERT().
+ If the installation fails, then ASSERT().
+
+ @param ImageHandle The image handle of the driver.
+ @param SystemTable The EFI System Table that was passed to the driver's entry point.
+ @param DriverBinding A Driver Binding Protocol instance that this driver is producing.
+ @param DriverBindingHandle The handle that DriverBinding is to be installed onto. If this
+ parameter is NULL, then a new handle is created.
+ @param ComponentName A Component Name Protocol instance that this driver is producing.
+ @param DriverConfiguration A Driver Configuration Protocol instance that this driver is producing.
+ @param DriverDiagnostics A Driver Diagnostics Protocol instance that this driver is producing.
+
+ @retval EFI_SUCCESS The protocol installation successfully completed.
+ @retval EFI_OUT_OF_RESOURCES There was not enough memory in pool to install all the protocols.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibInstallAllDriverProtocols (
+ IN CONST EFI_HANDLE ImageHandle,
+ IN CONST EFI_SYSTEM_TABLE *SystemTable,
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN EFI_HANDLE DriverBindingHandle,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION_PROTOCOL *DriverConfiguration, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS_PROTOCOL *DriverDiagnostics OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ //
+ // Update the ImageHandle and DriverBindingHandle fields of the Driver Binding Protocol
+ //
+ DriverBinding->ImageHandle = ImageHandle;
+ DriverBinding->DriverBindingHandle = DriverBindingHandle;
+
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverConfiguration == NULL) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (DriverConfiguration == NULL) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ }
+
+ //
+ // ASSERT if the call to InstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Uninstalls a Driver Binding Protocol instance and optionally uninstalls the
+ Component Name, Driver Configuration and Driver Diagnostics Protocols.
+
+ If DriverBinding is NULL, then ASSERT().
+ If the uninstallation fails, then ASSERT().
+
+ @param DriverBinding A Driver Binding Protocol instance that this driver produced.
+ @param ComponentName A Component Name Protocol instance that this driver produced.
+ @param DriverConfiguration A Driver Configuration Protocol instance that this driver produced.
+ @param DriverDiagnostics A Driver Diagnostics Protocol instance that this driver produced.
+
+ @retval EFI_SUCCESS The protocol uninstallation successfully completed.
+ @retval Others Status from gBS->UninstallMultipleProtocolInterfaces().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibUninstallAllDriverProtocols (
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION_PROTOCOL *DriverConfiguration, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS_PROTOCOL *DriverDiagnostics OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverConfiguration == NULL) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (DriverConfiguration == NULL) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ }
+
+ //
+ // ASSERT if the call to UninstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Installs Driver Binding Protocol with optional Component Name and Component Name 2 Protocols.
+
+ Initializes a driver by installing the Driver Binding Protocol together with the
+ optional Component Name and optional Component Name 2 protocols onto the driver's
+ DriverBindingHandle. If DriverBindingHandle is NULL, then the protocols are installed
+ onto a newly created handle. DriverBindingHandle is typically the same as the driver's
+ ImageHandle, but it can be different if the driver produces multiple Driver Binding Protocols.
+ If DriverBinding is NULL, then ASSERT().
+ If the installation fails, then ASSERT().
+
+ @param ImageHandle The image handle of the driver.
+ @param SystemTable The EFI System Table that was passed to the driver's entry point.
+ @param DriverBinding A Driver Binding Protocol instance that this driver is producing.
+ @param DriverBindingHandle The handle that DriverBinding is to be installed onto. If this
+ parameter is NULL, then a new handle is created.
+ @param ComponentName A Component Name Protocol instance that this driver is producing.
+ @param ComponentName2 A Component Name 2 Protocol instance that this driver is producing.
+
+ @retval EFI_SUCCESS The protocol installation successfully completed.
+ @retval EFI_OUT_OF_RESOURCES There was not enough memory in pool to install all the protocols.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibInstallDriverBindingComponentName2 (
+ IN CONST EFI_HANDLE ImageHandle,
+ IN CONST EFI_SYSTEM_TABLE *SystemTable,
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN EFI_HANDLE DriverBindingHandle,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_COMPONENT_NAME2_PROTOCOL *ComponentName2 OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ //
+ // Update the ImageHandle and DriverBindingHandle fields of the Driver Binding Protocol
+ //
+ DriverBinding->ImageHandle = ImageHandle;
+ DriverBinding->DriverBindingHandle = DriverBindingHandle;
+
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ }
+
+ //
+ // ASSERT if the call to InstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Uninstalls Driver Binding Protocol with optional Component Name and Component Name 2 Protocols.
+
+ If DriverBinding is NULL, then ASSERT().
+ If the uninstallation fails, then ASSERT().
+
+ @param DriverBinding A Driver Binding Protocol instance that this driver produced.
+ @param ComponentName A Component Name Protocol instance that this driver produced.
+ @param ComponentName2 A Component Name 2 Protocol instance that this driver produced.
+
+ @retval EFI_SUCCESS The protocol installation successfully completed.
+ @retval Others Status from gBS->UninstallMultipleProtocolInterfaces().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibUninstallDriverBindingComponentName2 (
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_COMPONENT_NAME2_PROTOCOL *ComponentName2 OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ }
+
+ //
+ // ASSERT if the call to UninstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Installs Driver Binding Protocol with optional Component Name, Component Name 2, Driver
+ Configuration, Driver Configuration 2, Driver Diagnostics, and Driver Diagnostics 2 Protocols.
+
+ Initializes a driver by installing the Driver Binding Protocol together with the optional
+ Component Name, optional Component Name 2, optional Driver Configuration, optional Driver Configuration 2,
+ optional Driver Diagnostic, and optional Driver Diagnostic 2 Protocols onto the driver's DriverBindingHandle.
+ DriverBindingHandle is typically the same as the driver's ImageHandle, but it can be different if the driver
+ produces multiple Driver Binding Protocols.
+ If DriverBinding is NULL, then ASSERT().
+ If the installation fails, then ASSERT().
+
+
+ @param ImageHandle The image handle of the driver.
+ @param SystemTable The EFI System Table that was passed to the driver's entry point.
+ @param DriverBinding A Driver Binding Protocol instance that this driver is producing.
+ @param DriverBindingHandle The handle that DriverBinding is to be installed onto. If this
+ parameter is NULL, then a new handle is created.
+ @param ComponentName A Component Name Protocol instance that this driver is producing.
+ @param ComponentName2 A Component Name 2 Protocol instance that this driver is producing.
+ @param DriverConfiguration A Driver Configuration Protocol instance that this driver is producing.
+ @param DriverConfiguration2 A Driver Configuration Protocol 2 instance that this driver is producing.
+ @param DriverDiagnostics A Driver Diagnostics Protocol instance that this driver is producing.
+ @param DriverDiagnostics2 A Driver Diagnostics Protocol 2 instance that this driver is producing.
+
+ @retval EFI_SUCCESS The protocol installation successfully completed.
+ @retval EFI_OUT_OF_RESOURCES There was not enough memory in pool to install all the protocols.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibInstallAllDriverProtocols2 (
+ IN CONST EFI_HANDLE ImageHandle,
+ IN CONST EFI_SYSTEM_TABLE *SystemTable,
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN EFI_HANDLE DriverBindingHandle,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_COMPONENT_NAME2_PROTOCOL *ComponentName2, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION_PROTOCOL *DriverConfiguration, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION2_PROTOCOL *DriverConfiguration2, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS_PROTOCOL *DriverDiagnostics, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS2_PROTOCOL *DriverDiagnostics2 OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ //
+ // Update the ImageHandle and DriverBindingHandle fields of the Driver Binding Protocol
+ //
+ DriverBinding->ImageHandle = ImageHandle;
+ DriverBinding->DriverBindingHandle = DriverBindingHandle;
+
+ if (DriverConfiguration2 == NULL) {
+ if (DriverConfiguration == NULL) {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverConfiguration == NULL) {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ }
+ }
+
+ //
+ // ASSERT if the call to InstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+
+
+/**
+ Uninstalls Driver Binding Protocol with optional Component Name, Component Name 2, Driver
+ Configuration, Driver Configuration 2, Driver Diagnostics, and Driver Diagnostics 2 Protocols.
+
+ If DriverBinding is NULL, then ASSERT().
+ If the installation fails, then ASSERT().
+
+
+ @param DriverBinding A Driver Binding Protocol instance that this driver produced.
+ @param ComponentName A Component Name Protocol instance that this driver produced.
+ @param ComponentName2 A Component Name 2 Protocol instance that this driver produced.
+ @param DriverConfiguration A Driver Configuration Protocol instance that this driver produced.
+ @param DriverConfiguration2 A Driver Configuration Protocol 2 instance that this driver produced.
+ @param DriverDiagnostics A Driver Diagnostics Protocol instance that this driver produced.
+ @param DriverDiagnostics2 A Driver Diagnostics Protocol 2 instance that this driver produced.
+
+ @retval EFI_SUCCESS The protocol uninstallation successfully completed.
+ @retval Others Status from gBS->UninstallMultipleProtocolInterfaces().
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLibUninstallAllDriverProtocols2 (
+ IN EFI_DRIVER_BINDING_PROTOCOL *DriverBinding,
+ IN CONST EFI_COMPONENT_NAME_PROTOCOL *ComponentName, OPTIONAL
+ IN CONST EFI_COMPONENT_NAME2_PROTOCOL *ComponentName2, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION_PROTOCOL *DriverConfiguration, OPTIONAL
+ IN CONST EFI_DRIVER_CONFIGURATION2_PROTOCOL *DriverConfiguration2, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS_PROTOCOL *DriverDiagnostics, OPTIONAL
+ IN CONST EFI_DRIVER_DIAGNOSTICS2_PROTOCOL *DriverDiagnostics2 OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ ASSERT (DriverBinding != NULL);
+
+ if (DriverConfiguration2 == NULL) {
+ if (DriverConfiguration == NULL) {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverConfiguration == NULL) {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics == NULL || FeaturePcdGet(PcdDriverDiagnosticsDisable)) {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ } else {
+ if (DriverDiagnostics2 == NULL || FeaturePcdGet(PcdDriverDiagnostics2Disable)) {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ NULL
+ );
+ }
+ }
+ } else {
+ if (ComponentName == NULL || FeaturePcdGet(PcdComponentNameDisable)) {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ } else {
+ if (ComponentName2 == NULL || FeaturePcdGet(PcdComponentName2Disable)) {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ } else {
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ DriverBinding->DriverBindingHandle,
+ &gEfiDriverBindingProtocolGuid, DriverBinding,
+ &gEfiComponentNameProtocolGuid, ComponentName,
+ &gEfiComponentName2ProtocolGuid, ComponentName2,
+ &gEfiDriverConfigurationProtocolGuid, DriverConfiguration,
+ &gEfiDriverConfiguration2ProtocolGuid, DriverConfiguration2,
+ &gEfiDriverDiagnosticsProtocolGuid, DriverDiagnostics,
+ &gEfiDriverDiagnostics2ProtocolGuid, DriverDiagnostics2,
+ NULL
+ );
+ }
+ }
+ }
+ }
+ }
+ }
+
+ //
+ // ASSERT if the call to UninstallMultipleProtocolInterfaces() failed
+ //
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLib.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLib.c
new file mode 100644
index 0000000..b6a33a0
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLib.c
@@ -0,0 +1,1921 @@
+/** @file
+ The UEFI Library provides functions and macros that simplify the development of
+ UEFI Drivers and UEFI Applications. These functions and macros help manage EFI
+ events, build simple locks utilizing EFI Task Priority Levels (TPLs), install
+ EFI Driver Model related protocols, manage Unicode string tables for UEFI Drivers,
+ and print messages on the console output and standard error devices.
+
+ Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "UefiLibInternal.h"
+
+/**
+ Empty constructor function that is required to resolve dependencies between
+ libraries.
+
+ ** DO NOT REMOVE **
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The constructor executed correctly.
+
+**/
+EFI_STATUS
+EFIAPI
+UefiLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ return EFI_SUCCESS;
+}
+
+/**
+ Compare whether two names of languages are identical.
+
+ @param Language1 Name of language 1.
+ @param Language2 Name of language 2.
+
+ @retval TRUE Language 1 and language 2 are the same.
+ @retval FALSE Language 1 and language 2 are not the same.
+
+**/
+BOOLEAN
+CompareIso639LanguageCode (
+ IN CONST CHAR8 *Language1,
+ IN CONST CHAR8 *Language2
+ )
+{
+ UINT32 Name1;
+ UINT32 Name2;
+
+ Name1 = ReadUnaligned24 ((CONST UINT32 *) Language1);
+ Name2 = ReadUnaligned24 ((CONST UINT32 *) Language2);
+
+ return (BOOLEAN) (Name1 == Name2);
+}
+
+/**
+ Retrieves a pointer to the system configuration table from the EFI System Table
+ based on a specified GUID.
+
+ This function searches the list of configuration tables stored in the EFI System Table
+ for a table with a GUID that matches TableGuid. If a match is found, then a pointer to
+ the configuration table is returned in Table., and EFI_SUCCESS is returned. If a matching GUID
+ is not found, then EFI_NOT_FOUND is returned.
+ If TableGuid is NULL, then ASSERT().
+ If Table is NULL, then ASSERT().
+
+ @param TableGuid The pointer to table's GUID type.
+ @param Table The pointer to the table associated with TableGuid in the EFI System Table.
+
+ @retval EFI_SUCCESS A configuration table matching TableGuid was found.
+ @retval EFI_NOT_FOUND A configuration table matching TableGuid could not be found.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiGetSystemConfigurationTable (
+ IN EFI_GUID *TableGuid,
+ OUT VOID **Table
+ )
+{
+ EFI_SYSTEM_TABLE *SystemTable;
+ UINTN Index;
+
+ ASSERT (TableGuid != NULL);
+ ASSERT (Table != NULL);
+
+ SystemTable = gST;
+ *Table = NULL;
+ for (Index = 0; Index < SystemTable->NumberOfTableEntries; Index++) {
+ if (CompareGuid (TableGuid, &(SystemTable->ConfigurationTable[Index].VendorGuid))) {
+ *Table = SystemTable->ConfigurationTable[Index].VendorTable;
+ return EFI_SUCCESS;
+ }
+ }
+
+ return EFI_NOT_FOUND;
+}
+
+/**
+ Creates and returns a notification event and registers that event with all the protocol
+ instances specified by ProtocolGuid.
+
+ This function causes the notification function to be executed for every protocol of type
+ ProtocolGuid instance that exists in the system when this function is invoked. If there are
+ no instances of ProtocolGuid in the handle database at the time this function is invoked,
+ then the notification function is still executed one time. In addition, every time a protocol
+ of type ProtocolGuid instance is installed or reinstalled, the notification function is also
+ executed. This function returns the notification event that was created.
+ If ProtocolGuid is NULL, then ASSERT().
+ If NotifyTpl is not a legal TPL value, then ASSERT().
+ If NotifyFunction is NULL, then ASSERT().
+ If Registration is NULL, then ASSERT().
+
+
+ @param ProtocolGuid Supplies GUID of the protocol upon whose installation the event is fired.
+ @param NotifyTpl Supplies the task priority level of the event notifications.
+ @param NotifyFunction Supplies the function to notify when the event is signaled.
+ @param NotifyContext The context parameter to pass to NotifyFunction.
+ @param Registration A pointer to a memory location to receive the registration value.
+ This value is passed to LocateHandle() to obtain new handles that
+ have been added that support the ProtocolGuid-specified protocol.
+
+ @return The notification event that was created.
+
+**/
+EFI_EVENT
+EFIAPI
+EfiCreateProtocolNotifyEvent(
+ IN EFI_GUID *ProtocolGuid,
+ IN EFI_TPL NotifyTpl,
+ IN EFI_EVENT_NOTIFY NotifyFunction,
+ IN VOID *NotifyContext, OPTIONAL
+ OUT VOID **Registration
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT Event;
+
+ ASSERT (ProtocolGuid != NULL);
+ ASSERT (NotifyFunction != NULL);
+ ASSERT (Registration != NULL);
+
+ //
+ // Create the event
+ //
+
+ Status = gBS->CreateEvent (
+ EVT_NOTIFY_SIGNAL,
+ NotifyTpl,
+ NotifyFunction,
+ NotifyContext,
+ &Event
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ //
+ // Register for protocol notifications on this event
+ //
+
+ Status = gBS->RegisterProtocolNotify (
+ ProtocolGuid,
+ Event,
+ Registration
+ );
+
+ ASSERT_EFI_ERROR (Status);
+
+ //
+ // Kick the event so we will perform an initial pass of
+ // current installed drivers
+ //
+
+ gBS->SignalEvent (Event);
+ return Event;
+}
+
+/**
+ Creates a named event that can be signaled with EfiNamedEventSignal().
+
+ This function creates an event using NotifyTpl, NoifyFunction, and NotifyContext.
+ This event is signaled with EfiNamedEventSignal(). This provides the ability for one or more
+ listeners on the same event named by the GUID specified by Name.
+ If Name is NULL, then ASSERT().
+ If NotifyTpl is not a legal TPL value, then ASSERT().
+ If NotifyFunction is NULL, then ASSERT().
+
+ @param Name Supplies the GUID name of the event.
+ @param NotifyTpl Supplies the task priority level of the event notifications.
+ @param NotifyFunction Supplies the function to notify when the event is signaled.
+ @param NotifyContext The context parameter to pass to NotifyFunction.
+ @param Registration A pointer to a memory location to receive the registration value.
+
+ @retval EFI_SUCCESS A named event was created.
+ @retval EFI_OUT_OF_RESOURCES There are not enough resource to create the named event.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiNamedEventListen (
+ IN CONST EFI_GUID *Name,
+ IN EFI_TPL NotifyTpl,
+ IN EFI_EVENT_NOTIFY NotifyFunction,
+ IN CONST VOID *NotifyContext, OPTIONAL
+ OUT VOID *Registration OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT Event;
+ VOID *RegistrationLocal;
+
+ ASSERT (Name != NULL);
+ ASSERT (NotifyFunction != NULL);
+ ASSERT (NotifyTpl <= TPL_HIGH_LEVEL);
+
+ //
+ // Create event
+ //
+ Status = gBS->CreateEvent (
+ EVT_NOTIFY_SIGNAL,
+ NotifyTpl,
+ NotifyFunction,
+ (VOID *) NotifyContext,
+ &Event
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ //
+ // The Registration is not optional to RegisterProtocolNotify().
+ // To make it optional to EfiNamedEventListen(), may need to substitute with a local.
+ //
+ if (Registration != NULL) {
+ RegistrationLocal = Registration;
+ } else {
+ RegistrationLocal = &RegistrationLocal;
+ }
+
+ //
+ // Register for an installation of protocol interface
+ //
+
+ Status = gBS->RegisterProtocolNotify (
+ (EFI_GUID *) Name,
+ Event,
+ RegistrationLocal
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+/**
+ Signals a named event created with EfiNamedEventListen().
+
+ This function signals the named event specified by Name. The named event must have been
+ created with EfiNamedEventListen().
+ If Name is NULL, then ASSERT().
+
+ @param Name Supplies the GUID name of the event.
+
+ @retval EFI_SUCCESS A named event was signaled.
+ @retval EFI_OUT_OF_RESOURCES There are not enough resource to signal the named event.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiNamedEventSignal (
+ IN CONST EFI_GUID *Name
+ )
+{
+ EFI_STATUS Status;
+ EFI_HANDLE Handle;
+
+ ASSERT(Name != NULL);
+
+ Handle = NULL;
+ Status = gBS->InstallProtocolInterface (
+ &Handle,
+ (EFI_GUID *) Name,
+ EFI_NATIVE_INTERFACE,
+ NULL
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ Status = gBS->UninstallProtocolInterface (
+ Handle,
+ (EFI_GUID *) Name,
+ NULL
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
+
+/**
+ Signals an event group by placing a new event in the group temporarily and
+ signaling it.
+
+ @param[in] EventGroup Supplies the unique identifier of the event
+ group to signal.
+
+ @retval EFI_SUCCESS The event group was signaled successfully.
+ @retval EFI_INVALID_PARAMETER EventGroup is NULL.
+ @return Error codes that report problems about event
+ creation or signaling.
+**/
+EFI_STATUS
+EFIAPI
+EfiEventGroupSignal (
+ IN CONST EFI_GUID *EventGroup
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT Event;
+
+ if (EventGroup == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Status = gBS->CreateEventEx (
+ EVT_NOTIFY_SIGNAL,
+ TPL_CALLBACK,
+ EfiEventEmptyFunction,
+ NULL,
+ EventGroup,
+ &Event
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = gBS->SignalEvent (Event);
+ gBS->CloseEvent (Event);
+
+ return Status;
+}
+
+/**
+ An empty function that can be used as NotifyFunction parameter of
+ CreateEvent() or CreateEventEx().
+
+ @param Event Event whose notification function is being invoked.
+ @param Context The pointer to the notification function's context,
+ which is implementation-dependent.
+
+**/
+VOID
+EFIAPI
+EfiEventEmptyFunction (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+}
+
+/**
+ Returns the current TPL.
+
+ This function returns the current TPL. There is no EFI service to directly
+ retrieve the current TPL. Instead, the RaiseTPL() function is used to raise
+ the TPL to TPL_HIGH_LEVEL. This will return the current TPL. The TPL level
+ can then immediately be restored back to the current TPL level with a call
+ to RestoreTPL().
+
+ @return The current TPL.
+
+**/
+EFI_TPL
+EFIAPI
+EfiGetCurrentTpl (
+ VOID
+ )
+{
+ EFI_TPL Tpl;
+
+ Tpl = gBS->RaiseTPL (TPL_HIGH_LEVEL);
+ gBS->RestoreTPL (Tpl);
+
+ return Tpl;
+}
+
+
+/**
+ Initializes a basic mutual exclusion lock.
+
+ This function initializes a basic mutual exclusion lock to the released state
+ and returns the lock. Each lock provides mutual exclusion access at its task
+ priority level. Since there is no preemption or multiprocessor support in EFI,
+ acquiring the lock only consists of raising to the locks TPL.
+ If Lock is NULL, then ASSERT().
+ If Priority is not a valid TPL value, then ASSERT().
+
+ @param Lock A pointer to the lock data structure to initialize.
+ @param Priority EFI TPL is associated with the lock.
+
+ @return The lock.
+
+**/
+EFI_LOCK *
+EFIAPI
+EfiInitializeLock (
+ IN OUT EFI_LOCK *Lock,
+ IN EFI_TPL Priority
+ )
+{
+ ASSERT (Lock != NULL);
+ ASSERT (Priority <= TPL_HIGH_LEVEL);
+
+ Lock->Tpl = Priority;
+ Lock->OwnerTpl = TPL_APPLICATION;
+ Lock->Lock = EfiLockReleased ;
+ return Lock;
+}
+
+/**
+ Acquires ownership of a lock.
+
+ This function raises the system's current task priority level to the task
+ priority level of the mutual exclusion lock. Then, it places the lock in the
+ acquired state.
+ If Lock is NULL, then ASSERT().
+ If Lock is not initialized, then ASSERT().
+ If Lock is already in the acquired state, then ASSERT().
+
+ @param Lock A pointer to the lock to acquire.
+
+**/
+VOID
+EFIAPI
+EfiAcquireLock (
+ IN EFI_LOCK *Lock
+ )
+{
+ ASSERT (Lock != NULL);
+ ASSERT (Lock->Lock == EfiLockReleased);
+
+ Lock->OwnerTpl = gBS->RaiseTPL (Lock->Tpl);
+ Lock->Lock = EfiLockAcquired;
+}
+
+/**
+ Acquires ownership of a lock.
+
+ This function raises the system's current task priority level to the task priority
+ level of the mutual exclusion lock. Then, it attempts to place the lock in the acquired state.
+ If the lock is already in the acquired state, then EFI_ACCESS_DENIED is returned.
+ Otherwise, EFI_SUCCESS is returned.
+ If Lock is NULL, then ASSERT().
+ If Lock is not initialized, then ASSERT().
+
+ @param Lock A pointer to the lock to acquire.
+
+ @retval EFI_SUCCESS The lock was acquired.
+ @retval EFI_ACCESS_DENIED The lock could not be acquired because it is already owned.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiAcquireLockOrFail (
+ IN EFI_LOCK *Lock
+ )
+{
+
+ ASSERT (Lock != NULL);
+ ASSERT (Lock->Lock != EfiLockUninitialized);
+
+ if (Lock->Lock == EfiLockAcquired) {
+ //
+ // Lock is already owned, so bail out
+ //
+ return EFI_ACCESS_DENIED;
+ }
+
+ Lock->OwnerTpl = gBS->RaiseTPL (Lock->Tpl);
+
+ Lock->Lock = EfiLockAcquired;
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Releases ownership of a lock.
+
+ This function transitions a mutual exclusion lock from the acquired state to
+ the released state, and restores the system's task priority level to its
+ previous level.
+ If Lock is NULL, then ASSERT().
+ If Lock is not initialized, then ASSERT().
+ If Lock is already in the released state, then ASSERT().
+
+ @param Lock A pointer to the lock to release.
+
+**/
+VOID
+EFIAPI
+EfiReleaseLock (
+ IN EFI_LOCK *Lock
+ )
+{
+ EFI_TPL Tpl;
+
+ ASSERT (Lock != NULL);
+ ASSERT (Lock->Lock == EfiLockAcquired);
+
+ Tpl = Lock->OwnerTpl;
+
+ Lock->Lock = EfiLockReleased;
+
+ gBS->RestoreTPL (Tpl);
+}
+
+/**
+ Tests whether a controller handle is being managed by a specific driver.
+
+ This function tests whether the driver specified by DriverBindingHandle is
+ currently managing the controller specified by ControllerHandle. This test
+ is performed by evaluating if the the protocol specified by ProtocolGuid is
+ present on ControllerHandle and is was opened by DriverBindingHandle with an
+ attribute of EFI_OPEN_PROTOCOL_BY_DRIVER.
+ If ProtocolGuid is NULL, then ASSERT().
+
+ @param ControllerHandle A handle for a controller to test.
+ @param DriverBindingHandle Specifies the driver binding handle for the
+ driver.
+ @param ProtocolGuid Specifies the protocol that the driver specified
+ by DriverBindingHandle opens in its Start()
+ function.
+
+ @retval EFI_SUCCESS ControllerHandle is managed by the driver
+ specified by DriverBindingHandle.
+ @retval EFI_UNSUPPORTED ControllerHandle is not managed by the driver
+ specified by DriverBindingHandle.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiTestManagedDevice (
+ IN CONST EFI_HANDLE ControllerHandle,
+ IN CONST EFI_HANDLE DriverBindingHandle,
+ IN CONST EFI_GUID *ProtocolGuid
+ )
+{
+ EFI_STATUS Status;
+ VOID *ManagedInterface;
+
+ ASSERT (ProtocolGuid != NULL);
+
+ Status = gBS->OpenProtocol (
+ ControllerHandle,
+ (EFI_GUID *) ProtocolGuid,
+ &ManagedInterface,
+ DriverBindingHandle,
+ ControllerHandle,
+ EFI_OPEN_PROTOCOL_BY_DRIVER
+ );
+ if (!EFI_ERROR (Status)) {
+ gBS->CloseProtocol (
+ ControllerHandle,
+ (EFI_GUID *) ProtocolGuid,
+ DriverBindingHandle,
+ ControllerHandle
+ );
+ return EFI_UNSUPPORTED;
+ }
+
+ if (Status != EFI_ALREADY_STARTED) {
+ return EFI_UNSUPPORTED;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Tests whether a child handle is a child device of the controller.
+
+ This function tests whether ChildHandle is one of the children of
+ ControllerHandle. This test is performed by checking to see if the protocol
+ specified by ProtocolGuid is present on ControllerHandle and opened by
+ ChildHandle with an attribute of EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER.
+ If ProtocolGuid is NULL, then ASSERT().
+
+ @param ControllerHandle A handle for a (parent) controller to test.
+ @param ChildHandle A child handle to test.
+ @param ProtocolGuid Supplies the protocol that the child controller
+ opens on its parent controller.
+
+ @retval EFI_SUCCESS ChildHandle is a child of the ControllerHandle.
+ @retval EFI_UNSUPPORTED ChildHandle is not a child of the
+ ControllerHandle.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiTestChildHandle (
+ IN CONST EFI_HANDLE ControllerHandle,
+ IN CONST EFI_HANDLE ChildHandle,
+ IN CONST EFI_GUID *ProtocolGuid
+ )
+{
+ EFI_STATUS Status;
+ EFI_OPEN_PROTOCOL_INFORMATION_ENTRY *OpenInfoBuffer;
+ UINTN EntryCount;
+ UINTN Index;
+
+ ASSERT (ProtocolGuid != NULL);
+
+ //
+ // Retrieve the list of agents that are consuming the specific protocol
+ // on ControllerHandle.
+ //
+ Status = gBS->OpenProtocolInformation (
+ ControllerHandle,
+ (EFI_GUID *) ProtocolGuid,
+ &OpenInfoBuffer,
+ &EntryCount
+ );
+ if (EFI_ERROR (Status)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // Inspect if ChildHandle is one of the agents.
+ //
+ Status = EFI_UNSUPPORTED;
+ for (Index = 0; Index < EntryCount; Index++) {
+ if ((OpenInfoBuffer[Index].ControllerHandle == ChildHandle) &&
+ (OpenInfoBuffer[Index].Attributes & EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER) != 0) {
+ Status = EFI_SUCCESS;
+ break;
+ }
+ }
+
+ FreePool (OpenInfoBuffer);
+ return Status;
+}
+
+/**
+ This function checks the supported languages list for a target language,
+ This only supports RFC 4646 Languages.
+
+ @param SupportedLanguages The supported languages
+ @param TargetLanguage The target language
+
+ @retval Returns EFI_SUCCESS if the language is supported,
+ EFI_UNSUPPORTED otherwise
+**/
+EFI_STATUS
+EFIAPI
+IsLanguageSupported (
+ IN CONST CHAR8 *SupportedLanguages,
+ IN CONST CHAR8 *TargetLanguage
+ )
+{
+ UINTN Index;
+ while (*SupportedLanguages != 0) {
+ for (Index = 0; SupportedLanguages[Index] != 0 && SupportedLanguages[Index] != ';'; Index++);
+ if ((AsciiStrnCmp(SupportedLanguages, TargetLanguage, Index) == 0) && (TargetLanguage[Index] == 0)) {
+ return EFI_SUCCESS;
+ }
+ SupportedLanguages += Index;
+ for (; *SupportedLanguages != 0 && *SupportedLanguages == ';'; SupportedLanguages++);
+ }
+
+ return EFI_UNSUPPORTED;
+}
+
+/**
+ This function looks up a Unicode string in UnicodeStringTable.
+
+ If Language is a member of SupportedLanguages and a Unicode string is found in
+ UnicodeStringTable that matches the language code specified by Language, then it
+ is returned in UnicodeString.
+
+ @param Language A pointer to the ISO 639-2 language code for the
+ Unicode string to look up and return.
+ @param SupportedLanguages A pointer to the set of ISO 639-2 language codes
+ that the Unicode string table supports. Language
+ must be a member of this set.
+ @param UnicodeStringTable A pointer to the table of Unicode strings.
+ @param UnicodeString A pointer to the Unicode string from UnicodeStringTable
+ that matches the language specified by Language.
+
+ @retval EFI_SUCCESS The Unicode string that matches the language
+ specified by Language was found
+ in the table of Unicode strings UnicodeStringTable,
+ and it was returned in UnicodeString.
+ @retval EFI_INVALID_PARAMETER Language is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is NULL.
+ @retval EFI_UNSUPPORTED SupportedLanguages is NULL.
+ @retval EFI_UNSUPPORTED UnicodeStringTable is NULL.
+ @retval EFI_UNSUPPORTED The language specified by Language is not a
+ member of SupportedLanguages.
+ @retval EFI_UNSUPPORTED The language specified by Language is not
+ supported by UnicodeStringTable.
+
+**/
+EFI_STATUS
+EFIAPI
+LookupUnicodeString (
+ IN CONST CHAR8 *Language,
+ IN CONST CHAR8 *SupportedLanguages,
+ IN CONST EFI_UNICODE_STRING_TABLE *UnicodeStringTable,
+ OUT CHAR16 **UnicodeString
+ )
+{
+ //
+ // Make sure the parameters are valid
+ //
+ if (Language == NULL || UnicodeString == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // If there are no supported languages, or the Unicode String Table is empty, then the
+ // Unicode String specified by Language is not supported by this Unicode String Table
+ //
+ if (SupportedLanguages == NULL || UnicodeStringTable == NULL) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // Make sure Language is in the set of Supported Languages
+ //
+ while (*SupportedLanguages != 0) {
+ if (CompareIso639LanguageCode (Language, SupportedLanguages)) {
+
+ //
+ // Search the Unicode String Table for the matching Language specifier
+ //
+ while (UnicodeStringTable->Language != NULL) {
+ if (CompareIso639LanguageCode (Language, UnicodeStringTable->Language)) {
+
+ //
+ // A matching string was found, so return it
+ //
+ *UnicodeString = UnicodeStringTable->UnicodeString;
+ return EFI_SUCCESS;
+ }
+
+ UnicodeStringTable++;
+ }
+
+ return EFI_UNSUPPORTED;
+ }
+
+ SupportedLanguages += 3;
+ }
+
+ return EFI_UNSUPPORTED;
+}
+
+
+
+/**
+ This function looks up a Unicode string in UnicodeStringTable.
+
+ If Language is a member of SupportedLanguages and a Unicode string is found in
+ UnicodeStringTable that matches the language code specified by Language, then
+ it is returned in UnicodeString.
+
+ @param Language A pointer to an ASCII string containing the ISO 639-2 or the
+ RFC 4646 language code for the Unicode string to look up and
+ return. If Iso639Language is TRUE, then this ASCII string is
+ not assumed to be Null-terminated, and only the first three
+ characters are used. If Iso639Language is FALSE, then this ASCII
+ string must be Null-terminated.
+ @param SupportedLanguages A pointer to a Null-terminated ASCII string that contains a
+ set of ISO 639-2 or RFC 4646 language codes that the Unicode
+ string table supports. Language must be a member of this set.
+ If Iso639Language is TRUE, then this string contains one or more
+ ISO 639-2 language codes with no separator characters. If Iso639Language
+ is FALSE, then is string contains one or more RFC 4646 language
+ codes separated by ';'.
+ @param UnicodeStringTable A pointer to the table of Unicode strings. Type EFI_UNICODE_STRING_TABLE
+ is defined in "Related Definitions".
+ @param UnicodeString A pointer to the Null-terminated Unicode string from UnicodeStringTable
+ that matches the language specified by Language.
+ @param Iso639Language Specifies the supported language code format. If it is TRUE, then
+ Language and SupportedLanguages follow ISO 639-2 language code format.
+ Otherwise, they follow RFC 4646 language code format.
+
+
+ @retval EFI_SUCCESS The Unicode string that matches the language specified by Language
+ was found in the table of Unicode strings UnicodeStringTable, and
+ it was returned in UnicodeString.
+ @retval EFI_INVALID_PARAMETER Language is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is NULL.
+ @retval EFI_UNSUPPORTED SupportedLanguages is NULL.
+ @retval EFI_UNSUPPORTED UnicodeStringTable is NULL.
+ @retval EFI_UNSUPPORTED The language specified by Language is not a member of SupportedLanguages.
+ @retval EFI_UNSUPPORTED The language specified by Language is not supported by UnicodeStringTable.
+
+**/
+EFI_STATUS
+EFIAPI
+LookupUnicodeString2 (
+ IN CONST CHAR8 *Language,
+ IN CONST CHAR8 *SupportedLanguages,
+ IN CONST EFI_UNICODE_STRING_TABLE *UnicodeStringTable,
+ OUT CHAR16 **UnicodeString,
+ IN BOOLEAN Iso639Language
+ )
+{
+ BOOLEAN Found;
+ UINTN Index;
+ CHAR8 *LanguageString;
+
+ //
+ // Make sure the parameters are valid
+ //
+ if (Language == NULL || UnicodeString == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // If there are no supported languages, or the Unicode String Table is empty, then the
+ // Unicode String specified by Language is not supported by this Unicode String Table
+ //
+ if (SupportedLanguages == NULL || UnicodeStringTable == NULL) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // Make sure Language is in the set of Supported Languages
+ //
+ Found = FALSE;
+ if (Iso639Language) {
+ while (*SupportedLanguages != 0) {
+ if (CompareIso639LanguageCode (Language, SupportedLanguages)) {
+ Found = TRUE;
+ break;
+ }
+ SupportedLanguages += 3;
+ }
+ } else {
+ Found = !IsLanguageSupported(SupportedLanguages, Language);
+ }
+
+
+ //
+ // If Language is not a member of SupportedLanguages, then return EFI_UNSUPPORTED
+ //
+ if (!Found) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // Search the Unicode String Table for the matching Language specifier
+ //
+ while (UnicodeStringTable->Language != NULL) {
+ LanguageString = UnicodeStringTable->Language;
+ while (0 != *LanguageString) {
+ for (Index = 0 ;LanguageString[Index] != 0 && LanguageString[Index] != ';'; Index++);
+ if (AsciiStrnCmp(LanguageString, Language, Index) == 0) {
+ *UnicodeString = UnicodeStringTable->UnicodeString;
+ return EFI_SUCCESS;
+ }
+ LanguageString += Index;
+ for (Index = 0 ;LanguageString[Index] != 0 && LanguageString[Index] == ';'; Index++);
+ }
+ UnicodeStringTable++;
+ }
+
+ return EFI_UNSUPPORTED;
+}
+
+
+/**
+ This function adds a Unicode string to UnicodeStringTable.
+
+ If Language is a member of SupportedLanguages then UnicodeString is added to
+ UnicodeStringTable. New buffers are allocated for both Language and
+ UnicodeString. The contents of Language and UnicodeString are copied into
+ these new buffers. These buffers are automatically freed when
+ FreeUnicodeStringTable() is called.
+
+ @param Language A pointer to the ISO 639-2 language code for the Unicode
+ string to add.
+ @param SupportedLanguages A pointer to the set of ISO 639-2 language codes
+ that the Unicode string table supports.
+ Language must be a member of this set.
+ @param UnicodeStringTable A pointer to the table of Unicode strings.
+ @param UnicodeString A pointer to the Unicode string to add.
+
+ @retval EFI_SUCCESS The Unicode string that matches the language
+ specified by Language was found in the table of
+ Unicode strings UnicodeStringTable, and it was
+ returned in UnicodeString.
+ @retval EFI_INVALID_PARAMETER Language is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is an empty string.
+ @retval EFI_UNSUPPORTED SupportedLanguages is NULL.
+ @retval EFI_ALREADY_STARTED A Unicode string with language Language is
+ already present in UnicodeStringTable.
+ @retval EFI_OUT_OF_RESOURCES There is not enough memory to add another
+ Unicode string to UnicodeStringTable.
+ @retval EFI_UNSUPPORTED The language specified by Language is not a
+ member of SupportedLanguages.
+
+**/
+EFI_STATUS
+EFIAPI
+AddUnicodeString (
+ IN CONST CHAR8 *Language,
+ IN CONST CHAR8 *SupportedLanguages,
+ IN OUT EFI_UNICODE_STRING_TABLE **UnicodeStringTable,
+ IN CONST CHAR16 *UnicodeString
+ )
+{
+ UINTN NumberOfEntries;
+ EFI_UNICODE_STRING_TABLE *OldUnicodeStringTable;
+ EFI_UNICODE_STRING_TABLE *NewUnicodeStringTable;
+ UINTN UnicodeStringLength;
+
+ //
+ // Make sure the parameter are valid
+ //
+ if (Language == NULL || UnicodeString == NULL || UnicodeStringTable == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // If there are no supported languages, then a Unicode String can not be added
+ //
+ if (SupportedLanguages == NULL) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // If the Unicode String is empty, then a Unicode String can not be added
+ //
+ if (UnicodeString[0] == 0) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Make sure Language is a member of SupportedLanguages
+ //
+ while (*SupportedLanguages != 0) {
+ if (CompareIso639LanguageCode (Language, SupportedLanguages)) {
+
+ //
+ // Determine the size of the Unicode String Table by looking for a NULL Language entry
+ //
+ NumberOfEntries = 0;
+ if (*UnicodeStringTable != NULL) {
+ OldUnicodeStringTable = *UnicodeStringTable;
+ while (OldUnicodeStringTable->Language != NULL) {
+ if (CompareIso639LanguageCode (Language, OldUnicodeStringTable->Language)) {
+ return EFI_ALREADY_STARTED;
+ }
+
+ OldUnicodeStringTable++;
+ NumberOfEntries++;
+ }
+ }
+
+ //
+ // Allocate space for a new Unicode String Table. It must hold the current number of
+ // entries, plus 1 entry for the new Unicode String, plus 1 entry for the end of table
+ // marker
+ //
+ NewUnicodeStringTable = AllocatePool ((NumberOfEntries + 2) * sizeof (EFI_UNICODE_STRING_TABLE));
+ if (NewUnicodeStringTable == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // If the current Unicode String Table contains any entries, then copy them to the
+ // newly allocated Unicode String Table.
+ //
+ if (*UnicodeStringTable != NULL) {
+ CopyMem (
+ NewUnicodeStringTable,
+ *UnicodeStringTable,
+ NumberOfEntries * sizeof (EFI_UNICODE_STRING_TABLE)
+ );
+ }
+
+ //
+ // Allocate space for a copy of the Language specifier
+ //
+ NewUnicodeStringTable[NumberOfEntries].Language = AllocateCopyPool (3, Language);
+ if (NewUnicodeStringTable[NumberOfEntries].Language == NULL) {
+ FreePool (NewUnicodeStringTable);
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Compute the length of the Unicode String
+ //
+ for (UnicodeStringLength = 0; UnicodeString[UnicodeStringLength] != 0; UnicodeStringLength++)
+ ;
+
+ //
+ // Allocate space for a copy of the Unicode String
+ //
+ NewUnicodeStringTable[NumberOfEntries].UnicodeString = AllocateCopyPool (
+ (UnicodeStringLength + 1) * sizeof (CHAR16),
+ UnicodeString
+ );
+ if (NewUnicodeStringTable[NumberOfEntries].UnicodeString == NULL) {
+ FreePool (NewUnicodeStringTable[NumberOfEntries].Language);
+ FreePool (NewUnicodeStringTable);
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Mark the end of the Unicode String Table
+ //
+ NewUnicodeStringTable[NumberOfEntries + 1].Language = NULL;
+ NewUnicodeStringTable[NumberOfEntries + 1].UnicodeString = NULL;
+
+ //
+ // Free the old Unicode String Table
+ //
+ if (*UnicodeStringTable != NULL) {
+ FreePool (*UnicodeStringTable);
+ }
+
+ //
+ // Point UnicodeStringTable at the newly allocated Unicode String Table
+ //
+ *UnicodeStringTable = NewUnicodeStringTable;
+
+ return EFI_SUCCESS;
+ }
+
+ SupportedLanguages += 3;
+ }
+
+ return EFI_UNSUPPORTED;
+}
+
+
+/**
+ This function adds the Null-terminated Unicode string specified by UnicodeString
+ to UnicodeStringTable.
+
+ If Language is a member of SupportedLanguages then UnicodeString is added to
+ UnicodeStringTable. New buffers are allocated for both Language and UnicodeString.
+ The contents of Language and UnicodeString are copied into these new buffers.
+ These buffers are automatically freed when EfiLibFreeUnicodeStringTable() is called.
+
+ @param Language A pointer to an ASCII string containing the ISO 639-2 or
+ the RFC 4646 language code for the Unicode string to add.
+ If Iso639Language is TRUE, then this ASCII string is not
+ assumed to be Null-terminated, and only the first three
+ chacters are used. If Iso639Language is FALSE, then this
+ ASCII string must be Null-terminated.
+ @param SupportedLanguages A pointer to a Null-terminated ASCII string that contains
+ a set of ISO 639-2 or RFC 4646 language codes that the Unicode
+ string table supports. Language must be a member of this set.
+ If Iso639Language is TRUE, then this string contains one or more
+ ISO 639-2 language codes with no separator characters.
+ If Iso639Language is FALSE, then is string contains one or more
+ RFC 4646 language codes separated by ';'.
+ @param UnicodeStringTable A pointer to the table of Unicode strings. Type EFI_UNICODE_STRING_TABLE
+ is defined in "Related Definitions".
+ @param UnicodeString A pointer to the Unicode string to add.
+ @param Iso639Language Specifies the supported language code format. If it is TRUE,
+ then Language and SupportedLanguages follow ISO 639-2 language code format.
+ Otherwise, they follow RFC 4646 language code format.
+
+ @retval EFI_SUCCESS The Unicode string that matches the language specified by
+ Language was found in the table of Unicode strings UnicodeStringTable,
+ and it was returned in UnicodeString.
+ @retval EFI_INVALID_PARAMETER Language is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is NULL.
+ @retval EFI_INVALID_PARAMETER UnicodeString is an empty string.
+ @retval EFI_UNSUPPORTED SupportedLanguages is NULL.
+ @retval EFI_ALREADY_STARTED A Unicode string with language Language is already present in
+ UnicodeStringTable.
+ @retval EFI_OUT_OF_RESOURCES There is not enough memory to add another Unicode string UnicodeStringTable.
+ @retval EFI_UNSUPPORTED The language specified by Language is not a member of SupportedLanguages.
+
+**/
+EFI_STATUS
+EFIAPI
+AddUnicodeString2 (
+ IN CONST CHAR8 *Language,
+ IN CONST CHAR8 *SupportedLanguages,
+ IN OUT EFI_UNICODE_STRING_TABLE **UnicodeStringTable,
+ IN CONST CHAR16 *UnicodeString,
+ IN BOOLEAN Iso639Language
+ )
+{
+ UINTN NumberOfEntries;
+ EFI_UNICODE_STRING_TABLE *OldUnicodeStringTable;
+ EFI_UNICODE_STRING_TABLE *NewUnicodeStringTable;
+ UINTN UnicodeStringLength;
+ BOOLEAN Found;
+ UINTN Index;
+ CHAR8 *LanguageString;
+
+ //
+ // Make sure the parameter are valid
+ //
+ if (Language == NULL || UnicodeString == NULL || UnicodeStringTable == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // If there are no supported languages, then a Unicode String can not be added
+ //
+ if (SupportedLanguages == NULL) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // If the Unicode String is empty, then a Unicode String can not be added
+ //
+ if (UnicodeString[0] == 0) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Make sure Language is a member of SupportedLanguages
+ //
+ Found = FALSE;
+ if (Iso639Language) {
+ while (*SupportedLanguages != 0) {
+ if (CompareIso639LanguageCode (Language, SupportedLanguages)) {
+ Found = TRUE;
+ break;
+ }
+ SupportedLanguages += 3;
+ }
+ } else {
+ Found = !IsLanguageSupported(SupportedLanguages, Language);
+ }
+ //
+ // If Language is not a member of SupportedLanguages, then return EFI_UNSUPPORTED
+ //
+ if (!Found) {
+ return EFI_UNSUPPORTED;
+ }
+
+ //
+ // Determine the size of the Unicode String Table by looking for a NULL Language entry
+ //
+ NumberOfEntries = 0;
+ if (*UnicodeStringTable != NULL) {
+ OldUnicodeStringTable = *UnicodeStringTable;
+ while (OldUnicodeStringTable->Language != NULL) {
+ LanguageString = OldUnicodeStringTable->Language;
+
+ while (*LanguageString != 0) {
+ for (Index = 0; LanguageString[Index] != 0 && LanguageString[Index] != ';'; Index++);
+
+ if (AsciiStrnCmp (Language, LanguageString, Index) == 0) {
+ return EFI_ALREADY_STARTED;
+ }
+ LanguageString += Index;
+ for (; *LanguageString != 0 && *LanguageString == ';'; LanguageString++);
+ }
+ OldUnicodeStringTable++;
+ NumberOfEntries++;
+ }
+ }
+
+ //
+ // Allocate space for a new Unicode String Table. It must hold the current number of
+ // entries, plus 1 entry for the new Unicode String, plus 1 entry for the end of table
+ // marker
+ //
+ NewUnicodeStringTable = AllocatePool ((NumberOfEntries + 2) * sizeof (EFI_UNICODE_STRING_TABLE));
+ if (NewUnicodeStringTable == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // If the current Unicode String Table contains any entries, then copy them to the
+ // newly allocated Unicode String Table.
+ //
+ if (*UnicodeStringTable != NULL) {
+ CopyMem (
+ NewUnicodeStringTable,
+ *UnicodeStringTable,
+ NumberOfEntries * sizeof (EFI_UNICODE_STRING_TABLE)
+ );
+ }
+
+ //
+ // Allocate space for a copy of the Language specifier
+ //
+ NewUnicodeStringTable[NumberOfEntries].Language = AllocateCopyPool (AsciiStrSize(Language), Language);
+ if (NewUnicodeStringTable[NumberOfEntries].Language == NULL) {
+ FreePool (NewUnicodeStringTable);
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Compute the length of the Unicode String
+ //
+ for (UnicodeStringLength = 0; UnicodeString[UnicodeStringLength] != 0; UnicodeStringLength++);
+
+ //
+ // Allocate space for a copy of the Unicode String
+ //
+ NewUnicodeStringTable[NumberOfEntries].UnicodeString = AllocateCopyPool (StrSize (UnicodeString), UnicodeString);
+ if (NewUnicodeStringTable[NumberOfEntries].UnicodeString == NULL) {
+ FreePool (NewUnicodeStringTable[NumberOfEntries].Language);
+ FreePool (NewUnicodeStringTable);
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Mark the end of the Unicode String Table
+ //
+ NewUnicodeStringTable[NumberOfEntries + 1].Language = NULL;
+ NewUnicodeStringTable[NumberOfEntries + 1].UnicodeString = NULL;
+
+ //
+ // Free the old Unicode String Table
+ //
+ if (*UnicodeStringTable != NULL) {
+ FreePool (*UnicodeStringTable);
+ }
+
+ //
+ // Point UnicodeStringTable at the newly allocated Unicode String Table
+ //
+ *UnicodeStringTable = NewUnicodeStringTable;
+
+ return EFI_SUCCESS;
+}
+
+/**
+ This function frees the table of Unicode strings in UnicodeStringTable.
+
+ If UnicodeStringTable is NULL, then EFI_SUCCESS is returned.
+ Otherwise, each language code, and each Unicode string in the Unicode string
+ table are freed, and EFI_SUCCESS is returned.
+
+ @param UnicodeStringTable A pointer to the table of Unicode strings.
+
+ @retval EFI_SUCCESS The Unicode string table was freed.
+
+**/
+EFI_STATUS
+EFIAPI
+FreeUnicodeStringTable (
+ IN EFI_UNICODE_STRING_TABLE *UnicodeStringTable
+ )
+{
+ UINTN Index;
+
+ //
+ // If the Unicode String Table is NULL, then it is already freed
+ //
+ if (UnicodeStringTable == NULL) {
+ return EFI_SUCCESS;
+ }
+
+ //
+ // Loop through the Unicode String Table until we reach the end of table marker
+ //
+ for (Index = 0; UnicodeStringTable[Index].Language != NULL; Index++) {
+
+ //
+ // Free the Language string from the Unicode String Table
+ //
+ FreePool (UnicodeStringTable[Index].Language);
+
+ //
+ // Free the Unicode String from the Unicode String Table
+ //
+ if (UnicodeStringTable[Index].UnicodeString != NULL) {
+ FreePool (UnicodeStringTable[Index].UnicodeString);
+ }
+ }
+
+ //
+ // Free the Unicode String Table itself
+ //
+ FreePool (UnicodeStringTable);
+
+ return EFI_SUCCESS;
+}
+
+
+/**
+ Returns the status whether get the variable success. The function retrieves
+ variable through the UEFI Runtime Service GetVariable(). The
+ returned buffer is allocated using AllocatePool(). The caller is responsible
+ for freeing this buffer with FreePool().
+
+ If Name is NULL, then ASSERT().
+ If Guid is NULL, then ASSERT().
+ If Value is NULL, then ASSERT().
+
+ @param[in] Name The pointer to a Null-terminated Unicode string.
+ @param[in] Guid The pointer to an EFI_GUID structure
+ @param[out] Value The buffer point saved the variable info.
+ @param[out] Size The buffer size of the variable.
+
+ @return EFI_OUT_OF_RESOURCES Allocate buffer failed.
+ @return EFI_SUCCESS Find the specified variable.
+ @return Others Errors Return errors from call to gRT->GetVariable.
+
+**/
+EFI_STATUS
+EFIAPI
+GetVariable2 (
+ IN CONST CHAR16 *Name,
+ IN CONST EFI_GUID *Guid,
+ OUT VOID **Value,
+ OUT UINTN *Size OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ UINTN BufferSize;
+
+ ASSERT (Name != NULL && Guid != NULL && Value != NULL);
+
+ //
+ // Try to get the variable size.
+ //
+ BufferSize = 0;
+ *Value = NULL;
+ if (Size != NULL) {
+ *Size = 0;
+ }
+
+ Status = gRT->GetVariable ((CHAR16 *) Name, (EFI_GUID *) Guid, NULL, &BufferSize, *Value);
+ if (Status != EFI_BUFFER_TOO_SMALL) {
+ return Status;
+ }
+
+ //
+ // Allocate buffer to get the variable.
+ //
+ *Value = AllocatePool (BufferSize);
+ ASSERT (*Value != NULL);
+ if (*Value == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Get the variable data.
+ //
+ Status = gRT->GetVariable ((CHAR16 *) Name, (EFI_GUID *) Guid, NULL, &BufferSize, *Value);
+ if (EFI_ERROR (Status)) {
+ FreePool(*Value);
+ *Value = NULL;
+ }
+
+ if (Size != NULL) {
+ *Size = BufferSize;
+ }
+
+ return Status;
+}
+
+/** Return the attributes of the variable.
+
+ Returns the status whether get the variable success. The function retrieves
+ variable through the UEFI Runtime Service GetVariable(). The
+ returned buffer is allocated using AllocatePool(). The caller is responsible
+ for freeing this buffer with FreePool(). The attributes are returned if
+ the caller provides a valid Attribute parameter.
+
+ If Name is NULL, then ASSERT().
+ If Guid is NULL, then ASSERT().
+ If Value is NULL, then ASSERT().
+
+ @param[in] Name The pointer to a Null-terminated Unicode string.
+ @param[in] Guid The pointer to an EFI_GUID structure
+ @param[out] Value The buffer point saved the variable info.
+ @param[out] Size The buffer size of the variable.
+ @param[out] Attr The pointer to the variable attributes as found in var store
+
+ @retval EFI_OUT_OF_RESOURCES Allocate buffer failed.
+ @retval EFI_SUCCESS Find the specified variable.
+ @retval Others Errors Return errors from call to gRT->GetVariable.
+
+**/
+EFI_STATUS
+EFIAPI
+GetVariable3(
+ IN CONST CHAR16 *Name,
+ IN CONST EFI_GUID *Guid,
+ OUT VOID **Value,
+ OUT UINTN *Size OPTIONAL,
+ OUT UINT32 *Attr OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ UINTN BufferSize;
+
+ ASSERT(Name != NULL && Guid != NULL && Value != NULL);
+
+ //
+ // Try to get the variable size.
+ //
+ BufferSize = 0;
+ *Value = NULL;
+ if (Size != NULL) {
+ *Size = 0;
+ }
+
+ if (Attr != NULL) {
+ *Attr = 0;
+ }
+
+ Status = gRT->GetVariable((CHAR16 *)Name, (EFI_GUID *)Guid, Attr, &BufferSize, *Value);
+ if (Status != EFI_BUFFER_TOO_SMALL) {
+ return Status;
+ }
+
+ //
+ // Allocate buffer to get the variable.
+ //
+ *Value = AllocatePool(BufferSize);
+ ASSERT(*Value != NULL);
+ if (*Value == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ //
+ // Get the variable data.
+ //
+ Status = gRT->GetVariable((CHAR16 *)Name, (EFI_GUID *)Guid, Attr, &BufferSize, *Value);
+ if (EFI_ERROR(Status)) {
+ FreePool(*Value);
+ *Value = NULL;
+ }
+
+ if (Size != NULL) {
+ *Size = BufferSize;
+ }
+
+ return Status;
+}
+
+/**
+ Returns a pointer to an allocated buffer that contains the contents of a
+ variable retrieved through the UEFI Runtime Service GetVariable(). This
+ function always uses the EFI_GLOBAL_VARIABLE GUID to retrieve variables.
+ The returned buffer is allocated using AllocatePool(). The caller is
+ responsible for freeing this buffer with FreePool().
+
+ If Name is NULL, then ASSERT().
+ If Value is NULL, then ASSERT().
+
+ @param[in] Name The pointer to a Null-terminated Unicode string.
+ @param[out] Value The buffer point saved the variable info.
+ @param[out] Size The buffer size of the variable.
+
+ @return EFI_OUT_OF_RESOURCES Allocate buffer failed.
+ @return EFI_SUCCESS Find the specified variable.
+ @return Others Errors Return errors from call to gRT->GetVariable.
+
+**/
+EFI_STATUS
+EFIAPI
+GetEfiGlobalVariable2 (
+ IN CONST CHAR16 *Name,
+ OUT VOID **Value,
+ OUT UINTN *Size OPTIONAL
+ )
+{
+ return GetVariable2 (Name, &gEfiGlobalVariableGuid, Value, Size);
+}
+
+/**
+ Returns a pointer to an allocated buffer that contains the best matching language
+ from a set of supported languages.
+
+ This function supports both ISO 639-2 and RFC 4646 language codes, but language
+ code types may not be mixed in a single call to this function. The language
+ code returned is allocated using AllocatePool(). The caller is responsible for
+ freeing the allocated buffer using FreePool(). This function supports a variable
+ argument list that allows the caller to pass in a prioritized list of language
+ codes to test against all the language codes in SupportedLanguages.
+
+ If SupportedLanguages is NULL, then ASSERT().
+
+ @param[in] SupportedLanguages A pointer to a Null-terminated ASCII string that
+ contains a set of language codes in the format
+ specified by Iso639Language.
+ @param[in] Iso639Language If not zero, then all language codes are assumed to be
+ in ISO 639-2 format. If zero, then all language
+ codes are assumed to be in RFC 4646 language format
+ @param[in] ... A variable argument list that contains pointers to
+ Null-terminated ASCII strings that contain one or more
+ language codes in the format specified by Iso639Language.
+ The first language code from each of these language
+ code lists is used to determine if it is an exact or
+ close match to any of the language codes in
+ SupportedLanguages. Close matches only apply to RFC 4646
+ language codes, and the matching algorithm from RFC 4647
+ is used to determine if a close match is present. If
+ an exact or close match is found, then the matching
+ language code from SupportedLanguages is returned. If
+ no matches are found, then the next variable argument
+ parameter is evaluated. The variable argument list
+ is terminated by a NULL.
+
+ @retval NULL The best matching language could not be found in SupportedLanguages.
+ @retval NULL There are not enough resources available to return the best matching
+ language.
+ @retval Other A pointer to a Null-terminated ASCII string that is the best matching
+ language in SupportedLanguages.
+
+**/
+CHAR8 *
+EFIAPI
+GetBestLanguage (
+ IN CONST CHAR8 *SupportedLanguages,
+ IN UINTN Iso639Language,
+ ...
+ )
+{
+ VA_LIST Args;
+ CHAR8 *Language;
+ UINTN CompareLength;
+ UINTN LanguageLength;
+ CONST CHAR8 *Supported;
+ CHAR8 *BestLanguage;
+
+ ASSERT (SupportedLanguages != NULL);
+
+ VA_START (Args, Iso639Language);
+ while ((Language = VA_ARG (Args, CHAR8 *)) != NULL) {
+ //
+ // Default to ISO 639-2 mode
+ //
+ CompareLength = 3;
+ LanguageLength = MIN (3, AsciiStrLen (Language));
+
+ //
+ // If in RFC 4646 mode, then determine the length of the first RFC 4646 language code in Language
+ //
+ if (Iso639Language == 0) {
+ for (LanguageLength = 0; Language[LanguageLength] != 0 && Language[LanguageLength] != ';'; LanguageLength++);
+ }
+
+ //
+ // Trim back the length of Language used until it is empty
+ //
+ while (LanguageLength > 0) {
+ //
+ // Loop through all language codes in SupportedLanguages
+ //
+ for (Supported = SupportedLanguages; *Supported != '\0'; Supported += CompareLength) {
+ //
+ // In RFC 4646 mode, then Loop through all language codes in SupportedLanguages
+ //
+ if (Iso639Language == 0) {
+ //
+ // Skip ';' characters in Supported
+ //
+ for (; *Supported != '\0' && *Supported == ';'; Supported++);
+ //
+ // Determine the length of the next language code in Supported
+ //
+ for (CompareLength = 0; Supported[CompareLength] != 0 && Supported[CompareLength] != ';'; CompareLength++);
+ //
+ // If Language is longer than the Supported, then skip to the next language
+ //
+ if (LanguageLength > CompareLength) {
+ continue;
+ }
+ }
+ //
+ // See if the first LanguageLength characters in Supported match Language
+ //
+ if (AsciiStrnCmp (Supported, Language, LanguageLength) == 0) {
+ VA_END (Args);
+ //
+ // Allocate, copy, and return the best matching language code from SupportedLanguages
+ //
+ BestLanguage = AllocateZeroPool (CompareLength + 1);
+ if (BestLanguage == NULL) {
+ return NULL;
+ }
+ return CopyMem (BestLanguage, Supported, CompareLength);
+ }
+ }
+
+ if (Iso639Language != 0) {
+ //
+ // If ISO 639 mode, then each language can only be tested once
+ //
+ LanguageLength = 0;
+ } else {
+ //
+ // If RFC 4646 mode, then trim Language from the right to the next '-' character
+ //
+ for (LanguageLength--; LanguageLength > 0 && Language[LanguageLength] != '-'; LanguageLength--);
+ }
+ }
+ }
+ VA_END (Args);
+
+ //
+ // No matches were found
+ //
+ return NULL;
+}
+
+/**
+ Returns an array of protocol instance that matches the given protocol.
+
+ @param[in] Protocol Provides the protocol to search for.
+ @param[out] NoProtocols The number of protocols returned in Buffer.
+ @param[out] Buffer A pointer to the buffer to return the requested
+ array of protocol instances that match Protocol.
+ The returned buffer is allocated using
+ EFI_BOOT_SERVICES.AllocatePool(). The caller is
+ responsible for freeing this buffer with
+ EFI_BOOT_SERVICES.FreePool().
+
+ @retval EFI_SUCCESS The array of protocols was returned in Buffer,
+ and the number of protocols in Buffer was
+ returned in NoProtocols.
+ @retval EFI_NOT_FOUND No protocols found.
+ @retval EFI_OUT_OF_RESOURCES There is not enough pool memory to store the
+ matching results.
+ @retval EFI_INVALID_PARAMETER Protocol is NULL.
+ @retval EFI_INVALID_PARAMETER NoProtocols is NULL.
+ @retval EFI_INVALID_PARAMETER Buffer is NULL.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiLocateProtocolBuffer (
+ IN EFI_GUID *Protocol,
+ OUT UINTN *NoProtocols,
+ OUT VOID ***Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINTN NoHandles;
+ EFI_HANDLE *HandleBuffer;
+ UINTN Index;
+
+ //
+ // Check input parameters
+ //
+ if (Protocol == NULL || NoProtocols == NULL || Buffer == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Initialze output parameters
+ //
+ *NoProtocols = 0;
+ *Buffer = NULL;
+
+ //
+ // Retrieve the array of handles that support Protocol
+ //
+ Status = gBS->LocateHandleBuffer (
+ ByProtocol,
+ Protocol,
+ NULL,
+ &NoHandles,
+ &HandleBuffer
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ //
+ // Allocate array of protocol instances
+ //
+ Status = gBS->AllocatePool (
+ EfiBootServicesData,
+ NoHandles * sizeof (VOID *),
+ (VOID **)Buffer
+ );
+ if (EFI_ERROR (Status)) {
+ //
+ // Free the handle buffer
+ //
+ gBS->FreePool (HandleBuffer);
+ return EFI_OUT_OF_RESOURCES;
+ }
+ ZeroMem (*Buffer, NoHandles * sizeof (VOID *));
+
+ //
+ // Lookup Protocol on each handle in HandleBuffer to fill in the array of
+ // protocol instances. Handle case where protocol instance was present when
+ // LocateHandleBuffer() was called, but is not present when HandleProtocol()
+ // is called.
+ //
+ for (Index = 0, *NoProtocols = 0; Index < NoHandles; Index++) {
+ Status = gBS->HandleProtocol (
+ HandleBuffer[Index],
+ Protocol,
+ &((*Buffer)[*NoProtocols])
+ );
+ if (!EFI_ERROR (Status)) {
+ (*NoProtocols)++;
+ }
+ }
+
+ //
+ // Free the handle buffer
+ //
+ gBS->FreePool (HandleBuffer);
+
+ //
+ // Make sure at least one protocol instance was found
+ //
+ if (*NoProtocols == 0) {
+ gBS->FreePool (*Buffer);
+ *Buffer = NULL;
+ return EFI_NOT_FOUND;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Open or create a file or directory, possibly creating the chain of
+ directories leading up to the directory.
+
+ EfiOpenFileByDevicePath() first locates EFI_SIMPLE_FILE_SYSTEM_PROTOCOL on
+ FilePath, and opens the root directory of that filesystem with
+ EFI_SIMPLE_FILE_SYSTEM_PROTOCOL.OpenVolume().
+
+ On the remaining device path, the longest initial sequence of
+ FILEPATH_DEVICE_PATH nodes is node-wise traversed with
+ EFI_FILE_PROTOCOL.Open().
+
+ (As a consequence, if OpenMode includes EFI_FILE_MODE_CREATE, and Attributes
+ includes EFI_FILE_DIRECTORY, and each FILEPATH_DEVICE_PATH specifies a single
+ pathname component, then EfiOpenFileByDevicePath() ensures that the specified
+ series of subdirectories exist on return.)
+
+ The EFI_FILE_PROTOCOL identified by the last FILEPATH_DEVICE_PATH node is
+ output to the caller; intermediate EFI_FILE_PROTOCOL instances are closed. If
+ there are no FILEPATH_DEVICE_PATH nodes past the node that identifies the
+ filesystem, then the EFI_FILE_PROTOCOL of the root directory of the
+ filesystem is output to the caller. If a device path node that is different
+ from FILEPATH_DEVICE_PATH is encountered relative to the filesystem, the
+ traversal is stopped with an error, and a NULL EFI_FILE_PROTOCOL is output.
+
+ @param[in,out] FilePath On input, the device path to the file or directory
+ to open or create. The caller is responsible for
+ ensuring that the device path pointed-to by FilePath
+ is well-formed. On output, FilePath points one past
+ the last node in the original device path that has
+ been successfully processed. FilePath is set on
+ output even if EfiOpenFileByDevicePath() returns an
+ error.
+
+ @param[out] File On error, File is set to NULL. On success, File is
+ set to the EFI_FILE_PROTOCOL of the root directory
+ of the filesystem, if there are no
+ FILEPATH_DEVICE_PATH nodes in FilePath; otherwise,
+ File is set to the EFI_FILE_PROTOCOL identified by
+ the last node in FilePath.
+
+ @param[in] OpenMode The OpenMode parameter to pass to
+ EFI_FILE_PROTOCOL.Open().
+
+ @param[in] Attributes The Attributes parameter to pass to
+ EFI_FILE_PROTOCOL.Open().
+
+ @retval EFI_SUCCESS The file or directory has been opened or
+ created.
+
+ @retval EFI_INVALID_PARAMETER FilePath is NULL; or File is NULL; or FilePath
+ contains a device path node, past the node
+ that identifies
+ EFI_SIMPLE_FILE_SYSTEM_PROTOCOL, that is not a
+ FILEPATH_DEVICE_PATH node.
+
+ @retval EFI_OUT_OF_RESOURCES Memory allocation failed.
+
+ @return Error codes propagated from the
+ LocateDevicePath() and OpenProtocol() boot
+ services, and from the
+ EFI_SIMPLE_FILE_SYSTEM_PROTOCOL.OpenVolume()
+ and EFI_FILE_PROTOCOL.Open() member functions.
+**/
+EFI_STATUS
+EFIAPI
+EfiOpenFileByDevicePath (
+ IN OUT EFI_DEVICE_PATH_PROTOCOL **FilePath,
+ OUT EFI_FILE_PROTOCOL **File,
+ IN UINT64 OpenMode,
+ IN UINT64 Attributes
+ )
+{
+ EFI_STATUS Status;
+ EFI_HANDLE FileSystemHandle;
+ EFI_SIMPLE_FILE_SYSTEM_PROTOCOL *FileSystem;
+ EFI_FILE_PROTOCOL *LastFile;
+ FILEPATH_DEVICE_PATH *FilePathNode;
+ CHAR16 *AlignedPathName;
+ CHAR16 *PathName;
+ EFI_FILE_PROTOCOL *NextFile;
+
+ if (File == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+ *File = NULL;
+
+ if (FilePath == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Look up the filesystem.
+ //
+ Status = gBS->LocateDevicePath (
+ &gEfiSimpleFileSystemProtocolGuid,
+ FilePath,
+ &FileSystemHandle
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ Status = gBS->OpenProtocol (
+ FileSystemHandle,
+ &gEfiSimpleFileSystemProtocolGuid,
+ (VOID **)&FileSystem,
+ gImageHandle,
+ NULL,
+ EFI_OPEN_PROTOCOL_GET_PROTOCOL
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ //
+ // Open the root directory of the filesystem. After this operation succeeds,
+ // we have to release LastFile on error.
+ //
+ Status = FileSystem->OpenVolume (FileSystem, &LastFile);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ //
+ // Traverse the device path nodes relative to the filesystem.
+ //
+ while (!IsDevicePathEnd (*FilePath)) {
+ if (DevicePathType (*FilePath) != MEDIA_DEVICE_PATH ||
+ DevicePathSubType (*FilePath) != MEDIA_FILEPATH_DP) {
+ Status = EFI_INVALID_PARAMETER;
+ goto CloseLastFile;
+ }
+ FilePathNode = (FILEPATH_DEVICE_PATH *)*FilePath;
+
+ //
+ // FilePathNode->PathName may be unaligned, and the UEFI specification
+ // requires pointers that are passed to protocol member functions to be
+ // aligned. Create an aligned copy of the pathname if necessary.
+ //
+ if ((UINTN)FilePathNode->PathName % sizeof *FilePathNode->PathName == 0) {
+ AlignedPathName = NULL;
+ PathName = FilePathNode->PathName;
+ } else {
+ AlignedPathName = AllocateCopyPool (
+ (DevicePathNodeLength (FilePathNode) -
+ SIZE_OF_FILEPATH_DEVICE_PATH),
+ FilePathNode->PathName
+ );
+ if (AlignedPathName == NULL) {
+ Status = EFI_OUT_OF_RESOURCES;
+ goto CloseLastFile;
+ }
+ PathName = AlignedPathName;
+ }
+
+ //
+ // Open or create the file corresponding to the next pathname fragment.
+ //
+ Status = LastFile->Open (
+ LastFile,
+ &NextFile,
+ PathName,
+ OpenMode,
+ Attributes
+ );
+
+ //
+ // Release any AlignedPathName on both error and success paths; PathName is
+ // no longer needed.
+ //
+ if (AlignedPathName != NULL) {
+ FreePool (AlignedPathName);
+ }
+ if (EFI_ERROR (Status)) {
+ goto CloseLastFile;
+ }
+
+ //
+ // Advance to the next device path node.
+ //
+ LastFile->Close (LastFile);
+ LastFile = NextFile;
+ *FilePath = NextDevicePathNode (FilePathNode);
+ }
+
+ *File = LastFile;
+ return EFI_SUCCESS;
+
+CloseLastFile:
+ LastFile->Close (LastFile);
+
+ //
+ // We are on the error path; we must have set an error Status for returning
+ // to the caller.
+ //
+ ASSERT (EFI_ERROR (Status));
+ return Status;
+}
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibInternal.h b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibInternal.h
new file mode 100644
index 0000000..d2b2c44
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibInternal.h
@@ -0,0 +1,38 @@
+/** @file
+ Internal include file for UefiLib.
+
+ Copyright (c) 2007 - 2017, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef __UEFI_LIB_INTERNAL_H_
+#define __UEFI_LIB_INTERNAL_H_
+
+
+#include <Uefi.h>
+#include <Protocol/DriverBinding.h>
+#include <Protocol/ComponentName.h>
+#include <Protocol/ComponentName2.h>
+#include <Protocol/DriverConfiguration.h>
+#include <Protocol/DriverConfiguration2.h>
+#include <Protocol/DriverDiagnostics.h>
+#include <Protocol/DriverDiagnostics2.h>
+#include <Protocol/LoadedImage.h>
+#include <Protocol/GraphicsOutput.h>
+#include <Protocol/UgaDraw.h>
+#include <Protocol/HiiFont.h>
+
+#include "Efi_Defs_GUID.h"
+#include <Guid/GlobalVariable.h>
+#include <Library/UefiLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/UefiRuntimeServicesTableLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/PcdLib.h>
+#include <Library/PrintLib.h>
+#include <Library/DevicePathLib.h>
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibPrint.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibPrint.c
new file mode 100644
index 0000000..e848a92
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiLibPrint.c
@@ -0,0 +1,817 @@
+/** @file
+ Mde UEFI library API implementation.
+ Print to StdErr or ConOut defined in EFI_SYSTEM_TABLE
+
+ Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "UefiLibInternal.h"
+#include "Efi_Defs.h"
+
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_GRAPHICS_OUTPUT_BLT_PIXEL mEfiColors[16] = {
+ { 0x00, 0x00, 0x00, 0x00 },
+ { 0x98, 0x00, 0x00, 0x00 },
+ { 0x00, 0x98, 0x00, 0x00 },
+ { 0x98, 0x98, 0x00, 0x00 },
+ { 0x00, 0x00, 0x98, 0x00 },
+ { 0x98, 0x00, 0x98, 0x00 },
+ { 0x00, 0x98, 0x98, 0x00 },
+ { 0x98, 0x98, 0x98, 0x00 },
+ { 0x10, 0x10, 0x10, 0x00 },
+ { 0xff, 0x10, 0x10, 0x00 },
+ { 0x10, 0xff, 0x10, 0x00 },
+ { 0xff, 0xff, 0x10, 0x00 },
+ { 0x10, 0x10, 0xff, 0x00 },
+ { 0xf0, 0x10, 0xff, 0x00 },
+ { 0x10, 0xff, 0xff, 0x00 },
+ { 0xff, 0xff, 0xff, 0x00 }
+};
+
+/**
+ Internal function which prints a formatted Unicode string to the console output device
+ specified by Console
+
+ This function prints a formatted Unicode string to the console output device
+ specified by Console and returns the number of Unicode characters that printed
+ to it. If the length of the formatted Unicode string is greater than PcdUefiLibMaxPrintBufferSize,
+ then only the first PcdUefiLibMaxPrintBufferSize characters are sent to Console.
+ If Format is NULL, then ASSERT().
+ If Format is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param Format A Null-terminated Unicode format string.
+ @param Console The output console.
+ @param Marker A VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced
+ output buffer, not including the Null-terminator.
+**/
+UINTN
+InternalPrint (
+ IN CONST CHAR16 *Format,
+ IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console,
+ IN VA_LIST Marker
+ )
+{
+ EFI_STATUS Status;
+ UINTN Return;
+ CHAR16 *Buffer;
+ UINTN BufferSize;
+
+ ASSERT (Format != NULL);
+ ASSERT (((UINTN) Format & BIT0) == 0);
+ ASSERT (Console != NULL);
+
+ BufferSize = (PcdGet32 (PcdUefiLibMaxPrintBufferSize) + 1) * sizeof (CHAR16);
+
+ Buffer = (CHAR16 *) AllocatePool(BufferSize);
+ ASSERT (Buffer != NULL);
+
+ Return = UnicodeVSPrint (Buffer, BufferSize, Format, Marker);
+
+ if (Console != NULL && Return > 0) {
+ //
+ // To be extra safe make sure Console has been initialized
+ //
+ Status = Console->OutputString (Console, Buffer);
+ if (EFI_ERROR (Status)) {
+ Return = 0;
+ }
+ }
+
+ FreePool (Buffer);
+
+ return Return;
+}
+
+/**
+ Prints a formatted Unicode string to the console output device specified by
+ ConOut defined in the EFI_SYSTEM_TABLE.
+
+ This function prints a formatted Unicode string to the console output device
+ specified by ConOut in EFI_SYSTEM_TABLE and returns the number of Unicode
+ characters that printed to ConOut. If the length of the formatted Unicode
+ string is greater than PcdUefiLibMaxPrintBufferSize, then only the first
+ PcdUefiLibMaxPrintBufferSize characters are sent to ConOut.
+ If Format is NULL, then ASSERT().
+ If Format is not aligned on a 16-bit boundary, then ASSERT().
+ If gST->ConOut is NULL, then ASSERT().
+
+ @param Format A Null-terminated Unicode format string.
+ @param ... A Variable argument list whose contents are accessed based
+ on the format string specified by Format.
+
+ @return The number of Unicode characters printed to ConOut.
+
+**/
+UINTN
+EFIAPI
+Print (
+ IN CONST CHAR16 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN Return;
+
+ VA_START (Marker, Format);
+
+ Return = InternalPrint (Format, gST->ConOut, Marker);
+
+ VA_END (Marker);
+
+ return Return;
+}
+
+/**
+ Prints a formatted Unicode string to the console output device specified by
+ StdErr defined in the EFI_SYSTEM_TABLE.
+
+ This function prints a formatted Unicode string to the console output device
+ specified by StdErr in EFI_SYSTEM_TABLE and returns the number of Unicode
+ characters that printed to StdErr. If the length of the formatted Unicode
+ string is greater than PcdUefiLibMaxPrintBufferSize, then only the first
+ PcdUefiLibMaxPrintBufferSize characters are sent to StdErr.
+ If Format is NULL, then ASSERT().
+ If Format is not aligned on a 16-bit boundary, then ASSERT().
+ If gST->StdErr is NULL, then ASSERT().
+
+ @param Format A Null-terminated Unicode format string.
+ @param ... Variable argument list whose contents are accessed based
+ on the format string specified by Format.
+
+ @return The number of Unicode characters printed to StdErr.
+
+**/
+UINTN
+EFIAPI
+ErrorPrint (
+ IN CONST CHAR16 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN Return;
+
+ VA_START (Marker, Format);
+
+ Return = InternalPrint( Format, gST->StdErr, Marker);
+
+ VA_END (Marker);
+
+ return Return;
+}
+
+
+/**
+ Internal function which prints a formatted ASCII string to the console output device
+ specified by Console
+
+ This function prints a formatted ASCII string to the console output device
+ specified by Console and returns the number of ASCII characters that printed
+ to it. If the length of the formatted ASCII string is greater than PcdUefiLibMaxPrintBufferSize,
+ then only the first PcdUefiLibMaxPrintBufferSize characters are sent to Console.
+
+ If Format is NULL, then ASSERT().
+
+ @param Format A Null-terminated ASCII format string.
+ @param Console The output console.
+ @param Marker VA_LIST marker for the variable argument list.
+
+ @return The number of Unicode characters in the produced
+ output buffer not including the Null-terminator.
+
+**/
+UINTN
+AsciiInternalPrint (
+ IN CONST CHAR8 *Format,
+ IN EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console,
+ IN VA_LIST Marker
+ )
+{
+ EFI_STATUS Status;
+ UINTN Return;
+ CHAR16 *Buffer;
+ UINTN BufferSize;
+
+ ASSERT (Format != NULL);
+ ASSERT (Console != NULL);
+
+ BufferSize = (PcdGet32 (PcdUefiLibMaxPrintBufferSize) + 1) * sizeof (CHAR16);
+
+ Buffer = (CHAR16 *) AllocatePool(BufferSize);
+ ASSERT (Buffer != NULL);
+
+ Return = UnicodeVSPrintAsciiFormat (Buffer, BufferSize, Format, Marker);
+
+ if (Console != NULL) {
+ //
+ // To be extra safe make sure Console has been initialized
+ //
+ Status = Console->OutputString (Console, Buffer);
+ if (EFI_ERROR (Status)) {
+ Return = 0;
+ }
+ }
+
+ FreePool (Buffer);
+
+ return Return;
+}
+
+/**
+ Prints a formatted ASCII string to the console output device specified by
+ ConOut defined in the EFI_SYSTEM_TABLE.
+
+ This function prints a formatted ASCII string to the console output device
+ specified by ConOut in EFI_SYSTEM_TABLE and returns the number of ASCII
+ characters that printed to ConOut. If the length of the formatted ASCII
+ string is greater than PcdUefiLibMaxPrintBufferSize, then only the first
+ PcdUefiLibMaxPrintBufferSize characters are sent to ConOut.
+ If Format is NULL, then ASSERT().
+ If gST->ConOut is NULL, then ASSERT().
+
+ @param Format A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based
+ on the format string specified by Format.
+
+ @return The number of ASCII characters printed to ConOut.
+
+**/
+UINTN
+EFIAPI
+AsciiPrint (
+ IN CONST CHAR8 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN Return;
+ ASSERT (Format != NULL);
+
+ VA_START (Marker, Format);
+
+ Return = AsciiInternalPrint( Format, gST->ConOut, Marker);
+
+ VA_END (Marker);
+
+ return Return;
+}
+
+/**
+ Prints a formatted ASCII string to the console output device specified by
+ StdErr defined in the EFI_SYSTEM_TABLE.
+
+ This function prints a formatted ASCII string to the console output device
+ specified by StdErr in EFI_SYSTEM_TABLE and returns the number of ASCII
+ characters that printed to StdErr. If the length of the formatted ASCII
+ string is greater than PcdUefiLibMaxPrintBufferSize, then only the first
+ PcdUefiLibMaxPrintBufferSize characters are sent to StdErr.
+ If Format is NULL, then ASSERT().
+ If gST->StdErr is NULL, then ASSERT().
+
+ @param Format A Null-terminated ASCII format string.
+ @param ... Variable argument list whose contents are accessed based
+ on the format string specified by Format.
+
+ @return The number of ASCII characters printed to ConErr.
+
+**/
+UINTN
+EFIAPI
+AsciiErrorPrint (
+ IN CONST CHAR8 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ UINTN Return;
+
+ ASSERT (Format != NULL);
+
+ VA_START (Marker, Format);
+
+ Return = AsciiInternalPrint( Format, gST->StdErr, Marker);
+
+ VA_END (Marker);
+
+ return Return;
+}
+
+/**
+ Internal function to print a formatted Unicode string to a graphics console device specified by
+ ConsoleOutputHandle defined in the EFI_SYSTEM_TABLE at the given (X,Y) coordinates.
+
+ This function prints a formatted Unicode string to the graphics console device
+ specified by ConsoleOutputHandle in EFI_SYSTEM_TABLE and returns the number of
+ Unicode characters printed. The EFI_HII_FONT_PROTOCOL is used to convert the
+ string to a bitmap using the glyphs registered with the
+ HII database. No wrapping is performed, so any portions of the string the fall
+ outside the active display region will not be displayed.
+
+ If a graphics console device is not associated with the ConsoleOutputHandle
+ defined in the EFI_SYSTEM_TABLE then no string is printed, and 0 is returned.
+ If the EFI_HII_FONT_PROTOCOL is not present in the handle database, then no
+ string is printed, and 0 is returned.
+
+ @param PointX An X coordinate to print the string.
+ @param PointY A Y coordinate to print the string.
+ @param Foreground The foreground color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the foreground color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param Background The background color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the background color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param Buffer A Null-terminated Unicode formatted string.
+ @param PrintNum The number of Unicode formatted string to be printed.
+
+ @return The number of Unicode Characters printed. Zero means no any character
+ displayed successfully.
+
+**/
+UINTN
+InternalPrintGraphic (
+ IN UINTN PointX,
+ IN UINTN PointY,
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Foreground,
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *Background,
+ IN CHAR16 *Buffer,
+ IN UINTN PrintNum
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HorizontalResolution;
+ UINT32 VerticalResolution;
+ UINT32 ColorDepth;
+ UINT32 RefreshRate;
+ EFI_HII_FONT_PROTOCOL *HiiFont;
+ EFI_IMAGE_OUTPUT *Blt;
+ EFI_FONT_DISPLAY_INFO FontInfo;
+ EFI_HII_ROW_INFO *RowInfoArray;
+ UINTN RowInfoArraySize;
+ EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput;
+ EFI_UGA_DRAW_PROTOCOL *UgaDraw;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Sto;
+ EFI_HANDLE ConsoleHandle;
+ UINTN Width;
+ UINTN Height;
+ UINTN Delta;
+
+ HorizontalResolution = 0;
+ VerticalResolution = 0;
+ Blt = NULL;
+ RowInfoArray = NULL;
+
+ ConsoleHandle = gST->ConsoleOutHandle;
+
+ ASSERT( ConsoleHandle != NULL);
+
+ Status = gBS->HandleProtocol (
+ ConsoleHandle,
+ &gEfiGraphicsOutputProtocolGuid,
+ (VOID **) &GraphicsOutput
+ );
+
+ UgaDraw = NULL;
+ if (EFI_ERROR (Status) && FeaturePcdGet (PcdUgaConsumeSupport)) {
+ //
+ // If no GOP available, try to open UGA Draw protocol if supported.
+ //
+ GraphicsOutput = NULL;
+
+ Status = gBS->HandleProtocol (
+ ConsoleHandle,
+ &gEfiUgaDrawProtocolGuid,
+ (VOID **) &UgaDraw
+ );
+ }
+ if (EFI_ERROR (Status)) {
+ goto Error;
+ }
+
+ Status = gBS->HandleProtocol (
+ ConsoleHandle,
+ &gEfiSimpleTextOutProtocolGuid,
+ (VOID **) &Sto
+ );
+
+ if (EFI_ERROR (Status)) {
+ goto Error;
+ }
+
+ if (GraphicsOutput != NULL) {
+ HorizontalResolution = GraphicsOutput->Mode->Info->HorizontalResolution;
+ VerticalResolution = GraphicsOutput->Mode->Info->VerticalResolution;
+ } else if (UgaDraw != NULL && FeaturePcdGet (PcdUgaConsumeSupport)) {
+ UgaDraw->GetMode (UgaDraw, &HorizontalResolution, &VerticalResolution, &ColorDepth, &RefreshRate);
+ } else {
+ goto Error;
+ }
+
+ ASSERT ((HorizontalResolution != 0) && (VerticalResolution !=0));
+
+ Status = gBS->LocateProtocol (&gEfiHiiFontProtocolGuid, NULL, (VOID **) &HiiFont);
+ if (EFI_ERROR (Status)) {
+ goto Error;
+ }
+
+ Blt = (EFI_IMAGE_OUTPUT *) AllocateZeroPool (sizeof (EFI_IMAGE_OUTPUT));
+ ASSERT (Blt != NULL);
+
+ Blt->Width = (UINT16) (HorizontalResolution);
+ Blt->Height = (UINT16) (VerticalResolution);
+
+ ZeroMem (&FontInfo, sizeof (EFI_FONT_DISPLAY_INFO));
+
+ if (Foreground != NULL) {
+ CopyMem (&FontInfo.ForegroundColor, Foreground, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL));
+ } else {
+ CopyMem (
+ &FontInfo.ForegroundColor,
+ &mEfiColors[Sto->Mode->Attribute & 0x0f],
+ sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL)
+ );
+ }
+ if (Background != NULL) {
+ CopyMem (&FontInfo.BackgroundColor, Background, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL));
+ } else {
+ CopyMem (
+ &FontInfo.BackgroundColor,
+ &mEfiColors[Sto->Mode->Attribute >> 4],
+ sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL)
+ );
+ }
+
+ if (GraphicsOutput != NULL) {
+ Blt->Image.Screen = GraphicsOutput;
+
+ Status = HiiFont->StringToImage (
+ HiiFont,
+ EFI_HII_IGNORE_IF_NO_GLYPH | EFI_HII_OUT_FLAG_CLIP |
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_X | EFI_HII_OUT_FLAG_CLIP_CLEAN_Y |
+ EFI_HII_IGNORE_LINE_BREAK | EFI_HII_DIRECT_TO_SCREEN,
+ Buffer,
+ &FontInfo,
+ &Blt,
+ PointX,
+ PointY,
+ &RowInfoArray,
+ &RowInfoArraySize,
+ NULL
+ );
+ if (EFI_ERROR (Status)) {
+ goto Error;
+ }
+
+ } else if (FeaturePcdGet (PcdUgaConsumeSupport)) {
+ ASSERT (UgaDraw!= NULL);
+
+ //
+ // Ensure Width * Height * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL) doesn't overflow.
+ //
+ if (Blt->Width > DivU64x32 (MAX_UINTN, Blt->Height * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL))) {
+ goto Error;
+ }
+
+ Blt->Image.Bitmap = AllocateZeroPool ((UINT32) Blt->Width * Blt->Height * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL));
+ ASSERT (Blt->Image.Bitmap != NULL);
+
+ //
+ // StringToImage only support blt'ing image to device using GOP protocol. If GOP is not supported in this platform,
+ // we ask StringToImage to print the string to blt buffer, then blt to device using UgaDraw.
+ //
+ Status = HiiFont->StringToImage (
+ HiiFont,
+ EFI_HII_IGNORE_IF_NO_GLYPH | EFI_HII_OUT_FLAG_CLIP |
+ EFI_HII_OUT_FLAG_CLIP_CLEAN_X | EFI_HII_OUT_FLAG_CLIP_CLEAN_Y |
+ EFI_HII_IGNORE_LINE_BREAK,
+ Buffer,
+ &FontInfo,
+ &Blt,
+ PointX,
+ PointY,
+ &RowInfoArray,
+ &RowInfoArraySize,
+ NULL
+ );
+
+ if (!EFI_ERROR (Status)) {
+ ASSERT (RowInfoArray != NULL);
+ //
+ // Explicit Line break characters are ignored, so the updated parameter RowInfoArraySize by StringToImage will
+ // always be 1 or 0 (if there is no valid Unicode Char can be printed). ASSERT here to make sure.
+ //
+ ASSERT (RowInfoArraySize <= 1);
+
+ if (RowInfoArraySize != 0) {
+ Width = RowInfoArray[0].LineWidth;
+ Height = RowInfoArray[0].LineHeight;
+ Delta = Blt->Width * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
+ } else {
+ Width = 0;
+ Height = 0;
+ Delta = 0;
+ }
+ Status = UgaDraw->Blt (
+ UgaDraw,
+ (EFI_UGA_PIXEL *) Blt->Image.Bitmap,
+ EfiUgaBltBufferToVideo,
+ PointX,
+ PointY,
+ PointX,
+ PointY,
+ Width,
+ Height,
+ Delta
+ );
+ } else {
+ goto Error;
+ }
+ FreePool (Blt->Image.Bitmap);
+ } else {
+ goto Error;
+ }
+ //
+ // Calculate the number of actual printed characters
+ //
+ if (RowInfoArraySize != 0) {
+ PrintNum = RowInfoArray[0].EndIndex - RowInfoArray[0].StartIndex + 1;
+ } else {
+ PrintNum = 0;
+ }
+
+ FreePool (RowInfoArray);
+ FreePool (Blt);
+ return PrintNum;
+
+Error:
+ if (Blt != NULL) {
+ FreePool (Blt);
+ }
+ return 0;
+}
+
+/**
+ Prints a formatted Unicode string to a graphics console device specified by
+ ConsoleOutputHandle defined in the EFI_SYSTEM_TABLE at the given (X,Y) coordinates.
+
+ This function prints a formatted Unicode string to the graphics console device
+ specified by ConsoleOutputHandle in EFI_SYSTEM_TABLE and returns the number of
+ Unicode characters displayed, not including partial characters that may be clipped
+ by the right edge of the display. If the length of the formatted Unicode string is
+ greater than PcdUefiLibMaxPrintBufferSize, then at most the first
+ PcdUefiLibMaxPrintBufferSize characters are printed.The EFI_HII_FONT_PROTOCOL
+ StringToImage() service is used to convert the string to a bitmap using the glyphs
+ registered with the HII database. No wrapping is performed, so any portions of the
+ string the fall outside the active display region will not be displayed. Please see
+ Section 27.2.6 of the UEFI Specification for a description of the supported string
+ format including the set of control codes supported by the StringToImage() service.
+
+ If a graphics console device is not associated with the ConsoleOutputHandle
+ defined in the EFI_SYSTEM_TABLE then no string is printed, and 0 is returned.
+ If the EFI_HII_FONT_PROTOCOL is not present in the handle database, then no
+ string is printed, and 0 is returned.
+ If Format is NULL, then ASSERT().
+ If Format is not aligned on a 16-bit boundary, then ASSERT().
+ If gST->ConsoleOutputHandle is NULL, then ASSERT().
+
+ @param PointX An X coordinate to print the string.
+ @param PointY A Y coordinate to print the string.
+ @param ForeGround The foreground color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the foreground color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param BackGround The background color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the background color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param Format A Null-terminated Unicode format string. See Print Library
+ for the supported format string syntax.
+ @param ... A Variable argument list whose contents are accessed based on
+ the format string specified by Format.
+
+ @return The number of Unicode characters printed.
+
+**/
+UINTN
+EFIAPI
+PrintXY (
+ IN UINTN PointX,
+ IN UINTN PointY,
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *ForeGround, OPTIONAL
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BackGround, OPTIONAL
+ IN CONST CHAR16 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ CHAR16 *Buffer;
+ UINTN BufferSize;
+ UINTN PrintNum;
+ UINTN ReturnNum;
+
+ ASSERT (Format != NULL);
+ ASSERT (((UINTN) Format & BIT0) == 0);
+
+ VA_START (Marker, Format);
+
+ BufferSize = (PcdGet32 (PcdUefiLibMaxPrintBufferSize) + 1) * sizeof (CHAR16);
+
+ Buffer = (CHAR16 *) AllocatePool (BufferSize);
+ ASSERT (Buffer != NULL);
+
+ PrintNum = UnicodeVSPrint (Buffer, BufferSize, Format, Marker);
+
+ VA_END (Marker);
+
+ ReturnNum = InternalPrintGraphic (PointX, PointY, ForeGround, BackGround, Buffer, PrintNum);
+
+ FreePool (Buffer);
+
+ return ReturnNum;
+}
+
+/**
+ Prints a formatted ASCII string to a graphics console device specified by
+ ConsoleOutputHandle defined in the EFI_SYSTEM_TABLE at the given (X,Y) coordinates.
+
+ This function prints a formatted ASCII string to the graphics console device
+ specified by ConsoleOutputHandle in EFI_SYSTEM_TABLE and returns the number of
+ ASCII characters displayed, not including partial characters that may be clipped
+ by the right edge of the display. If the length of the formatted ASCII string is
+ greater than PcdUefiLibMaxPrintBufferSize, then at most the first
+ PcdUefiLibMaxPrintBufferSize characters are printed.The EFI_HII_FONT_PROTOCOL
+ StringToImage() service is used to convert the string to a bitmap using the glyphs
+ registered with the HII database. No wrapping is performed, so any portions of the
+ string the fall outside the active display region will not be displayed. Please see
+ Section 27.2.6 of the UEFI Specification for a description of the supported string
+ format including the set of control codes supported by the StringToImage() service.
+
+ If a graphics console device is not associated with the ConsoleOutputHandle
+ defined in the EFI_SYSTEM_TABLE then no string is printed, and 0 is returned.
+ If the EFI_HII_FONT_PROTOCOL is not present in the handle database, then no
+ string is printed, and 0 is returned.
+ If Format is NULL, then ASSERT().
+ If gST->ConsoleOutputHandle is NULL, then ASSERT().
+
+ @param PointX An X coordinate to print the string.
+ @param PointY A Y coordinate to print the string.
+ @param ForeGround The foreground color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the foreground color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param BackGround The background color of the string being printed. This is
+ an optional parameter that may be NULL. If it is NULL,
+ then the background color of the current ConOut device
+ in the EFI_SYSTEM_TABLE is used.
+ @param Format A Null-terminated ASCII format string. See Print Library
+ for the supported format string syntax.
+ @param ... Variable argument list whose contents are accessed based on
+ the format string specified by Format.
+
+ @return The number of ASCII characters printed.
+
+**/
+UINTN
+EFIAPI
+AsciiPrintXY (
+ IN UINTN PointX,
+ IN UINTN PointY,
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *ForeGround, OPTIONAL
+ IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL *BackGround, OPTIONAL
+ IN CONST CHAR8 *Format,
+ ...
+ )
+{
+ VA_LIST Marker;
+ CHAR16 *Buffer;
+ UINTN BufferSize;
+ UINTN PrintNum;
+ UINTN ReturnNum;
+
+ ASSERT (Format != NULL);
+
+ VA_START (Marker, Format);
+
+ BufferSize = (PcdGet32 (PcdUefiLibMaxPrintBufferSize) + 1) * sizeof (CHAR16);
+
+ Buffer = (CHAR16 *) AllocatePool (BufferSize);
+ ASSERT (Buffer != NULL);
+
+ PrintNum = UnicodeSPrintAsciiFormat (Buffer, BufferSize, Format, Marker);
+
+ VA_END (Marker);
+
+ ReturnNum = InternalPrintGraphic (PointX, PointY, ForeGround, BackGround, Buffer, PrintNum);
+
+ FreePool (Buffer);
+
+ return ReturnNum;
+}
+
+/**
+ Appends a formatted Unicode string to a Null-terminated Unicode string
+
+ This function appends a formatted Unicode string to the Null-terminated
+ Unicode string specified by String. String is optional and may be NULL.
+ Storage for the formatted Unicode string returned is allocated using
+ AllocatePool(). The pointer to the appended string is returned. The caller
+ is responsible for freeing the returned string.
+
+ If String is not NULL and not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is NULL, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param[in] String A Null-terminated Unicode string.
+ @param[in] FormatString A Null-terminated Unicode format string.
+ @param[in] Marker VA_LIST marker for the variable argument list.
+
+ @retval NULL There was not enough available memory.
+ @return Null-terminated Unicode string is that is the formatted
+ string appended to String.
+**/
+CHAR16*
+EFIAPI
+CatVSPrint (
+ IN CHAR16 *String, OPTIONAL
+ IN CONST CHAR16 *FormatString,
+ IN VA_LIST Marker
+ )
+{
+ UINTN CharactersRequired;
+ UINTN SizeRequired;
+ CHAR16 *BufferToReturn;
+ VA_LIST ExtraMarker;
+
+ VA_COPY (ExtraMarker, Marker);
+ CharactersRequired = SPrintLength(FormatString, ExtraMarker);
+ VA_END (ExtraMarker);
+
+ if (String != NULL) {
+ SizeRequired = StrSize(String) + (CharactersRequired * sizeof(CHAR16));
+ } else {
+ SizeRequired = sizeof(CHAR16) + (CharactersRequired * sizeof(CHAR16));
+ }
+
+ BufferToReturn = AllocatePool(SizeRequired);
+
+ if (BufferToReturn == NULL) {
+ return NULL;
+ } else {
+ BufferToReturn[0] = L'\0';
+ }
+
+ if (String != NULL) {
+ StrCpyS(BufferToReturn, SizeRequired / sizeof(CHAR16), String);
+ }
+
+ UnicodeVSPrint(BufferToReturn + StrLen(BufferToReturn), (CharactersRequired+1) * sizeof(CHAR16), FormatString, Marker);
+
+ ASSERT(StrSize(BufferToReturn)==SizeRequired);
+
+ return (BufferToReturn);
+}
+
+/**
+ Appends a formatted Unicode string to a Null-terminated Unicode string
+
+ This function appends a formatted Unicode string to the Null-terminated
+ Unicode string specified by String. String is optional and may be NULL.
+ Storage for the formatted Unicode string returned is allocated using
+ AllocatePool(). The pointer to the appended string is returned. The caller
+ is responsible for freeing the returned string.
+
+ If String is not NULL and not aligned on a 16-bit boundary, then ASSERT().
+ If FormatString is NULL, then ASSERT().
+ If FormatString is not aligned on a 16-bit boundary, then ASSERT().
+
+ @param[in] String A Null-terminated Unicode string.
+ @param[in] FormatString A Null-terminated Unicode format string.
+ @param[in] ... The variable argument list whose contents are
+ accessed based on the format string specified by
+ FormatString.
+
+ @retval NULL There was not enough available memory.
+ @return Null-terminated Unicode string is that is the formatted
+ string appended to String.
+**/
+CHAR16 *
+EFIAPI
+CatSPrint (
+ IN CHAR16 *String, OPTIONAL
+ IN CONST CHAR16 *FormatString,
+ ...
+ )
+{
+ VA_LIST Marker;
+ CHAR16 *NewString;
+
+ VA_START (Marker, FormatString);
+ NewString = CatVSPrint(String, FormatString, Marker);
+ VA_END (Marker);
+ return NewString;
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiNotTiano.c b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiNotTiano.c
new file mode 100644
index 0000000..5e32f4a
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiLib/UefiNotTiano.c
@@ -0,0 +1,330 @@
+/** @file
+ Library functions that abstract areas of conflict between framework and UEFI 2.0.
+
+ Help Port Framework code that has conflicts with UEFI 2.0 by hiding the
+ old conflicts with library functions and supporting implementations of the old
+ (EDK/EFI 1.10) and new (EDK II/UEFI 2.0) way. This module is a DXE driver as
+ it contains DXE enum extensions for EFI event services.
+
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+
+#include "UefiLibInternal.h"
+
+/**
+ Creates an EFI event in the Legacy Boot Event Group.
+
+ Prior to UEFI 2.0 this was done via a non blessed UEFI extensions and this library
+ abstracts the implementation mechanism of this event from the caller. This function
+ abstracts the creation of the Legacy Boot Event. The Framework moved from a proprietary
+ to UEFI 2.0 based mechanism. This library abstracts the caller from how this event
+ is created to prevent to code form having to change with the version of the
+ specification supported.
+ If LegacyBootEvent is NULL, then ASSERT().
+
+ @param LegacyBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex).
+
+ @retval EFI_SUCCESS Event was created.
+ @retval Other Event was not created.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiCreateEventLegacyBoot (
+ OUT EFI_EVENT *LegacyBootEvent
+ )
+{
+ return EfiCreateEventLegacyBootEx (
+ TPL_CALLBACK,
+ EfiEventEmptyFunction,
+ NULL,
+ LegacyBootEvent
+ );
+}
+
+/**
+ Create an EFI event in the Legacy Boot Event Group and allows
+ the caller to specify a notification function.
+
+ This function abstracts the creation of the Legacy Boot Event.
+ The Framework moved from a proprietary to UEFI 2.0 based mechanism.
+ This library abstracts the caller from how this event is created to prevent
+ to code form having to change with the version of the specification supported.
+ If LegacyBootEvent is NULL, then ASSERT().
+
+ @param NotifyTpl The task priority level of the event.
+ @param NotifyFunction The notification function to call when the event is signaled.
+ @param NotifyContext The content to pass to NotifyFunction when the event is signaled.
+ @param LegacyBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex).
+
+ @retval EFI_SUCCESS Event was created.
+ @retval Other Event was not created.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiCreateEventLegacyBootEx (
+ IN EFI_TPL NotifyTpl,
+ IN EFI_EVENT_NOTIFY NotifyFunction, OPTIONAL
+ IN VOID *NotifyContext, OPTIONAL
+ OUT EFI_EVENT *LegacyBootEvent
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT_NOTIFY WorkerNotifyFunction;
+
+ ASSERT (LegacyBootEvent != NULL);
+
+ if (gST->Hdr.Revision < EFI_2_00_SYSTEM_TABLE_REVISION) {
+ DEBUG ((EFI_D_ERROR, "EFI1.1 can't support LegacyBootEvent!"));
+ ASSERT (FALSE);
+
+ return EFI_UNSUPPORTED;
+ } else {
+ //
+ // For UEFI 2.0 and the future use an Event Group
+ //
+ if (NotifyFunction == NULL) {
+ //
+ // CreateEventEx will check NotifyFunction is NULL or not and return error.
+ // Use dummy routine for the case NotifyFunction is NULL.
+ //
+ WorkerNotifyFunction = EfiEventEmptyFunction;
+ } else {
+ WorkerNotifyFunction = NotifyFunction;
+ }
+ Status = gBS->CreateEventEx (
+ EVT_NOTIFY_SIGNAL,
+ NotifyTpl,
+ WorkerNotifyFunction,
+ NotifyContext,
+ &gEfiEventLegacyBootGuid,
+ LegacyBootEvent
+ );
+ }
+
+ return Status;
+}
+
+/**
+ Create an EFI event in the Ready To Boot Event Group.
+
+ Prior to UEFI 2.0 this was done via a non-standard UEFI extension, and this library
+ abstracts the implementation mechanism of this event from the caller.
+ This function abstracts the creation of the Ready to Boot Event. The Framework
+ moved from a proprietary to UEFI 2.0-based mechanism. This library abstracts
+ the caller from how this event is created to prevent the code form having to
+ change with the version of the specification supported.
+ If ReadyToBootEvent is NULL, then ASSERT().
+
+ @param ReadyToBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex).
+
+ @retval EFI_SUCCESS Event was created.
+ @retval Other Event was not created.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiCreateEventReadyToBoot (
+ OUT EFI_EVENT *ReadyToBootEvent
+ )
+{
+ return EfiCreateEventReadyToBootEx (
+ TPL_CALLBACK,
+ EfiEventEmptyFunction,
+ NULL,
+ ReadyToBootEvent
+ );
+}
+
+/**
+ Create an EFI event in the Ready To Boot Event Group and allows
+ the caller to specify a notification function.
+
+ This function abstracts the creation of the Ready to Boot Event.
+ The Framework moved from a proprietary to UEFI 2.0 based mechanism.
+ This library abstracts the caller from how this event is created to prevent
+ to code form having to change with the version of the specification supported.
+ If ReadyToBootEvent is NULL, then ASSERT().
+
+ @param NotifyTpl The task priority level of the event.
+ @param NotifyFunction The notification function to call when the event is signaled.
+ @param NotifyContext The content to pass to NotifyFunction when the event is signaled.
+ @param ReadyToBootEvent Returns the EFI event returned from gBS->CreateEvent(Ex).
+
+ @retval EFI_SUCCESS Event was created.
+ @retval Other Event was not created.
+
+**/
+EFI_STATUS
+EFIAPI
+EfiCreateEventReadyToBootEx (
+ IN EFI_TPL NotifyTpl,
+ IN EFI_EVENT_NOTIFY NotifyFunction, OPTIONAL
+ IN VOID *NotifyContext, OPTIONAL
+ OUT EFI_EVENT *ReadyToBootEvent
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT_NOTIFY WorkerNotifyFunction;
+
+ ASSERT (ReadyToBootEvent != NULL);
+
+ if (gST->Hdr.Revision < EFI_2_00_SYSTEM_TABLE_REVISION) {
+ DEBUG ((EFI_D_ERROR, "EFI1.1 can't support ReadyToBootEvent!"));
+ ASSERT (FALSE);
+
+ return EFI_UNSUPPORTED;
+ } else {
+ //
+ // For UEFI 2.0 and the future use an Event Group
+ //
+ if (NotifyFunction == NULL) {
+ //
+ // CreateEventEx will check NotifyFunction is NULL or not and return error.
+ // Use dummy routine for the case NotifyFunction is NULL.
+ //
+ WorkerNotifyFunction = EfiEventEmptyFunction;
+ } else {
+ WorkerNotifyFunction = NotifyFunction;
+ }
+ Status = gBS->CreateEventEx (
+ EVT_NOTIFY_SIGNAL,
+ NotifyTpl,
+ WorkerNotifyFunction,
+ NotifyContext,
+ &gEfiEventReadyToBootGuid,
+ ReadyToBootEvent
+ );
+ }
+
+ return Status;
+}
+
+
+/**
+ Create, Signal, and Close the Ready to Boot event using EfiSignalEventReadyToBoot().
+
+ This function abstracts the signaling of the Ready to Boot Event. The Framework moved
+ from a proprietary to UEFI 2.0 based mechanism. This library abstracts the caller
+ from how this event is created to prevent to code form having to change with the
+ version of the specification supported.
+
+**/
+VOID
+EFIAPI
+EfiSignalEventReadyToBoot (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT ReadyToBootEvent;
+
+ Status = EfiCreateEventReadyToBoot (&ReadyToBootEvent);
+ if (!EFI_ERROR (Status)) {
+ gBS->SignalEvent (ReadyToBootEvent);
+ gBS->CloseEvent (ReadyToBootEvent);
+ }
+}
+
+/**
+ Create, Signal, and Close the Ready to Boot event using EfiSignalEventLegacyBoot().
+
+ This function abstracts the signaling of the Legacy Boot Event. The Framework moved from
+ a proprietary to UEFI 2.0 based mechanism. This library abstracts the caller from how
+ this event is created to prevent to code form having to change with the version of the
+ specification supported.
+
+**/
+VOID
+EFIAPI
+EfiSignalEventLegacyBoot (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ EFI_EVENT LegacyBootEvent;
+
+ Status = EfiCreateEventLegacyBoot (&LegacyBootEvent);
+ if (!EFI_ERROR (Status)) {
+ gBS->SignalEvent (LegacyBootEvent);
+ gBS->CloseEvent (LegacyBootEvent);
+ }
+}
+
+
+/**
+ Check to see if the Firmware Volume (FV) Media Device Path is valid
+
+ The Framework FwVol Device Path changed to conform to the UEFI 2.0 specification.
+ This library function abstracts validating a device path node.
+ Check the MEDIA_FW_VOL_FILEPATH_DEVICE_PATH data structure to see if it's valid.
+ If it is valid, then return the GUID file name from the device path node. Otherwise,
+ return NULL. This device path changed in the DXE CIS version 0.92 in a non back ward
+ compatible way to not conflict with the UEFI 2.0 specification. This function abstracts
+ the differences from the caller.
+ If FvDevicePathNode is NULL, then ASSERT().
+
+ @param FvDevicePathNode The pointer to FV device path to check.
+
+ @retval NULL FvDevicePathNode is not valid.
+ @retval Other FvDevicePathNode is valid and pointer to NameGuid was returned.
+
+**/
+EFI_GUID *
+EFIAPI
+EfiGetNameGuidFromFwVolDevicePathNode (
+ IN CONST MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode
+ )
+{
+ ASSERT (FvDevicePathNode != NULL);
+
+ if (DevicePathType (&FvDevicePathNode->Header) == MEDIA_DEVICE_PATH &&
+ DevicePathSubType (&FvDevicePathNode->Header) == MEDIA_PIWG_FW_FILE_DP) {
+ return (EFI_GUID *) &FvDevicePathNode->FvFileName;
+ }
+
+ return NULL;
+}
+
+
+/**
+ Initialize a Firmware Volume (FV) Media Device Path node.
+
+ The Framework FwVol Device Path changed to conform to the UEFI 2.0 specification.
+ This library function abstracts initializing a device path node.
+ Initialize the MEDIA_FW_VOL_FILEPATH_DEVICE_PATH data structure. This device
+ path changed in the DXE CIS version 0.92 in a non back ward compatible way to
+ not conflict with the UEFI 2.0 specification. This function abstracts the
+ differences from the caller.
+ If FvDevicePathNode is NULL, then ASSERT().
+ If NameGuid is NULL, then ASSERT().
+
+ @param FvDevicePathNode The pointer to a FV device path node to initialize
+ @param NameGuid FV file name to use in FvDevicePathNode
+
+**/
+VOID
+EFIAPI
+EfiInitializeFwVolDevicepathNode (
+ IN OUT MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode,
+ IN CONST EFI_GUID *NameGuid
+ )
+{
+ ASSERT (FvDevicePathNode != NULL);
+ ASSERT (NameGuid != NULL);
+
+ //
+ // Use the new Device path that does not conflict with the UEFI
+ //
+ FvDevicePathNode->Header.Type = MEDIA_DEVICE_PATH;
+ FvDevicePathNode->Header.SubType = MEDIA_PIWG_FW_FILE_DP;
+ SetDevicePathNodeLength (&FvDevicePathNode->Header, sizeof (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH));
+
+ CopyGuid (&FvDevicePathNode->FvFileName, NameGuid);
+}
+
diff --git a/efi_memtest/memtest86+/efi/Include/src/UefiRuntimeServicesTableLib.c b/efi_memtest/memtest86+/efi/Include/src/UefiRuntimeServicesTableLib.c
new file mode 100644
index 0000000..e2e9193
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/Include/src/UefiRuntimeServicesTableLib.c
@@ -0,0 +1,43 @@
+/** @file
+ UEFI Runtime Services Table Library.
+
+ This library instance retrieve EFI_RUNTIME_SERVICES pointer from EFI system table
+ in library's constructor.
+
+ Copyright (c) 2006 - 2008, Intel Corporation. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Uefi.h>
+#include <Library/DebugLib.h>
+
+EFI_RUNTIME_SERVICES *gRT = NULL;
+
+/**
+ The constructor function caches the pointer of Runtime Services Table.
+
+ The constructor function caches the pointer of Runtime Services Table.
+ It will ASSERT() if the pointer of Runtime Services Table is NULL.
+ It will always return EFI_SUCCESS.
+
+ @param ImageHandle The firmware allocated handle for the EFI image.
+ @param SystemTable A pointer to the EFI System Table.
+
+ @retval EFI_SUCCESS The constructor always returns EFI_SUCCESS.
+
+**/
+EFI_STATUS
+EFIAPI
+UefiRuntimeServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ //
+ // Cache pointer to the EFI Runtime Services Table
+ //
+ gRT = SystemTable->RuntimeServices;
+ ASSERT (gRT != NULL);
+ return EFI_SUCCESS;
+}
diff --git a/efi_memtest/memtest86+/efi/display.c b/efi_memtest/memtest86+/efi/display.c
index 2700138..7ae3c2a 100644
--- a/efi_memtest/memtest86+/efi/display.c
+++ b/efi_memtest/memtest86+/efi/display.c
@@ -8,24 +8,20 @@
extern volatile short btflag;
extern EFI_SYSTEM_TABLE *gST;
-extern struct barrier_s *barr;
+extern struct barrier_s *barr;
#define CONSOLE_WIDTH 80
CHAR16 scroll_buffer[10][79];
int scroll_begin = 0;
-void clear_screen()
-{
+void clear_screen() {
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
Console->SetMode(Console, 2); // TODO set only if it's possible
Console->SetAttribute(Console, EFI_TEXT_ATTR(EFI_BLACK, EFI_CYAN));
Console->ClearScreen(Console);
-/*
- char msg[] = "Screen cleared efi\n";
- print_log(msg, sizeof(msg));*/
if (btflag) {
Console->SetCursorPosition(Console, 0, 1);
@@ -43,9 +39,9 @@ void clear_screen()
Console->SetCursorPosition(Console, 0, 0);
for (int i = 0; i < 10; i++) {
- for (int j = 0; j < 78; j++) {
- scroll_buffer[i][j] = ' ';
- }
+ for (int j = 0; j < 78; j++) {
+ scroll_buffer[i][j] = ' ';
+ }
scroll_buffer[i][78] = '\0';
}
@@ -54,19 +50,29 @@ void clear_screen()
int print_mainscreen() {
extern int num_cpus;
+ extern int l1_cache, l2_cache, l3_cache;
+ extern char *cpu_type_s;
+ extern ulong cpu_speed;
+ extern ulong speed_l1;
+ extern ulong speed_l2;
+ extern ulong speed_l3;
+ //extern ulong memspeed_end_high;
clear_screen();
-
+
+ /*
+ * Frame
+ */
cprint(5, 60, "| Time: 0:00:00");
cprint(1, COL_MID,"Pass %");
cprint(2, COL_MID,"Test %");
cprint(3, COL_MID,"Test #");
cprint(4, COL_MID,"Testing: ");
cprint(5, COL_MID,"Pattern: ");
- cprint(1, 0, "CLK: (32b Mode)");
- cprint(2, 0, "L1 Cache: Unknown ");
- cprint(3, 0, "L2 Cache: Unknown ");
- cprint(4, 0, "L3 Cache: None ");
+ cprint(1, 0, "CLK:");
+ cprint(2, 0, "L1 Cache:");
+ cprint(3, 0, "L2 Cache:");
+ cprint(4, 0, "L3 Cache:");
cprint(5, 0, "Memory : ");
cprint(6, 0, "------------------------------------------------------------------------------");
cprint(7, 0, "Core#:");
@@ -80,7 +86,51 @@ int print_mainscreen() {
for(int i=0; i < 6; i++) {
cprint(i, COL_MID-2, "| ");
}
-
+
+ /*
+ * specific information
+ */
+ cprint(0, COL_MID, cpu_type_s);
+
+ // cpu and memory speed
+ int off = 4;
+ if (cpu_speed < 999499 + 50) {
+ cprint(1, off, " . MHz");
+ dprint(1, off+1, cpu_speed/1000, 3, 1);
+ dprint(1, off+5, (cpu_speed/100)%10, 1, 0);
+ } else {
+ cprint(1, off, " MHz");
+ dprint(1, off, cpu_speed/1000, 5, 0);
+ }
+
+ if (speed_l1) {
+ cprint(2, 16, " MB/s");
+ dprint(2, 16, speed_l1, 6, 0);
+ }
+
+ if (speed_l2) {
+ cprint(3, 16, " MB/s");
+ dprint(3, 16, speed_l2, 6, 0);
+ }
+
+ if (speed_l3) {
+ cprint(4, 16, " MB/s");
+ dprint(4, 16, speed_l3, 6, 0);
+ }
+
+ // TODO it just prints zeros. hprint(11,40,memspeed_end_high);
+
+ // Print out cache information
+ cprint(2, 0, "L1 Cache: K ");
+ dprint(2, 11, l1_cache, 3, 0);
+
+ cprint(3, 0, "L2 Cache: K ");
+ dprint(3, 10, l2_cache, 4, 0);
+
+
+ cprint(4, 0, "L3 Cache: K ");
+ aprint(4, 10, l3_cache/4);
+ //dprint(4, 10, l3_cache, 4, 0);
footer();
@@ -99,6 +149,9 @@ int print_mainscreen() {
cprint(LINE_RAM,9, "Running...");
}
+
+
+
/*
* Now follow the prints from common_err()
*/
@@ -117,24 +170,24 @@ int print_mainscreen() {
break;
case PRINTMODE_ADDRESSES:
- if (vv->erri.hdr_flag == 0) {
+ if (vv->erri.hdr_flag == 0) {
cprint(LINE_HEADER, 0,
"Tst Pass Failing Address Good Bad Err-Bits Count CPU");
cprint(LINE_HEADER+1, 0,
"--- ---- ----------------------- -------- -------- -------- ----- ----");
}
- break;
+ break;
case PRINTMODE_PATTERNS:
- break;
+ break;
case PRINTMODE_NONE:
- break;
+ break;
}
- return 0;
+ return 0;
}
// TODO UEFI functions
@@ -142,6 +195,7 @@ void getChar16FromInt(CHAR16* buffer, int num) {
int length = 0;
int tmp = num;
+
while(tmp > 10) {
tmp = tmp / 10;
Print(L"HJK %d", 6);
@@ -151,10 +205,9 @@ void getChar16FromInt(CHAR16* buffer, int num) {
/* Boot trace function */
short tidx = 25;
-void btrace(int me, int line, char *msg, int wait, long v1, long v2) // TODO
-{
+void btrace(int me, int line, char *msg, int wait, long v1, long v2) {// TODO
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
int y, x;
@@ -165,9 +218,11 @@ void btrace(int me, int line, char *msg, int wait, long v1, long v2) // TODO
y = tidx%13;
x = tidx/13*40;
cplace(y+11, x+1, ' ');
+
if (++tidx > 25) {
tidx = 0;
}
+
y = tidx%13;
x = tidx/13*40;
@@ -175,13 +230,13 @@ void btrace(int me, int line, char *msg, int wait, long v1, long v2) // TODO
Console->OutputString(Console, L">\n");
CHAR16 *buff;
getChar16FromInt(buff, me);
- /* TODO Console->SetCursorPosition(Console, 2, 11);
+ /* TODO Console->SetCursorPosition(Console, 2, 11);
CHAR16 num[8];
itoa(num, me);
Console->OutputString(Console, num);*/
//dprint(y+11, x+2, me, 2, 0);
//dprint(y+11, x+5, line, 4, 0);
- /* Console->SetCursorPosition(Console, 10, 11);
+ /* Console->SetCursorPosition(Console, 10, 11);
Console->OutputString(Console, msg);
cprint(y+11, x+10, msg);*/
//hprint(y+11, x+22, v1);
@@ -194,10 +249,10 @@ void btrace(int me, int line, char *msg, int wait, long v1, long v2) // TODO
void add_scroll_line(int x, int y, const char *text) {
- for (int i = 0; text[i]; ++i)
- {
- scroll_buffer[(scroll_begin + y)%10][x + i] = text[i];
- }
+
+ for (int i = 0; text[i]; ++i) {
+ scroll_buffer[(scroll_begin + y)%10][x + i] = text[i];
+ }
}
/*
@@ -206,7 +261,7 @@ void add_scroll_line(int x, int y, const char *text) {
void cprint(int y, int x, const char *text)
{
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
/* register int i;
char *dptr;
@@ -219,6 +274,7 @@ void cprint(int y, int x, const char *text)
// tty_print_line(y, x, text);
CHAR16 output_text[CONSOLE_WIDTH - 1]; // TODO think about the size
int i;
+
for (i = 0; text[i]; i++) {
output_text[i] = text[i];
}
@@ -227,10 +283,10 @@ void cprint(int y, int x, const char *text)
output_text[i] = '\0';
Console->SetCursorPosition(Console, x, y);
Console->OutputString(Console, output_text);
+
if (y <= 23 && y>= 14) {
- add_scroll_line(x, (y - 14), text);
+ add_scroll_line(x, (y - 14), text);
}
-
}
/*
@@ -239,12 +295,14 @@ void cprint(int y, int x, const char *text)
void trace_init(const char *text)
{
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
CHAR16 output_text[CONSOLE_WIDTH - 1]; // TODO think about the size
int i;
+
for (i = 0; text[i]; i++) {
output_text[i] = text[i];
+
if(i == CONSOLE_WIDTH) break;
}
@@ -254,166 +312,53 @@ void trace_init(const char *text)
INT32 row = Console->Mode->CursorRow;
Console->SetCursorPosition(Console, 0, row + 1);
Console->OutputString(Console, output_text);
-
-
}
-/*UINT32 *ScreenBuffer = NULL;
-UINTN bufferSize = 0;
-UINT32 *FrameBuffer = NULL;
-
-void load_screenshot() {
- clear_screen();
- for (int i = 0; i < bufferSize; i++) {
- FrameBuffer[i] = ScreenBuffer[i];
- }
- gST->BootServices->FreePool((VOID *)&ScreenBuffer);
-
-}*/
-
-
-/*int make_screenshot() {
-
- clear_screen();
-
- EFI_STATUS Status;
- //char *Image; // TODO
- //UINTN Index;
-
- EFI_GUID EfiGraphicsOutputProtocolGuid= EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
- EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput = NULL;
-
- static BOOLEAN mHasGraphics = FALSE;
- static UINTN mScreenWidth = 800;
- static UINTN mScreenHeight = 600;
-
- Status = gST->BootServices->LocateProtocol (&EfiGraphicsOutputProtocolGuid, NULL, (VOID**)&GraphicsOutput);
- if (Status != EFI_SUCCESS) {
- Print(L"GraphicsOutput not support!\n");
- return 1;
- } else {
- Print(L"Found at least one Graphics Output Protocol\n");
- }
-
- EFI_GUID **ProtocolGuidArray;
- UINTN BufferCount;
-
- Status = gST->BootServices->ProtocolsPerHandle(gST->ConsoleOutHandle, &ProtocolGuidArray, &BufferCount);
- if (Status != EFI_SUCCESS) {
- Print(L"ProtocolsPerHandle fail!\n");
- return 1;
- } else {
- Print(L"Found %d Protocols\n", BufferCount);
- for (UINTN ProtocolIndex = 0; ProtocolIndex < BufferCount; ProtocolIndex++) {
- EFI_GUID *guid = ProtocolGuidArray[ProtocolIndex];
- Print(L"GUID: %x-%x-%x-%x-%x-%x-%x-%x-%x-%x-%x\n",
- guid->Data1, guid->Data2, guid->Data3,
- guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3],
- guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7]);
- }
-
- }
-
-
- EFI_HANDLE* handleBuffer = NULL;
- UINTN handleCount = 0;
- Status = gST->BootServices->LocateHandleBuffer(ByProtocol,
- &EfiGraphicsOutputProtocolGuid,
- NULL,
- &handleCount,
- &handleBuffer
- );
- Print(L"Handles for Graphics Protocol: %d\n", handleCount);
-
- EFI_GRAPHICS_OUTPUT_PROTOCOL *go = (EFI_GRAPHICS_OUTPUT_PROTOCOL *) GraphicsOutput;
- EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE *mode = go->Mode;
- UINT32 MaxMode = mode-> MaxMode;
- UINT32 Mode = mode-> Mode;
- UINTN SizeOfInfo = mode->SizeOfInfo;
- EFI_PHYSICAL_ADDRESS FrameBufferBase = mode->FrameBufferBase;
- UINTN FrameBufferSize = mode->FrameBufferSize;
-
- Print(L"MaxMode %d\n", MaxMode);
- Print(L"Mode %d\n", Mode);
- Print(L"SizeOfInfo %d\n", SizeOfInfo);
- Print(L"Physical Address: %x\n", FrameBufferBase);
- Print(L"FrameBufferSize: %d\n", FrameBufferSize);
-
- EFI_GRAPHICS_OUTPUT_MODE_INFORMATION *Info = mode->Info;
-
- UINT32 Version = Info->Version;
- UINT32 HorizontalResolution = Info->HorizontalResolution;
- UINT32 VerticalResolution = Info-> VerticalResolution;
- EFI_GRAPHICS_PIXEL_FORMAT PixelFormat = Info->PixelFormat;
- //EFI_PIXEL_BITMASK PixelInformation = Info->PixelInformation;
- UINT32 PixelsPerScanLine = Info->PixelsPerScanLine;
-
- Print(L"Version %d\n", Version);
- Print(L"HorizontalResolution %d\n", HorizontalResolution);
- Print(L"VerticalResolution %d\n", VerticalResolution);
- Print(L"PixelsPerScanLine %d\n", PixelsPerScanLine);
- Print(L"PixelFormat %d\n", PixelFormat);
-
- bufferSize = FrameBufferSize / 4; // because we use UINT32
- Status = gST->BootServices->AllocatePool(EfiLoaderData, (UINTN) bufferSize, (VOID *)&ScreenBuffer);
- Print(L"Status of AllocatePool: %d\n", Status);
- FrameBuffer = (UINT32*)FrameBufferBase;
- Print(L"ScreenBuffer Address: %x\n", ScreenBuffer);
- Print(L"FrameBuffer Address: %x\n", FrameBuffer);
-
- //load_screenshot();
- while(1);
- return EFI_SUCCESS;
-}*/
-
void print_popup() {
-EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
-
- Console->SetAttribute(Console, EFI_TEXT_ATTR(EFI_BLACK, EFI_BLACK));
- Console->ClearScreen(Console);
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ Console->SetAttribute(Console, EFI_TEXT_ATTR(EFI_BLACK, EFI_BLACK));
+ Console->ClearScreen(Console);
- Console->SetAttribute(Console, EFI_TEXT_ATTR(EFI_BLACK, EFI_CYAN));
+ Console->SetAttribute(Console, EFI_TEXT_ATTR(EFI_BLACK, EFI_CYAN));
- for (int i = 0; i < POP_H; i++) {
- Console->SetCursorPosition(Console, POP_X, POP_Y + i);
- Console->OutputString(Console, L" "); // width: pop_w=34
- }
+ for (int i = 0; i < POP_H; i++) {
+ Console->SetCursorPosition(Console, POP_X, POP_Y + i);
+ Console->OutputString(Console, L" "); // width: pop_w=34
+ }
}
void clear_scroll_region() {
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
-
- int scroll_lines = 10;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
- for (int i = 0; i < scroll_lines; i++) {
- Console->SetCursorPosition(Console, 0, LINE_SCROLL + i);
- Console->OutputString(Console, L" ");
- }
+ int scroll_lines = 10;
- Console->SetCursorPosition(Console, 0, LINE_SCROLL - 1);
+ for (int i = 0; i < scroll_lines; i++) {
+ Console->SetCursorPosition(Console, 0, LINE_SCROLL + i);
+ Console->OutputString(Console, L" ");
+ }
+ Console->SetCursorPosition(Console, 0, LINE_SCROLL - 1);
}
void print_scroll_region() {
- EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
+ EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console = gST->ConOut;
- // clear_scroll_region?
+ // clear_scroll_region?
- for (int i = 0; i < 79; i++) {
- scroll_buffer[scroll_begin][i] = ' ';
- }
+ for (int i = 0; i < 79; i++) {
+ scroll_buffer[scroll_begin][i] = ' ';
+ }
scroll_buffer[scroll_begin][78] = '\0';
- scroll_begin++;
- scroll_begin %= 10;
+ scroll_begin++;
+ scroll_begin %= 10;
- for (int i = 0; i < 9; ++i)
- {
- Console->SetCursorPosition(Console, 0, LINE_SCROLL + i);
- Console->OutputString(Console, scroll_buffer[(scroll_begin + i) % 10]);
- }
+ for (int i = 0; i < 9; ++i) {
+ Console->SetCursorPosition(Console, 0, LINE_SCROLL + i);
+ Console->OutputString(Console, scroll_buffer[(scroll_begin + i) % 10]);
+ }
} \ No newline at end of file
diff --git a/efi_memtest/memtest86+/efi/dmi.c b/efi_memtest/memtest86+/efi/dmi.c
new file mode 100644
index 0000000..22e4d25
--- /dev/null
+++ b/efi_memtest/memtest86+/efi/dmi.c
@@ -0,0 +1,630 @@
+/* dmi.c using the DMI from SMBIOS to read information about the hardware's
+ * memory devices capabilities and where they are mapped into the address space
+ *
+ * Copyright (c) Joachim Deguara, AMD 2006
+ *
+ * Release under the GPL version 2
+ * ----------------------------------------------------
+ * Memtest86+ V4.00 - Added compliance with SMBIOS Spec V2.6.1
+ */
+
+#include "Uefi.h"
+#include "Library/UefiLib.h"
+
+#include "test.h"
+#include "stdint.h"
+
+#include "efi/Include/Efi_Defs_GUID.h"
+
+#include "logger.h"
+
+#define round_up(x,y) (((x) + (y) - 1) & ~((y)-1))
+#define round_down(x,y) ((x) & ~((y)-1))
+
+extern short logflag;
+extern short log_dmi;
+
+struct dmi_eps {
+ uint8_t anchor[4];
+ int8_t checksum;
+ uint8_t length;
+ uint8_t majorversion;
+ uint8_t minorversion;
+ uint16_t maxstructsize;
+ uint8_t revision;
+ uint8_t pad[5];
+ uint8_t intanchor[5];
+ int8_t intchecksum;
+ uint16_t tablelength;
+ uint32_t tableaddress;
+ uint16_t numstructs;
+ uint8_t SMBIOSrev;
+} __attribute__((packed));
+
+struct tstruct_header{
+ uint8_t type;
+ uint8_t length;
+ uint16_t handle;
+} __attribute__((packed));
+
+struct system_map {
+ struct tstruct_header header;
+ uint8_t manufacturer;
+ uint8_t productname;
+ uint8_t version;
+ uint8_t serialnumber;
+ uint8_t uuidbytes[16];
+ uint8_t wut;
+} __attribute__((packed));
+
+struct cpu_map {
+ struct tstruct_header header;
+ uint8_t cpu_socket;
+ uint8_t cpu_type;
+ uint8_t cpu_family;
+ uint8_t cpu_manufacturer;
+ uint32_t cpu_id;
+ uint8_t cpu_version;
+ uint8_t cpu_voltage;
+ uint16_t ext_clock;
+ uint16_t max_speed;
+ uint16_t cur_speed;
+ uint8_t cpu_status;
+ uint8_t cpu_upgrade;
+ uint16_t l1_handle;
+ uint16_t l2_handle;
+ uint16_t l3_handle;
+ uint8_t cpu_serial;
+ uint8_t cpu_asset_tag;
+ uint8_t cpu_part_number;
+ uint8_t core_count;
+ uint8_t core_enabled;
+ uint8_t thread_count;
+ uint16_t cpu_specs;
+ uint16_t cpu_family_2;
+} __attribute__((packed));
+
+struct mem_dev {
+ struct tstruct_header header;
+ uint16_t pma_handle;
+ uint16_t err_handle;
+ uint16_t tot_width;
+ uint16_t dat_width;
+ uint16_t size;
+ uint8_t form;
+ uint8_t set;
+ uint8_t dev_locator;
+ uint8_t bank_locator;
+ uint8_t type;
+ uint16_t typedetail;
+ uint16_t speed;
+ uint8_t manufacturer;
+ uint8_t serialnum;
+ uint8_t asset;
+ uint8_t partnum;
+ uint8_t attributes;
+ uint8_t ext_size;
+ uint8_t conf_ram_speed;
+ uint8_t min_voltage;
+ uint8_t max_votage;
+ uint8_t conf_voltage;
+} __attribute__((packed));
+
+struct md_map{
+ struct tstruct_header header;
+ uint32_t start;
+ uint32_t end;
+ uint16_t md_handle;
+ uint16_t mama_handle;
+ uint8_t row_pos;
+ uint8_t interl_pos;
+ uint8_t interl_depth;
+} __attribute__((packed));
+
+struct pma{
+ struct tstruct_header header;
+ uint8_t location;
+ uint8_t use;
+ uint8_t ecc;
+ uint32_t capacity;
+ uint16_t errhandle;
+ uint16_t numdevs;
+} __attribute__((packed));
+
+static char *form_factors[] = {
+ "?",
+ "Other", "Unknown", "SIMM", "SIP", "Chip", "DIP", "ZIP",
+ "Proprietary Card", "DIMM", "TSOP", "Row of chips", "RIMM",
+ "SODIMM", "SRIMM", "FB-DIMM", "Die"
+};
+
+
+static char *memory_types[] = {
+ "?",
+ "Other", "????", "DRAM", "EDRAM", "VRAM", "SRAM", "RAM",
+ "ROM", "FLASH", "EEPROM", "FEPROM", "EPROM", "CDRAM", "3DRAM",
+ "SDRAM", "SGRAM", "RDRAM", "DDR", "DDR2", "DDR2 FB", "RSVD",
+ "RSVD","RSVD","DDR3","FBD2", "DDR4", "LPDDR", "LPDDR2", "LPDDR3",
+ "LPDDR4", "LNVD", "HBM", "HBM2", "DDR5", "LPDDR5"
+};
+
+
+struct mem_dev * mem_devs[MAX_DMI_MEMDEVS];
+int mem_devs_count=0;
+struct md_map * md_maps[MAX_DMI_MEMDEVS];
+struct system_map * dmi_system_info;
+struct cpu_map * dmi_cpu_info;
+int md_maps_count=0;
+int dmi_err_cnts[MAX_DMI_MEMDEVS];
+short dmi_initialized=0;
+
+char * get_tstruct_string(struct tstruct_header *header, int n){
+
+ if (logflag) print_log("get_tstruct_string() started.", 29);
+
+ if(n<1) return 0;
+
+ char * a = (char *)header + header->length;
+
+ n--;
+
+ do{
+ if (!*a)
+ n--;
+ if (!n && *a)
+ return a;
+ a++;
+ }while (!(*a==0 && *(a-1)==0));
+
+ return 0;
+}
+
+BOOLEAN abc(EFI_GUID* sfspGuid, EFI_GUID* guid) {
+ if (guid->Data1 == sfspGuid->Data1 && guid->Data2 == sfspGuid->Data2 && guid->Data3 == sfspGuid->Data3
+ && guid->Data4[0] == sfspGuid->Data4[0] && guid->Data4[1] == sfspGuid->Data4[1]
+ && guid->Data4[2] == sfspGuid->Data4[2] && guid->Data4[3] == sfspGuid->Data4[3]
+ && guid->Data4[4] == sfspGuid->Data4[4] && guid->Data4[5] == sfspGuid->Data4[5]
+ && guid->Data4[6] == sfspGuid->Data4[6] && guid->Data4[7] == sfspGuid->Data4[7]) {
+
+ return TRUE;
+ }
+ return FALSE;
+}
+
+
+// TODO Add support for SMBIOS3 table
+int open_dmi(void) {
+
+ char *dmi, *dmi_start;
+ int found=0;
+ struct dmi_eps *eps;
+ char *table_start;
+ int tstruct_count=0;
+
+ if (logflag) print_log("open_dmi() started.", 19);
+
+ extern EFI_SYSTEM_TABLE *gST;
+ EFI_CONFIGURATION_TABLE *ct = gST->ConfigurationTable;
+ UINTN NumberOfTableEntries = gST->NumberOfTableEntries;
+
+ if (logflag && log_dmi) {
+ char log[45] = "open_dmi(): NumberOfTableEntries = ";
+ int length = 35;
+ int_to_charr(NumberOfTableEntries, log, &length);
+ print_log(log, length);
+ }
+
+ EFI_GUID acpi_20 = gEfiAcpi20TableGuid;
+ EFI_GUID acpi_10 = gEfiAcpi10TableGuid;
+ EFI_GUID smbios = gEfiSmbiosGuid;
+ EFI_GUID smbios3 = gEfiSmbios3Guid;
+
+ for (int i = 0; i < NumberOfTableEntries; i++) {
+
+ EFI_GUID guid = ct->VendorGuid;
+ /*
+ Print(L"GUID: %x-%x-%x-%x-%x-%x-%x-%x-%x-%x-%x",
+ guid.Data1, guid.Data2, guid.Data3,
+ guid.Data4[0], guid.Data4[1], guid.Data4[2], guid.Data4[3],
+ guid.Data4[4], guid.Data4[5], guid.Data4[6], guid.Data4[7]);*/
+
+ if (abc(&guid, &acpi_20)) {
+ if (logflag && log_dmi) print_log("EFI_ACPI_20_TABLE_GUID", 22);
+ } else if (abc(&guid, &smbios)) {
+ if (log_dmi) print_log("SMBIOS_TABLE_GUID", 17);
+ dmi = ct->VendorTable;
+ found = 1;
+ } else if (abc(&guid, &smbios3)) {
+ if (logflag && log_dmi) print_log("SMBIOS3_TABLE_GUID", 18);
+ } else if (abc(&guid, &acpi_10)) {
+ if (logflag && log_dmi) print_log("ACPI_10_TABLE_GUID", 18);
+ } else {
+ if (logflag && log_dmi) print_log("Unknown table-GUID.", 19);
+ }
+ ct++;
+ }
+
+ if (!found) {
+ if (logflag && log_dmi) print_log("open_dmi(): dmi not found", 25);
+ return -1;
+ }
+
+ dmi_start=dmi;
+ eps=(struct dmi_eps *)dmi;
+
+ //check checksum
+ int8_t checksum=0;
+ for (; dmi < dmi_start + eps->length; dmi++)
+ checksum += *dmi;
+ if (checksum){
+ return -1;
+ }
+
+ if (logflag && log_dmi) {
+ char log[25] = "majorversion = ";
+ int length = 15;
+ int_to_charr(eps->majorversion, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[25] = "minorversion = ";
+ int length = 15;
+ int_to_charr(eps->minorversion, log, &length);
+ print_log(log, length);
+ }
+
+ //we need at least revision 2.1 of SMBIOS
+ if ( eps->majorversion < 2 &&
+ eps->minorversion < 1){
+ return -1;
+ }
+
+ table_start=(char *)(uintptr_t)eps->tableaddress;
+ dmi=table_start;
+ //look at all structs
+ while(dmi < table_start + eps->tablelength){
+ struct tstruct_header *header = (struct tstruct_header *)dmi;
+
+ if (logflag && log_dmi) {
+ char log[24] = "header type = ";
+ int length = 14;
+ int_to_charr(header->type, log, &length);
+ print_log(log, length);
+ }
+
+ if (header->type == 17) {
+ mem_devs[mem_devs_count++] = (struct mem_dev *)dmi;
+ }
+ // Mem Dev Map
+ else if (header->type == 20) {
+ md_maps[md_maps_count++] = (struct md_map *)dmi;
+ }
+
+ // MB_SPEC
+ else if (header->type == 2)
+ {
+ dmi_system_info = (struct system_map *)dmi;
+ }
+
+ // CPU_SPEC
+ else if (header->type == 4)
+ {
+ dmi_cpu_info = (struct cpu_map *)dmi;
+ }
+
+ dmi+=header->length;
+
+ while( ! (*dmi == 0 && *(dmi+1) == 0 ) )
+ dmi++;
+ dmi+=2;
+
+ if (++tstruct_count > eps->numstructs)
+ return -1;
+ }
+
+ if(logflag && log_dmi) {
+ char log[26] = "tstruct_count = ";
+ int length = 16;
+ int_to_charr(tstruct_count, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[43] = "SMBIOS entry point->numstructs = ";
+ int length = 33;
+ int_to_charr(eps->numstructs, log, &length);
+ print_log(log, length);
+ }
+
+ return 0;
+}
+
+
+int init_dmi(void){
+
+ if (logflag) print_log("init_dmi() started", 18);
+
+ int i;
+ for(i=0; i < MAX_DMI_MEMDEVS; i++)
+ dmi_err_cnts[i]=0;
+
+ int status = open_dmi();
+
+ if (logflag && log_dmi) print_log("Dmi openend.", 12);
+
+ dmi_initialized=1;
+
+ return status;
+}
+
+void print_dmi_startup_info(void)
+{
+
+ if (logflag) print_log("print_dmi_startup_info() started", 32);
+
+ char *string1;
+ char *string2;
+ char *string3;
+ int dmicol = 78;
+ int slength;
+ int sl1, sl2, sl3;
+
+ if(!dmi_initialized) {
+ if (init_dmi() == -1) return;
+ }
+
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+ if (logflag && log_dmi) {
+ char log[50] = "print_dmi_startup_info(): dmi pointer = ";
+ int length = 40;
+ int_to_charr((ulong)&dmi_system_info, log, &length);
+ print_log(log, length);
+ }
+
+ string1 = get_tstruct_string(&dmi_system_info->header,dmi_system_info->manufacturer);
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+ sl1 = mt86_strlen(string1);
+
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+ string2 = get_tstruct_string(&dmi_system_info->header,dmi_system_info->productname);
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+
+ sl2 = mt86_strlen(string2);
+
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+ string3 = get_tstruct_string(&dmi_cpu_info->header,dmi_cpu_info->cpu_socket);
+
+ if (logflag && log_dmi) print_log("Dmi initialized.", 16);
+
+ sl3 = mt86_strlen(string3);
+
+ if (logflag && log_dmi) {
+ char log[61] = "print_dmi_startup_info(): manufacturer = ";
+ int length = 41;
+ string_to_charr(string1, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[16] = "sl1 = ";
+ int length = 6;
+ int_to_charr(sl1, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[60] = "print_dmi_startup_info(): productname = ";
+ int length = 40;
+ string_to_charr(string2, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[16] = "sl2 = ";
+ int length = 6;
+ int_to_charr(sl2, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[59] = "print_dmi_startup_info(): cpu_socket = ";
+ int length = 39;
+ string_to_charr(string3, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag && log_dmi) {
+ char log[16] = "sl3 = ";
+ int length = 6;
+ int_to_charr(sl3, log, &length);
+ print_log(log, length);
+ }
+
+ slength = sl1 + sl2;
+
+ if (logflag && log_dmi) print_log("test1", 5);
+
+ if(sl3 > 2) { slength += sl3 + 4; } else { slength++; }
+
+ if (logflag && log_dmi) print_log("test2", 5);
+
+ if(sl1 && sl2) {
+
+ if (logflag && log_dmi) print_log("Printing CPU information.", 25);
+
+
+ //dmicol -= slength; // right align
+ dmicol = 39 - slength/2; // center align
+ cprint(LINE_DMI, dmicol, string1);
+ dmicol += sl1 + 1;
+ cprint(LINE_DMI, dmicol, string2);
+ dmicol += sl2 + 1;
+
+ if(sl3 > 2){
+ cprint(LINE_DMI, dmicol, "(");
+ dmicol++;
+ cprint(LINE_DMI, dmicol, string3);
+ dmicol += sl3;
+ cprint(LINE_DMI, dmicol, ")");
+ }
+ }
+
+ if (logflag && log_dmi) print_log("test3", 5);
+
+}
+
+void print_dmi_info(void){
+ int i,j,page;
+ char * string=0;
+
+ if(!dmi_initialized) {
+ if (init_dmi() == -1) return;
+ }
+
+ if (mem_devs_count == 0){
+ cprint(POP2_Y+1, POP2_X+2, "No valid DMI Memory Devices info found");
+ while (get_key() == 0);
+ return;
+ }
+
+ for(page=1; page <= 1 + (mem_devs_count-1)/8; page++){
+ pop2clear();
+ cprint(POP2_Y+1, POP2_X+2, "DMI Memory Device Info (page ");
+ itoa(string,page);
+ cprint(POP2_Y+1, POP2_X+32, string);
+ cprint(POP2_Y+1, POP2_X+33, "/");
+ itoa(string,1 + (mem_devs_count-1)/8);
+ cprint(POP2_Y+1, POP2_X+34, string);
+ cprint(POP2_Y+1, POP2_X+35, ")");
+
+ cprint(POP2_Y+3, POP2_X+4, "Location Size(MB) Speed(MHz) Type Form");
+ cprint(POP2_Y+4, POP2_X+4, "--------------------------------------------------------------");
+
+ for(i=8*(page-1); i<mem_devs_count && i<8*page; i++){
+ int size_in_mb;
+ int yof;
+
+ yof = POP2_Y+5+2*(i-8*(page-1));
+ cprint(yof, POP2_X+4, get_tstruct_string(&(mem_devs[i]->header), mem_devs[i]->dev_locator));
+
+ if (mem_devs[i]->size == 0){
+ cprint(yof, POP2_X+4+18, "Empty");
+ }else if (mem_devs[i]->size == 0xFFFF){
+ cprint(yof, POP2_X+4+18, "Unknown");
+ }else if (mem_devs[i]->size == 0x7FFF){
+ // SMBIOS 2.7+
+ size_in_mb = mem_devs[i]->ext_size;
+ itoa(string, size_in_mb);
+ cprint(yof, POP2_X+4+18, string);
+ }else{
+ size_in_mb = 0xFFFF & mem_devs[i]->size;
+ if (mem_devs[i]->size & 0x8000)
+ size_in_mb <<= 10;
+ itoa(string, size_in_mb);
+ cprint(yof, POP2_X+4+18, string);
+ }
+
+ //this is the only field that needs to be SMBIOS 2.3+
+ if ( mem_devs[i]->speed &&
+ mem_devs[i]->header.length > 21){
+ itoa(string, mem_devs[i]->speed);
+ cprint(yof, POP2_X+4+27, string);
+ }else{
+ cprint(yof, POP2_X+4+27, "Unknown");
+ }
+ cprint(yof, POP2_X+4+37, memory_types[mem_devs[i]->type]);
+ cprint(yof, POP2_X+4+44, form_factors[mem_devs[i]->form]);
+
+ //print mappings
+ int mapped=0,of=0;
+ cprint(yof+1, POP2_X+6,"mapped to: ");
+ for(j=0; j<md_maps_count; j++)
+ {
+ if (mem_devs[i]->header.handle != md_maps[j]->md_handle)
+ continue;
+ if (mapped++){
+ cprint(yof+1, POP2_X+17+of, ",");
+ of++;
+ }
+ hprint3(yof+1, POP2_X+17+of, md_maps[j]->start>>22, 4);
+ of += 4;
+ hprint3(yof+1, POP2_X+17+of, md_maps[j]->start<<10, 8);
+ of += 8;
+ cprint(yof+1, POP2_X+17+of, "-");
+ of++;
+ hprint3(yof+1, POP2_X+17+of, md_maps[j]->end>>22, 4);
+ of += 4;
+ hprint3(yof+1, POP2_X+17+of, ((md_maps[j]->end+1)<<10) - 1, 8);
+ of += 8;
+ if(md_maps[j]->end == 0) { hprint3(yof+1, POP2_X+17+of-8,0,8); }
+ }
+ if (!mapped)
+ {
+ cprint(yof+1, POP2_X+17, "No mapping (Interleaved Device)");
+ }
+
+ }
+
+ wait_keyup();
+ while (get_key() == 0);
+ }
+}
+
+//return 1 if the list of bad memory devices changes, 0 otherwise, -1 if no mapped
+int add_dmi_err(ulong adr){
+ int i,j,found=-1;
+
+ if(!dmi_initialized)
+ init_dmi();
+
+ for(i=0; i < md_maps_count; i++){
+ if ( adr < (md_maps[i]->start<<10) ||
+ adr > (md_maps[i]->end<<10) )
+ continue;
+
+ //matching map found, now check find corresponding dev
+ for(j=0; j < mem_devs_count; j++){
+ if (mem_devs[j]->header.handle != md_maps[i]->md_handle)
+ continue;
+ if (dmi_err_cnts[j]){
+ found=0;
+ }else{
+ found = dmi_err_cnts[j] = 1;
+ }
+ }
+ }
+
+ return found;
+}
+
+void print_dmi_err(void){
+ int i,count,of;
+ char *string;
+
+ scroll();
+
+ cprint(vv->msg_line, 0,"Bad Memory Devices: ");
+ of=20;
+ for ( i=count=0; i < MAX_DMI_MEMDEVS; i++){
+ if (!dmi_err_cnts[i])
+ continue;
+ struct mem_dev *md = mem_devs[i];
+ if(count++){
+ cprint(vv->msg_line, of, ", ");
+ of+=2;
+ }
+ string=get_tstruct_string((struct tstruct_header *)md,md->dev_locator);
+ if (mt86_strlen(string) + of > 80){
+ scroll();
+ of=7;
+ }
+ cprint(vv->msg_line, of, string);
+ of += mt86_strlen(string);
+ }
+}
diff --git a/efi_memtest/memtest86+/efi/init.c b/efi_memtest/memtest86+/efi/init.c
index accfede..ef09f48 100644
--- a/efi_memtest/memtest86+/efi/init.c
+++ b/efi_memtest/memtest86+/efi/init.c
@@ -35,6 +35,7 @@ extern char cpu_mask[];
extern void initialise_cpus();
extern short logflag;
+extern short log_cpuspeed;
extern short log_memspeed;
/* Here we store all of the cpuid data */
@@ -43,6 +44,7 @@ extern struct cpu_ident cpu_id;
int l1_cache=0, l2_cache=0, l3_cache=0;
int tsc_invariable = 0;
ulong extclock;
+char *cpu_type_s;
ulong memspeed(ulong src, ulong len, int iter);
static void cpu_type(void);
@@ -210,67 +212,16 @@ void failsafe(int msec, int scs)
}
}
-/*static void display_init(void)
-{
- int i;
- volatile char *pp;
- */
- /* Set HW cursor out of screen boundaries */
- /* __outb(0x0F, 0x03D4);
- __outb(0xFF, 0x03D5);
-
- __outb(0x0E, 0x03D4);
- __outb(0xFF, 0x03D5);
-
-
- serial_echo_init();
- serial_echo_print("INE_SCROLL;24r");*/ /* Set scroll area row 7-23 */
- /* serial_echo_print("");*/ /* Clear Screen */
- /*serial_echo_print("");
- serial_echo_print("");
- serial_echo_print("");*/
-
- /* Clear screen & set background to blue */
- /* for(i=0, pp=(char *)(SCREEN_ADR); i<80*24; i++) {
- *pp++ = ' ';
- *pp++ = 0x17;
- }*/
-
- /* Make the name background green */
- /*for(i=0, pp=(char *)(SCREEN_ADR+1); i<TITLE_WIDTH; i++, pp+=2) {
- *pp = 0x20;
- }
- cprint(0, 0, " Memtest86 5.31b ");
-*/
- /* Set Blinking "+" */
- /* for(i=0, pp=(char *)(SCREEN_ADR+1); i<2; i++, pp+=30) {
- *pp = 0xA4;
- }
- cprint(0, 15, "+");
-*/
- /* Do reverse video for the bottom display line */
- /*for(i=0, pp=(char *)(SCREEN_ADR+1+(24 * 160)); i<80; i++, pp+=2) {
- *pp = 0x71;
- }
-
- serial_echo_print("");
-}
-*/
/*
* Initialize test, setup screen and find out how much memory there is.
*/
-void init(void)
-{
+void init(void) {
outb(0x8, 0x3f2); /* Kill Floppy Motor */
/* Turn on cache */
set_cache(1);
- /* Setup the display */
- // display_init();
-
-
vv->pass = 0;
vv->msg_line = 0;
vv->ecount = 0;
@@ -291,9 +242,11 @@ void init(void)
vv->erri.ebits = 0;
vv->erri.hdr_flag = 0;
vv->erri.tbits = 0;
+
for (int i=0; tseq[i].msg != NULL; i++) {
tseq[i].errors = 0;
}
+
if (dmi_initialized) {
for (int i=0; i < MAX_DMI_MEMDEVS; i++){
if (dmi_err_cnts[i] > 0) {
@@ -311,7 +264,7 @@ void init(void)
/* setup pci */
pci_init();
- get_cache_size();
+ get_cache_size();
cpu_type();
@@ -321,35 +274,24 @@ void init(void)
// failsafe(5000, 0x3B); // TODO depends on correct behavior of cpuspeed
if (logflag) {
- char log[34] = "init(): vv->fail_safe = ";
- int length = 24;
- int_to_charr(vv->fail_safe, log, &length);
- print_log(log, length);
+ char log[34] = "init(): vv->fail_safe = ";
+ int length = 24;
+ int_to_charr(vv->fail_safe, log, &length);
+ print_log(log, length);
}
if (logflag) {
- char log[29] = "init(): num_cpus = ";
- int length = 19;
- int_to_charr(num_cpus, log, &length);
- print_log(log, length);
+ char log[29] = "init(): num_cpus = ";
+ int length = 19;
+ int_to_charr(num_cpus, log, &length);
+ print_log(log, length);
}
/* Initalize SMP */
/*initialise_cpus();*/
- /* Find Memory Specs */
- if(vv->fail_safe & 1)
- {
- cprint(LINE_CPU, COL_SPEC, " **** FAIL SAFE **** FAIL SAFE **** ");
- cprint(LINE_RAM, COL_SPEC, " No detection, same reliability ");
- } else {
- // find_controller();
- // get_spd_spec();
- if(num_cpus <= 16 && !(vv->fail_safe & 4)) {
- //coretemp();
- }
- } /*
+ /*
if(vv->check_temp > 0 && !(vv->fail_safe & 4))
{
@@ -364,13 +306,31 @@ void init(void)
asm __volatile__ ("rdtsc":"=a" (vv->startl),"=d" (vv->starth));
vv->snapl = vv->startl;
vv->snaph = vv->starth;
+
if (l1_cache == 0) { l1_cache = 64; }
if (l2_cache == 0) { l1_cache = 512; }
+
vv->printmode=PRINTMODE_ADDRESSES;
vv->numpatn=0;
+ /*
+ * WARNING: do not print anything before this statement. Otherwise it will be overwritten
+ */
print_mainscreen();
+ /* Find Memory Specs */
+ if(vv->fail_safe & 1)
+ {
+ cprint(LINE_CPU, COL_SPEC, " **** FAIL SAFE **** FAIL SAFE **** "); // TODO should be printed AFTER prnt_mainscreen
+ cprint(LINE_RAM, COL_SPEC, " No detection, same reliability ");
+ } else {
+ find_controller();
+ // get_spd_spec();
+ if(num_cpus <= 16 && !(vv->fail_safe & 4)) {
+ //coretemp();
+ }
+ }
+
}
/* Get cache sizes for most AMD and Intel CPUs, exceptions for old CPUs are
@@ -378,9 +338,10 @@ void init(void)
void get_cache_size()
{
if (logflag) {
- char log[] = "get_cache_size() started.";
- print_log(log, sizeof(log) - 1);
+ char log[] = "get_cache_size() started.";
+ print_log(log, sizeof(log) - 1);
}
+
int i, j, n, size;
unsigned int v[4];
unsigned char *dp = (unsigned char *)v;
@@ -389,265 +350,220 @@ void get_cache_size()
struct cpuid4_ecx *ecx = (struct cpuid4_ecx *)&v[2];
switch(cpu_id.vend_id.char_array[0]) {
- /* AMD Processors */
- case 'A':
- //l1_cache = cpu_id.cache_info.amd.l1_i_sz;
- l1_cache = cpu_id.cache_info.amd.l1_d_sz;
- l2_cache = cpu_id.cache_info.amd.l2_sz;
- l3_cache = cpu_id.cache_info.amd.l3_sz;
- l3_cache *= 512;
+ /* AMD Processors */
+ case 'A':
+ //l1_cache = cpu_id.cache_info.amd.l1_i_sz;
+ l1_cache = cpu_id.cache_info.amd.l1_d_sz;
+ l2_cache = cpu_id.cache_info.amd.l2_sz;
+ l3_cache = cpu_id.cache_info.amd.l3_sz;
+ l3_cache *= 512;
- if (logflag) {
- char log[40] = "get_cache_size(): l1_cache = ";
- int length = 29;
- int_to_charr(l1_cache, log, &length);
- print_log(log, length);
- }
+ break;
- if (logflag) {
- char log[40] = "get_cache_size(): l2_cache = ";
- int length = 29;
- int_to_charr(l2_cache, log, &length);
- print_log(log, length);
- }
+ case 'G':
+ /* Intel Processors */
+ l1_cache = 0;
+ l2_cache = 0;
+ l3_cache = 0;
- if (logflag) {
- char log[40] = "get_cache_size(): l3_cache = ";
- int length = 29;
- int_to_charr(l3_cache, log, &length);
- print_log(log, length);
+ /* Use CPUID(4) if it is available */
+ if (cpu_id.max_cpuid > 3) {
- }
-
- break;
- case 'G':
- /* Intel Processors */
- l1_cache = 0;
- l2_cache = 0;
- l3_cache = 0;
-
- /* Use CPUID(4) if it is available */
- if (cpu_id.max_cpuid > 3) {
-
- /* figure out how many cache leaves */
- n = -1;
- do
- {
+ /* figure out how many cache leaves */
+ n = -1;
+ do {
++n;
// Do cpuid(4) loop to find out num_cache_leaves
cpuid_count(4, n, &v[0], &v[1], &v[2], &v[3]);
- } while ((eax->ctype) != 0);
+ } while ((eax->ctype) != 0);
- /* loop through all of the leaves */
- for (i=0; i<n; i++)
- {
- cpuid_count(4, i, &v[0], &v[1], &v[2], &v[3]);
+ /* loop through all of the leaves */
+ for (i=0; i<n; i++) {
+ cpuid_count(4, i, &v[0], &v[1], &v[2], &v[3]);
/* Check for a valid cache type */
- if (eax->ctype == 1 || eax->ctype == 3)
- {
-
- /* Compute the cache size */
- size = (ecx->number_of_sets + 1) *
- (ebx->coherency_line_size + 1) *
- (ebx->physical_line_partition + 1) *
- (ebx->ways_of_associativity + 1);
- size /= 1024;
-
- switch (eax->level)
- {
- case 1:
- l1_cache += size;
- break;
- case 2:
- l2_cache += size;
- break;
- case 3:
- l3_cache += size;
- break;
- }
- }
- }
-
- if (logflag) {
- char log[40] = "get_cache_size(): l1_cache = ";
- int length = 29;
- int_to_charr(l1_cache, log, &length);
- print_log(log, length);
- }
-
- if (logflag) {
- char log[40] = "get_cache_size(): l2_cache = ";
- int length = 29;
- int_to_charr(l2_cache, log, &length);
- print_log(log, length);
- }
-
- if (logflag) {
- char log[40] = "get_cache_size(): l3_cache = ";
- int length = 29;
- int_to_charr(l3_cache, log, &length);
- print_log(log, length);
- }
-
- return;
- }
+ if (eax->ctype == 1 || eax->ctype == 3) {
+
+ /* Compute the cache size */
+ size = (ecx->number_of_sets + 1) *
+ (ebx->coherency_line_size + 1) *
+ (ebx->physical_line_partition + 1) *
+ (ebx->ways_of_associativity + 1);
+ size /= 1024;
+
+ switch (eax->level) {
+ case 1:
+ l1_cache += size;
+ break;
+ case 2:
+ l2_cache += size;
+ break;
+ case 3:
+ l3_cache += size;
+ break;
+ }
+ }
+ }
+
+ break;
+ }
- /* No CPUID(4) so we use the older CPUID(2) method */
- /* Get number of times to iterate */
- cpuid(2, &v[0], &v[1], &v[2], &v[3]);
- n = v[0] & 0xff;
- for (i=0 ; i<n ; i++) {
+ /* No CPUID(4) so we use the older CPUID(2) method */
+ /* Get number of times to iterate */
cpuid(2, &v[0], &v[1], &v[2], &v[3]);
-
- /* If bit 31 is set, this is an unknown format */
- for (j=0 ; j<3 ; j++) {
- if (v[j] & (1 << 31)) {
- v[j] = 0;
- }
- }
-
- /* Byte 0 is level count, not a descriptor */
- for (j = 1 ; j < 16 ; j++) {
- switch(dp[j]) {
- case 0x6:
- case 0xa:
- case 0x66:
- l1_cache += 8;
- break;
- case 0x8:
- case 0xc:
- case 0xd:
- case 0x60:
- case 0x67:
- l1_cache += 16;
- break;
- case 0xe:
- l1_cache += 24;
- break;
- case 0x9:
- case 0x2c:
- case 0x30:
- case 0x68:
- l1_cache += 32;
- break;
- case 0x39:
- case 0x3b:
- case 0x41:
- case 0x79:
- l2_cache += 128;
- break;
- case 0x3a:
- l2_cache += 192;
- break;
- case 0x21:
- case 0x3c:
- case 0x3f:
- case 0x42:
- case 0x7a:
- case 0x82:
- l2_cache += 256;
- break;
- case 0x3d:
- l2_cache += 384;
- break;
- case 0x3e:
- case 0x43:
- case 0x7b:
- case 0x7f:
- case 0x80:
- case 0x83:
- case 0x86:
- l2_cache += 512;
- break;
- case 0x44:
- case 0x78:
- case 0x7c:
- case 0x84:
- case 0x87:
- l2_cache += 1024;
- break;
- case 0x45:
- case 0x7d:
- case 0x85:
- l2_cache += 2048;
+ n = v[0] & 0xff;
+ for (i=0 ; i<n ; i++) {
+ cpuid(2, &v[0], &v[1], &v[2], &v[3]);
+
+ /* If bit 31 is set, this is an unknown format */
+ for (j=0 ; j<3 ; j++) {
+ if (v[j] & (1 << 31)) {
+ v[j] = 0;
+ }
+ }
+
+ /* Byte 0 is level count, not a descriptor */
+ for (j = 1 ; j < 16 ; j++) {
+ switch(dp[j]) {
+ case 0x6:
+ case 0xa:
+ case 0x66:
+ l1_cache += 8;
+ break;
+ case 0x8:
+ case 0xc:
+ case 0xd:
+ case 0x60:
+ case 0x67:
+ l1_cache += 16;
+ break;
+ case 0xe:
+ l1_cache += 24;
+ break;
+ case 0x9:
+ case 0x2c:
+ case 0x30:
+ case 0x68:
+ l1_cache += 32;
break;
- case 0x48:
- l2_cache += 3072;
- break;
- case 0x4e:
- l2_cache += 6144;
- break;
- case 0x23:
- case 0xd0:
- l3_cache += 512;
- break;
- case 0xd1:
- case 0xd6:
- l3_cache += 1024;
- break;
- case 0x25:
- case 0xd2:
- case 0xd7:
- case 0xdc:
- case 0xe2:
- l3_cache += 2048;
- break;
- case 0x29:
- case 0x46:
- case 0x49:
- case 0xd8:
- case 0xdd:
- case 0xe3:
- l3_cache += 4096;
- break;
- case 0x4a:
- l3_cache += 6144;
- break;
- case 0x47:
- case 0x4b:
- case 0xde:
- case 0xe4:
- l3_cache += 8192;
- break;
- case 0x4c:
- case 0xea:
- l3_cache += 12288;
- break;
- case 0x4d:
- l3_cache += 16384;
- break;
- case 0xeb:
- l3_cache += 18432;
- break;
- case 0xec:
- l3_cache += 24576;
- break;
- } /* end switch */
- } /* end for 1-16 */
- } /* end for 0 - n */
-
- if (logflag) {
- char log[40] = "get_cache_size(): l1_cache = ";
- int length = 29;
- int_to_charr(l1_cache, log, &length);
- print_log(log, length);
- }
+ case 0x39:
+ case 0x3b:
+ case 0x41:
+ case 0x79:
+ l2_cache += 128;
+ break;
+ case 0x3a:
+ l2_cache += 192;
+ break;
+ case 0x21:
+ case 0x3c:
+ case 0x3f:
+ case 0x42:
+ case 0x7a:
+ case 0x82:
+ l2_cache += 256;
+ break;
+ case 0x3d:
+ l2_cache += 384;
+ break;
+ case 0x3e:
+ case 0x43:
+ case 0x7b:
+ case 0x7f:
+ case 0x80:
+ case 0x83:
+ case 0x86:
+ l2_cache += 512;
+ break;
+ case 0x44:
+ case 0x78:
+ case 0x7c:
+ case 0x84:
+ case 0x87:
+ l2_cache += 1024;
+ break;
+ case 0x45:
+ case 0x7d:
+ case 0x85:
+ l2_cache += 2048;
+ break;
+ case 0x48:
+ l2_cache += 3072;
+ break;
+ case 0x4e:
+ l2_cache += 6144;
+ break;
+ case 0x23:
+ case 0xd0:
+ l3_cache += 512;
+ break;
+ case 0xd1:
+ case 0xd6:
+ l3_cache += 1024;
+ break;
+ case 0x25:
+ case 0xd2:
+ case 0xd7:
+ case 0xdc:
+ case 0xe2:
+ l3_cache += 2048;
+ break;
+ case 0x29:
+ case 0x46:
+ case 0x49:
+ case 0xd8:
+ case 0xdd:
+ case 0xe3:
+ l3_cache += 4096;
+ break;
+ case 0x4a:
+ l3_cache += 6144;
+ break;
+ case 0x47:
+ case 0x4b:
+ case 0xde:
+ case 0xe4:
+ l3_cache += 8192;
+ break;
+ case 0x4c:
+ case 0xea:
+ l3_cache += 12288;
+ break;
+ case 0x4d:
+ l3_cache += 16384;
+ break;
+ case 0xeb:
+ l3_cache += 18432;
+ break;
+ case 0xec:
+ l3_cache += 24576;
+ break;
+ } /* end switch */
+ } /* end for 1-16 */
+ } /* end for 0 - n */
- if (logflag) {
- char log[40] = "get_cache_size(): l2_cache = ";
- int length = 29;
- int_to_charr(l2_cache, log, &length);
- print_log(log, length);
- }
+ }
- if (logflag) {
- char log[40] = "get_cache_size(): l3_cache = ";
- int length = 29;
- int_to_charr(l3_cache, log, &length);
- print_log(log, length);
- }
- }
+ if (logflag) {
+ char log[40] = "get_cache_size(): l1_cache = ";
+ int length = 29;
+ int_to_charr(l1_cache, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag) {
+ char log[40] = "get_cache_size(): l2_cache = ";
+ int length = 29;
+ int_to_charr(l2_cache, log, &length);
+ print_log(log, length);
+ }
+
+ if (logflag) {
+ char log[40] = "get_cache_size(): l3_cache = ";
+ int length = 29;
+ int_to_charr(l3_cache, log, &length);
+ print_log(log, length);
+ }
}
/*
@@ -679,7 +595,7 @@ void detect_imc(void)
case 0x7:
imc_type = 0x0105; // Kabini & related (Family 16h)
break;
- }
+ }
return;
}
@@ -761,11 +677,10 @@ void smp_default_mode(void)
/*
* Find CPU type
*/
-void cpu_type(void)
-{
+void cpu_type(void) {
/* If we can get a brand string use it, and we are done */
if (cpu_id.max_xcpuid >= 0x80000004) {
- cprint(0, COL_MID, cpu_id.brand_id.char_array); // TODO this hides an other cprint output
+ cpu_type_s = cpu_id.brand_id.char_array;
//If we have a brand string, maybe we have an IMC. Check that.
detect_imc();
smp_default_mode();
@@ -781,22 +696,22 @@ void cpu_type(void)
case 4:
switch(cpu_id.vers.bits.model) {
case 3:
- cprint(0, COL_MID, "AMD 486DX2");
+ cpu_type_s = "AMD 486DX2";
break;
case 7:
- cprint(0, COL_MID, "AMD 486DX2-WB");
+ cpu_type_s = "AMD 486DX2-WB";
break;
case 8:
- cprint(0, COL_MID, "AMD 486DX4");
+ cpu_type_s = "AMD 486DX4";
break;
case 9:
- cprint(0, COL_MID, "AMD 486DX4-WB");
+ cpu_type_s = "AMD 486DX4-WB";
break;
case 14:
- cprint(0, COL_MID, "AMD 5x86-WT");
+ cpu_type_s = "AMD 5x86-WT";
break;
case 15:
- cprint(0, COL_MID, "AMD 5x86-WB");
+ cpu_type_s = "AMD 5x86-WB";
break;
}
/* Since we can't get CPU speed or cache info return */
@@ -807,58 +722,56 @@ void cpu_type(void)
case 1:
case 2:
case 3:
- cprint(0, COL_MID, "AMD K5");
+ cpu_type_s = "AMD K5";
l1_cache = 8;
break;
case 6:
case 7:
- cprint(0, COL_MID, "AMD K6");
+ cpu_type_s = "AMD K6";
break;
case 8:
- cprint(0, COL_MID, "AMD K6-2");
+ cpu_type_s = "AMD K6-2";
break;
case 9:
- cprint(0, COL_MID, "AMD K6-III");
+ cpu_type_s = "AMD K6-III";
break;
case 13:
- cprint(0, COL_MID, "AMD K6-III+");
+ cpu_type_s = "AMD K6-III+";
break;
}
break;
case 6:
-
switch(cpu_id.vers.bits.model) {
case 1:
- cprint(0, COL_MID, "AMD Athlon (0.25)");
+ cpu_type_s = "AMD Athlon (0.25)";
break;
case 2:
case 4:
- cprint(0, COL_MID, "AMD Athlon (0.18)");
+ cpu_type_s = "AMD Athlon (0.18)";
break;
case 6:
if (l2_cache == 64) {
- cprint(0, COL_MID, "AMD Duron (0.18)");
+ cpu_type_s = "AMD Duron (0.18)";
} else {
- cprint(0, COL_MID, "Athlon XP (0.18)");
+ cpu_type_s = "Athlon XP (0.18)";
}
break;
case 8:
case 10:
if (l2_cache == 64) {
- cprint(0, COL_MID, "AMD Duron (0.13)");
+ cpu_type_s = "AMD Duron (0.13)";
} else {
- cprint(0, COL_MID, "Athlon XP (0.13)");
+ cpu_type_s = "Athlon XP (0.13)";
}
break;
case 3:
case 7:
- cprint(0, COL_MID, "AMD Duron");
+ cpu_type_s = "AMD Duron";
/* Duron stepping 0 CPUID for L2 is broken */
/* (AMD errata T13)*/
if (cpu_id.vers.bits.stepping == 0) { /* stepping 0 */
/* Hard code the right L2 size */
l2_cache = 64;
- } else {
}
break;
}
@@ -873,41 +786,42 @@ void cpu_type(void)
case 'G':
if ( cpu_id.vend_id.char_array[7] == 'T' ) { /* GenuineTMx86 */
if (cpu_id.vers.bits.family == 5) {
- cprint(0, COL_MID, "TM 5x00");
+ cpu_type_s = "TM 5x00";
} else if (cpu_id.vers.bits.family == 15) {
- cprint(0, COL_MID, "TM 8x00");
+ cpu_type_s = "TM 8x00";
}
l1_cache = cpu_id.cache_info.ch[3] + cpu_id.cache_info.ch[7];
l2_cache = (cpu_id.cache_info.ch[11]*256) + cpu_id.cache_info.ch[10];
} else { /* GenuineIntel */
if (cpu_id.vers.bits.family == 4) {
- switch(cpu_id.vers.bits.model) {
- case 0:
- case 1:
- cprint(0, COL_MID, "Intel 486DX");
- break;
- case 2:
- cprint(0, COL_MID, "Intel 486SX");
- break;
- case 3:
- cprint(0, COL_MID, "Intel 486DX2");
- break;
- case 4:
- cprint(0, COL_MID, "Intel 486SL");
- break;
- case 5:
- cprint(0, COL_MID, "Intel 486SX2");
- break;
- case 7:
- cprint(0, COL_MID, "Intel 486DX2-WB");
- break;
- case 8:
- cprint(0, COL_MID, "Intel 486DX4");
- break;
- case 9:
- cprint(0, COL_MID, "Intel 486DX4-WB");
- break;
- }
+ switch(cpu_id.vers.bits.model) {
+ case 0:
+ case 1:
+ cpu_type_s = "Intel 486DX";
+ break;
+ case 2:
+ cpu_type_s = "Intel 486SX";
+ break;
+ case 3:
+ cpu_type_s = "Intel 486DX2";
+ break;
+ case 4:
+ cpu_type_s = "Intel 486SL";
+ break;
+ case 5:
+ cpu_type_s = "Intel 486SX2";
+ break;
+ case 7:
+ cpu_type_s = "Intel 486DX2-WB";
+ break;
+ case 8:
+ cpu_type_s = "Intel 486DX4";
+ break;
+ case 9:
+ cpu_type_s = "Intel 486DX4-WB";
+ break;
+ }
+ }
/* Since we can't get CPU speed or cache info return */
return;
}
@@ -920,15 +834,15 @@ void cpu_type(void)
case 1:
case 2:
case 3:
+ case 4:
case 7:
- cprint(0, COL_MID, "Pentium");
+ cpu_type_s = "Pentium";
if (l1_cache == 0) {
l1_cache = 8;
}
break;
- case 4:
case 8:
- cprint(0, COL_MID, "Pentium-MMX");
+ cpu_type_s = "Pentium-MMX";
if (l1_cache == 0) {
l1_cache = 16;
}
@@ -939,65 +853,65 @@ void cpu_type(void)
switch(cpu_id.vers.bits.model) {
case 0:
case 1:
- cprint(0, COL_MID, "Pentium Pro");
+ cpu_type_s = "Pentium Pro";
break;
case 3:
case 4:
- cprint(0, COL_MID, "Pentium II");
+ cpu_type_s = "Pentium II";
break;
case 5:
if (l2_cache == 0) {
- cprint(0, COL_MID, "Celeron");
+ cpu_type_s = "Celeron";
} else {
- cprint(0, COL_MID, "Pentium II");
+ cpu_type_s = "Pentium II";
}
break;
case 6:
- if (l2_cache == 128) {
- cprint(0, COL_MID, "Celeron");
- } else {
- cprint(0, COL_MID, "Pentium II");
- }
- }
- break;
- case 7:
- case 8:
- case 11:
if (l2_cache == 128) {
- cprint(0, COL_MID, "Celeron");
+ cpu_type_s = "Celeron";
} else {
- cprint(0, COL_MID, "Pentium III");
+ cpu_type_s = "Pentium II";
}
+
break;
+ case 7:
+ case 8:
case 9:
if (l2_cache == 512) {
- cprint(0, COL_MID, "Celeron M (0.13)");
+ cpu_type_s = "Celeron M (0.13)";
} else {
- cprint(0, COL_MID, "Pentium M (0.13)");
+ cpu_type_s = "Pentium M (0.13)";
}
break;
- case 10:
- cprint(0, COL_MID, "Pentium III Xeon");
+ case 10:
+ cpu_type_s = "Pentium III Xeon";
break;
+ case 11:
+ if (l2_cache == 128) {
+ cpu_type_s = "Celeron";
+ } else {
+ cpu_type_s = "Pentium III";
+ }
+ break;
case 12:
l1_cache = 24;
- cprint(0, COL_MID, "Atom (0.045)");
+ cpu_type_s = "Atom (0.045)";
break;
case 13:
if (l2_cache == 1024) {
- cprint(0, COL_MID, "Celeron M (0.09)");
+ cpu_type_s = "Celeron M (0.09)";
} else {
- cprint(0, COL_MID, "Pentium M (0.09)");
+ cpu_type_s = "Pentium M (0.09)";
}
break;
case 14:
- cprint(0, COL_MID, "Intel Core");
+ cpu_type_s = "Intel Core";
break;
case 15:
if (l2_cache == 1024) {
- cprint(0, COL_MID, "Pentium E");
+ cpu_type_s = "Pentium E";
} else {
- cprint(0, COL_MID, "Intel Core 2");
+ cpu_type_s = "Intel Core 2";
}
break;
}
@@ -1008,24 +922,24 @@ void cpu_type(void)
case 1:
case 2:
if (l2_cache == 128) {
- cprint(0, COL_MID, "Celeron");
+ cpu_type_s = "Celeron";
} else {
- cprint(0, COL_MID, "Pentium 4");
+ cpu_type_s = "Pentium 4";
}
break;
case 3:
case 4:
if (l2_cache == 256) {
- cprint(0, COL_MID, "Celeron (0.09)");
+ cpu_type_s = "Celeron (0.09)";
} else {
- cprint(0, COL_MID, "Pentium 4 (0.09)");
+ cpu_type_s = "Pentium 4 (0.09)";
}
break;
case 6:
- cprint(0, COL_MID, "Pentium D (65nm)");
+ cpu_type_s = "Pentium D (65nm)";
break;
default:
- cprint(0, COL_MID, "Unknown Intel");
+ cpu_type_s = "Unknown Intel";
break;
break;
}
@@ -1040,29 +954,29 @@ void cpu_type(void)
l2_cache = cpu_id.cache_info.ch[11];
switch(cpu_id.vers.bits.family){
case 5:
- cprint(0, COL_MID, "Centaur 5x86");
+ cpu_type_s = "Centaur 5x86";
break;
case 6: // VIA C3
switch(cpu_id.vers.bits.model){
default:
if (cpu_id.vers.bits.stepping < 8) {
- cprint(0, COL_MID, "VIA C3 Samuel2");
+ cpu_type_s = "VIA C3 Samuel2";
} else {
- cprint(0, COL_MID, "VIA C3 Eden");
+ cpu_type_s = "VIA C3 Eden";
}
break;
case 10:
- cprint(0, COL_MID, "VIA C7 (C5J)");
+ cpu_type_s = "VIA C7 (C5J)";
l1_cache = 64;
l2_cache = 128;
break;
case 13:
- cprint(0, COL_MID, "VIA C7 (C5R)");
+ cpu_type_s = "VIA C7 (C5R)";
l1_cache = 64;
l2_cache = 128;
break;
case 15:
- cprint(0, COL_MID, "VIA Isaiah (CN)");
+ cpu_type_s = "VIA Isaiah (CN)";
l1_cache = 64;
l2_cache = 128;
break;
@@ -1073,10 +987,10 @@ void cpu_type(void)
case 5:
switch(cpu_id.vers.bits.model) {
case 0:
- cprint(0, COL_MID, "Cyrix 6x86MX/MII");
+ cpu_type_s = "Cyrix 6x86MX/MII";
break;
case 4:
- cprint(0, COL_MID, "Cyrix GXm");
+ cpu_type_s = "Cyrix GXm";
break;
}
return;
@@ -1084,20 +998,20 @@ void cpu_type(void)
case 6: // VIA C3
switch(cpu_id.vers.bits.model) {
case 6:
- cprint(0, COL_MID, "Cyrix III");
+ cpu_type_s = "Cyrix III";
break;
case 7:
if (cpu_id.vers.bits.stepping < 8) {
- cprint(0, COL_MID, "VIA C3 Samuel2");
+ cpu_type_s = "VIA C3 Samuel2";
} else {
- cprint(0, COL_MID, "VIA C3 Ezra-T");
+ cpu_type_s = "VIA C3 Ezra-T";
}
break;
case 8:
- cprint(0, COL_MID, "VIA C3 Ezra-T");
+ cpu_type_s = "VIA C3 Ezra-T";
break;
case 9:
- cprint(0, COL_MID, "VIA C3 Nehemiah");
+ cpu_type_s = "VIA C3 Nehemiah";
break;
}
// L1 = L2 = 64 KB from Cyrix III to Nehemiah
@@ -1112,11 +1026,11 @@ void cpu_type(void)
/* Make a guess at the family */
switch(cpu_id.vers.bits.family) {
case 5:
- cprint(0, COL_MID, "586");
+ cpu_type_s = "586";
case 6:
- cprint(0, COL_MID, "686");
+ cpu_type_s = "686";
default:
- cprint(0, COL_MID, "Unidentified Processor");
+ cpu_type_s = "Unidentified Processor";
}
}
}
@@ -1124,90 +1038,64 @@ void cpu_type(void)
#define STEST_ADDR 0x100000 /* Measure memory speed starting at 1MB */
/* Measure and display CPU and cache sizes and speeds */
-void cpu_cache_speed()
-{
+ulong cpu_speed;
+ulong speed_l1;
+ulong speed_l2;
+ulong speed_l3;
+void cpu_cache_speed() {
if (logflag) {
- char log[] = "cpu_cache_speed() started.";
- print_log(log, sizeof(log) - 1);
+ char log[] = "cpu_cache_speed() started.";
+ print_log(log, sizeof(log) - 1);
}
- int i, off = 4;
- ulong speed;
-
+ int i;
/* Print CPU speed */
- if ((speed = cpuspeed()) > 0) {
- if (speed < 999499) {
- speed += 50; /* for rounding */
- cprint(1, off, " . MHz");
- dprint(1, off+1, speed/1000, 3, 1);
- dprint(1, off+5, (speed/100)%10, 1, 0);
+ if ((cpu_speed = cpuspeed()) > 0) {
+ if (cpu_speed < 999499) {
+ cpu_speed += 50; /* for rounding */
} else {
- speed += 500; /* for rounding */
- cprint(1, off, " MHz");
- dprint(1, off, speed/1000, 5, 0);
+ cpu_speed += 500; /* for rounding */
}
- extclock = speed;
+ extclock = cpu_speed;
}
- if (logflag) {
- char log[38] = "cpu_cache_speed(): speed = ";
- int length = 27;
- int_to_charr(extclock, log, &length);
- print_log(log, length);
+ if (logflag && log_cpuspeed) {
+ char log[38] = "cpu_cache_speed(): speed = ";
+ int length = 27;
+ int_to_charr(extclock, log, &length);
+ print_log(log, length);
}
- /* Print out L1 cache info */
/* To measure L1 cache speed we use a block size that is 1/4th */
/* of the total L1 cache size since half of it is for instructions */
if (l1_cache) {
- cprint(2, 0, "L1 Cache: K ");
- dprint(2, 11, l1_cache, 3, 0);
- if ((speed=memspeed(STEST_ADDR, (l1_cache/2)*1024, 200))) {
- cprint(2, 16, " MB/s");
- dprint(2, 16, speed, 6, 0);
- }
+ speed_l1 = memspeed(STEST_ADDR, (l1_cache/2)*1024, 200);
}
- /* Print out L2 cache info */
/* We measure the L2 cache speed by using a block size that is */
/* the size of the L1 cache. We have to fudge if the L1 */
/* cache is bigger than the L2 */
if (l2_cache) {
- cprint(3, 0, "L2 Cache: K ");
- dprint(3, 10, l2_cache, 4, 0);
-
- if (l2_cache < l1_cache) {
+ if (l2_cache < l1_cache) {
i = l1_cache / 4 + l2_cache / 4;
} else {
i = l1_cache;
}
- if ((speed=memspeed(STEST_ADDR, i*1024, 200))) {
- cprint(3, 16, " MB/s");
- dprint(3, 16, speed, 6, 0);
- }
+ speed_l2 = memspeed(STEST_ADDR, i*1024, 200);
}
- /* Print out L3 cache info */
+
/* We measure the L3 cache speed by using a block size that is */
/* 2X the size of the L2 cache. */
- if (l3_cache)
- {
- cprint(4, 0, "L3 Cache: K ");
- aprint(4, 10, l3_cache/4);
- //dprint(4, 10, l3_cache, 4, 0);
-
- i = l2_cache*2;
-
- if ((speed=memspeed(STEST_ADDR, i*1024, 150))) {
- cprint(4, 16, " MB/s");
- dprint(4, 16, speed, 6, 0);
- }
- }
+ if (l3_cache) {
+ i = l2_cache*2;
+ speed_l3 = memspeed(STEST_ADDR, i*1024, 150);
+ }
}
/* Measure and display memory speed, multitasked using all CPUs */
-ulong spd[MAX_CPUS];
+//ulong spd[MAX_CPUS]; // TODO can we remove this var?
void get_mem_speed(int me, int ncpus)
{
int i;
@@ -1216,7 +1104,7 @@ void get_mem_speed(int me, int ncpus)
/* Determine memory speed. To find the memory speed we use
* A block size that is the sum of all the L1, L2 & L3 caches
* in all cpus * 6 */
- i = (l3_cache + l2_cache + l1_cache) * 4;
+ i = (l3_cache + l2_cache + l1_cache) * 4; // TODO is this calculation correct? The car ncpus is not used
/* Make sure that we have enough memory to do the test */
/* If not use all we have */
@@ -1243,16 +1131,16 @@ void get_mem_speed(int me, int ncpus)
#define TICKS 59659 /* 50 ms */
/* Returns CPU clock in khz */
-ulong stlow, sthigh;
static int cpuspeed(void)
{
- if (logflag) {
- char log[] = "cpuspeed() started.";
- print_log(log, sizeof(log) - 1);
+ if (logflag && log_cpuspeed) {
+ char log[] = "cpuspeed() started.";
+ print_log(log, sizeof(log) - 1);
}
int loops;
- //ulong end_low, end_high;
+ int stlow, sthigh;
+ int end_low, end_high;
if (cpu_id.fid.bits.rdtsc == 0 ) {
return(-1);
@@ -1264,30 +1152,32 @@ static int cpuspeed(void)
outb(TICKS & 0xff, 0x42);
outb(TICKS >> 8, 0x42);
+ /* Get start time */
asm __volatile__ ("rdtsc":"=a" (stlow),"=d" (sthigh));
-
loops = 0;
do {
loops++;
} while ((inb(0x61) & 0x20) == 0);
- /*asm __volatile__ (
- "rdtsc\n\t" \
- "subl stlow,%%eax\n\t" \
- "sbbl sthigh,%%edx\n\t" \
- :"=a" (end_low), "=d" (end_high)
- );*/
+ /* Get difference to end time */
+ asm __volatile__ (
+ "rdtsc\n\t" \
+ "subl %2, %%eax\n\t" \
+ "sbbl %3, %%edx\n\t" \
+ :"=a" (end_low), "=d" (end_high)
+ :"r" (stlow), "r" (sthigh)
+ );
/* Make sure we have a credible result */
- /*if (loops < 4 || end_low < 50000) {
+ if (loops < 4 || end_low < 50000) {
return(-1);
}
vv->clks_msec = end_low/50;
-*/
- //if (tsc_invariable) end_low = correct_tsc(end_low);
- if (logflag) {
+ if (tsc_invariable) end_low = correct_tsc(end_low);
+
+ if (logflag && log_cpuspeed) {
char log[35] = "cpuspeed(): clks_msec = ";
int length = 24;
int_to_charr(vv->clks_msec, log, &length);
@@ -1299,32 +1189,33 @@ static int cpuspeed(void)
/* Measure cache speed by copying a block of memory. */
/* Returned value is kbytes/second */
+ulong memspeed_end_high;
ulong memspeed(ulong src, ulong len, int iter)
{
- if (logflag) {
- char log[] = "\nmemspeed(ulong src, long len, int iter) started.";
- print_log(log, sizeof(log) - 1);
+ if (logflag && log_memspeed) {
+ char log[] = "\nmemspeed(ulong src, long len, int iter) started.";
+ print_log(log, sizeof(log) - 1);
}
if (logflag && log_memspeed) {
- char log[38] = "memspeed(): src = ";
- int length = 18;
- int_to_charr(src, log, &length);
- print_log(log, length);
+ char log[38] = "memspeed(): src = ";
+ int length = 18;
+ int_to_charr(src, log, &length);
+ print_log(log, length);
}
if (logflag && log_memspeed) {
- char log[38] = "memspeed(): len = ";
- int length = 18;
- int_to_charr(len, log, &length);
- print_log(log, length);
+ char log[38] = "memspeed(): len = ";
+ int length = 18;
+ int_to_charr(len, log, &length);
+ print_log(log, length);
}
if (logflag && log_memspeed) {
- char log[39] = "memspeed(): iter = ";
- int length = 19;
- int_to_charr(iter, log, &length);
- print_log(log, length);
+ char log[39] = "memspeed(): iter = ";
+ int length = 19;
+ int_to_charr(iter, log, &length);
+ print_log(log, length);
}
@@ -1335,17 +1226,17 @@ ulong memspeed(ulong src, ulong len, int iter)
ulong cal_low, cal_high;
if (logflag && log_memspeed) {
- char log[22] = "memspeed(): rdtsc = ";
- int length = 20;
- int_to_charr(cpu_id.fid.bits.rdtsc, log, &length);
- print_log(log, length);
+ char log[22] = "memspeed(): rdtsc = ";
+ int length = 20;
+ int_to_charr(cpu_id.fid.bits.rdtsc, log, &length);
+ print_log(log, length);
}
if (cpu_id.fid.bits.rdtsc == 0 ) {
if (logflag && log_memspeed) {
- char log[] = "memspeed(): returning with -1 because rdtsc = 0";
- print_log(log, sizeof(log) - 1);
+ char log[] = "memspeed(): returning with -1 because rdtsc = 0";
+ print_log(log, sizeof(log) - 1);
}
return(-1);
@@ -1353,8 +1244,8 @@ ulong memspeed(ulong src, ulong len, int iter)
if (len == 0) {
if (logflag && log_memspeed) {
- char log[] = "memspeed(): returning with -2 because len = 0";
- print_log(log, sizeof(log) - 1);
+ char log[] = "memspeed(): returning with -2 because len = 0";
+ print_log(log, sizeof(log) - 1);
}
return(-2);
@@ -1364,8 +1255,8 @@ ulong memspeed(ulong src, ulong len, int iter)
wlen = len / 4; /* Length is bytes */
if (logflag && log_memspeed) {
- char log[] = "\nmemspeed(): Calibrate overhead with a zero word copy.";
- print_log(log, sizeof(log) - 1);
+ char log[] = "\nmemspeed(): Calibrate overhead with a zero word copy.";
+ print_log(log, sizeof(log) - 1);
}
/* Calibrate the overhead with a zero word copy */
@@ -1492,7 +1383,7 @@ ulong memspeed(ulong src, ulong len, int iter)
);
/* Make sure that the result fits in 32 bits */
- hprint(11,40,end_high);
+ memspeed_end_high = end_high;
if (end_high) {
if (logflag && log_memspeed) {
diff --git a/efi_memtest/memtest86+/efi/logger.c b/efi_memtest/memtest86+/efi/logger.c
index dfea97c..b56e129 100644
--- a/efi_memtest/memtest86+/efi/logger.c
+++ b/efi_memtest/memtest86+/efi/logger.c
@@ -7,6 +7,10 @@
#include "display.h"
#include "string.h"
+#include "controller.h"
+
+#include "Efi_Defs_GUID.h"
+
/* TODOS
Replace Print by ConOut
@@ -16,7 +20,6 @@ extern short logflag;
extern EFI_SYSTEM_TABLE *gST;
-
EFI_STATUS efiStatus;
EFI_BOOT_SERVICES* bs;
EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL *Console;
@@ -51,11 +54,7 @@ BOOLEAN compareGuids(EFI_GUID* sfspGuid, EFI_GUID* guid) {
&& guid->Data4[2] == sfspGuid->Data4[2] && guid->Data4[3] == sfspGuid->Data4[3]
&& guid->Data4[4] == sfspGuid->Data4[4] && guid->Data4[5] == sfspGuid->Data4[5]
&& guid->Data4[6] == sfspGuid->Data4[6] && guid->Data4[7] == sfspGuid->Data4[7]) {
-/*
- Print(L"GUID: %x-%x-%x-%x-%x-%x-%x-%x-%x-%x-%x\n",
- guid->Data1, guid->Data2, guid->Data3,
- guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3],
- guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7]);*/
+
return TRUE;
}
return FALSE;
@@ -264,14 +263,15 @@ void int_to_charr(unsigned long num, char* arr, int *length) { // TODO test corn
*length = pos2-1;
}
-/*void string_to_charr(char *add, char *output, int *length) {
+void string_to_charr(char *add, char *output, int *length) {
for (int i = 0; add[i]; i++) {
- (*length)++;
+
output[*length] = add[i];
+ (*length)++;
}
(*length)++;
output[*length] = '\0';
-}*/
+}
/*void hex_to_charr(unsigned long num, char* arr, int *length) {
@@ -359,6 +359,18 @@ void print_pmap() {
int msegs = vv->msegs;
+ char log[42] ="print_pmap(): msegs = ";
+ int length = 22;
+ int_to_charr(msegs, log, &length);
+ print_log(log, length);
+
+ if(1) {
+ char log[23] = "vv addr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
for (int i = 0; i < msegs; i++) {
char log1[33] = "\nprint_pmap(): start = ";
@@ -405,4 +417,14 @@ void print_log_n(int log_flag, char *msg, ulong num) {
int_to_charr(num, log, &length);
print_log(log, length);
}
-} \ No newline at end of file
+}
+
+void print_controllers(int index) {
+
+}
+
+/*
+ Print(L"GUID: %x-%x-%x-%x-%x-%x-%x-%x-%x-%x-%x\n",
+ guid->Data1, guid->Data2, guid->Data3,
+ guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3],
+ guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7]);*/ \ No newline at end of file
diff --git a/efi_memtest/memtest86+/efi/memory_tables.c b/efi_memtest/memtest86+/efi/memory_tables.c
index 4f4d300..89f3ad5 100644
--- a/efi_memtest/memtest86+/efi/memory_tables.c
+++ b/efi_memtest/memtest86+/efi/memory_tables.c
@@ -1,4 +1,3 @@
-
#include "Uefi.h"
#include "Library/UefiLib.h"
@@ -32,13 +31,21 @@ const CHAR16 *memory_types[] =
int query_memory_table(void) {
+
if (logflag) {
- char log[] = "query_memory_table() started.";
- print_log(log, sizeof(log) - 1);
+ char log[] = "query_memory_table() started.";
+ print_log(log, sizeof(log) - 1);
}
int flag = 0;
+ if(logflag && log_mem_tbl) {
+ char log[23] = "vvqaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
UINTN MemoryMapSize = 0;
EFI_MEMORY_DESCRIPTOR *memoryMap = NULL;
UINTN LocalMapKey;
@@ -63,7 +70,7 @@ int query_memory_table(void) {
if (Status != EFI_SUCCESS) {
- if (logflag) {
+ if (logflag && log_mem_tbl) {
char log[32] = "query_memory_table(): Status = ";
log[31] = Status + '\0';
print_log(log, sizeof(log));
@@ -188,7 +195,7 @@ void get_mem_size(int flag, short e820_nr, struct e820entry *e820) {
}
end = e820[i].addr;
end += e820[i].size * 4096;
- // >> 12 = /4096
+ // >> 12 = /4096
vv->pmap[n].start = (e820[i].addr + 4095) >> 12;
vv->pmap[n].end = end >> 12;
vv->test_pages += vv->pmap[n].end - vv->pmap[n].start;
diff --git a/efi_memtest/memtest86+/efi/test.c b/efi_memtest/memtest86+/efi/test.c
index 1ab87bf..badba42 100644
--- a/efi_memtest/memtest86+/efi/test.c
+++ b/efi_memtest/memtest86+/efi/test.c
@@ -19,6 +19,11 @@
extern short logflag;
extern short log_fine;
+extern short log_tst2;
+
+// TODO REMOVE
+int addr_written = 0;
+ulong bad_addr = 103493632;
extern struct cpu_ident cpu_id;
extern volatile int mstr_cpu;
@@ -275,60 +280,87 @@ void addr_tst1(int me)
unsliced_foreach_segment(nullptr, me, addr_tst1_seg);
}
+// TODO remove
+void stack_addr() {
+ int i;
+ char log[32] = "stack ptr = ";
+ int length = 12;
+ int_to_charr((unsigned long) &i, log, &length);
+ print_log(log, length);
+}
+
int print_init_counter = 0;
STATIC void addr_tst2_init_segment(ulong* p,
ulong len_dw, const void* unused) {
ulong* pe = p + ((len_dw - 1) >> 1);
- if (logflag) {
+ if (logflag && log_tst2) {
char log[27] = "Number of pages: ";
int length = 17;
int_to_charr((ulong)(pe - p)>>9, log, &length);
print_log(log, length);
}
- if (logflag) {
+ if (logflag && log_tst2) {
char log[13] = "p: ";
int length = 3;
int_to_charr((ulong)p, log, &length);
print_log(log, length);
}
- if (logflag) {
+ if (logflag && log_tst2) {
char log[14] = "pe: ";
int length = 4;
int_to_charr((ulong)pe, log, &length);
print_log(log, length);
}
- if (logflag) {
+ if (logflag && log_tst2) {
char log[128] = "pe - p: ";
int length = 8;
int_to_charr((ulong)(pe - p)<<3, log, &length);
print_log(log, length);
}
- /*if (status != EFI_SUCCESS) {
- char log[19] = "status = ";
- int length = 9;
- int_to_charr(status, log, &length);
- print_log(log, length);
-
- } else {
- print_log(">>>>>>>>>>SUCCESS!!", 19);
- }*/
+ stack_addr();
//Original C code replaced with hand tuned assembly code
+
+ int round = 1;
+
for (; p <= pe; p++) {
*p = (ulong)p;
- /* if ((ulong)p == 103514112) {
- if (logflag) {
- char log[35] = "content of p = ";
- int length = 15;
- int_to_charr(*p, log, &length);
+ if ((ulong)p == bad_addr) {
+ addr_written = 1;
+ ulong *px = (ulong *)bad_addr;
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*px, log, &length);
+ print_log(log, length);
+ }
+
+ if (addr_written && (*(ulong *) bad_addr != bad_addr)) {
+ ulong *px = (ulong *)bad_addr;
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*px, log, &length);
+ print_log(log, length);
+
+ char lg[16] = "Round ";
+ length = 6;
+ int_to_charr(round, lg, &length);
+ print_log(lg, length);
+
+ if (logflag) {
+ char log[45] = "Current return address = ";
+ int length = 25;
+ int_to_charr((unsigned long) ((unsigned long *) __builtin_return_address(0)), log, &length);
print_log(log, length);
- }
- }*/
+ }
+
+ while(1);
+ }
+ round++;
}
/*asm __volatile__ (
@@ -342,6 +374,14 @@ STATIC void addr_tst2_init_segment(ulong* p,
"jb L90\n\t"
: : "D" (p), "d" (pe)
);*/
+
+/* if (addr_written) {
+ ulong *px = (ulong *)bad_addr;
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*px, log, &length);
+ print_log(log, length);
+ } */
}
int print_check_counter = 0;
@@ -378,9 +418,23 @@ STATIC void addr_tst2_check_segment(ulong* p,
}*/
//Original C code replaced with hand tuned assembly code
+
+/* if (logflag && log_tst2 && addr_written) {
+ ulong *px = (ulong*)bad_addr;
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*px, log, &length);
+ print_log(log, length);
+ } */
+
+
for (; p <= pe; p++) {
+
+
+
+
if((bad = *p) != (ulong)p) {
- ad_err2((ulong *)p, bad);
+ ad_err2((ulong *)p, bad);
}
}
@@ -445,11 +499,6 @@ STATIC void addr_tst2_check_segment(ulong* p,
: "ecx"
);
*/
- /* EFI_STATUS status = gST->BootServices->FreePages((EFI_PHYSICAL_ADDRESS) p, (UINTN) (pe - p) >> 12);
-
- if (status != EFI_SUCCESS) {
- print_log("no success", 10);
- }*/
}
@@ -460,17 +509,41 @@ void addr_tst2(int me)
{
cprint(LINE_PAT, COL_PAT, "address ");
- if (logflag) {
+ if (logflag && log_tst2) {
print_log("addr_tst2(): starting addr_tst2_init_segment", 44);
}
+
+ if (logflag) {
+ char log[49] = "Address of global variable = ";
+ int length = 29;
+ int_to_charr((unsigned long) &addr_written, log, &length);
+ print_log(log, length);
+ }
+
/* Write each address with its own address */
unsliced_foreach_segment(nullptr, me, addr_tst2_init_segment);
{ BAILR }
- if (logflag) {
+ /* ulong *p = (ulong * )bad_addr;
+ if (logflag && log_tst2 && addr_written) {
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*p, log, &length);
+ print_log(log, length);
+ } */
+
+
+ /* if (logflag && log_tst2) {
print_log("addr_tst2(): starting addr_tst2_check_segment", 45);
- }
+ }*/
+
+ /* if (logflag && log_tst2 && addr_written) {
+ char log[35] = "content of p = ";
+ int length = 15;
+ int_to_charr(*p, log, &length);
+ print_log(log, length);
+ }*/
/* Each address should have its own address */
unsliced_foreach_segment(nullptr, me, addr_tst2_check_segment);
diff --git a/efi_memtest/memtest86+/error.c b/efi_memtest/memtest86+/error.c
index 1151810..f256e5d 100644
--- a/efi_memtest/memtest86+/error.c
+++ b/efi_memtest/memtest86+/error.c
@@ -16,6 +16,7 @@
#include "display.h"
extern short logflag;
+extern short log_tst2;
extern int dmi_err_cnts[MAX_DMI_MEMDEVS];
extern int beepmode;
@@ -110,21 +111,23 @@ void ad_err1(ulong *adr1, ulong *mask, ulong bad, ulong good)
void ad_err2(ulong *adr, ulong bad)
{
- /*if (logflag) {
+ if (logflag) {
print_log("ad_err2(): FOUND ERROR IN MEMORY TEST # 2", 41);
}
- if (logflag) {
+ if (logflag && log_tst2) {
char log[28] = "ad_err2(): *adr = ";
int length = 18;
int_to_charr((ulong)adr, log, &length);
print_log(log, length);
}
- if (logflag) {
+ if (logflag && log_tst2) {
char log[27] = "ad_err2(): bad = ";
int length = 17;
int_to_charr(bad, log, &length);
print_log(log, length);
- }*/
+ }
+
+ while(1);
//query_memory_table(); // TODO remove
//print_pmap(); // TODO remove
@@ -624,8 +627,8 @@ void do_tick(int me)
* is supported
*/
- // TODO
- /* if (cpu_id.fid.bits.rdtsc) {
+/*TODO
+ if (cpu_id.fid.bits.rdtsc) {
asm __volatile__(
"rdtsc":"=a" (l),"=d" (h));
asm __volatile__ (
@@ -660,7 +663,7 @@ void do_tick(int me)
}*/
/* Poll for ECC errors */
- /*
- poll_errors();
- */
+
+ //poll_errors();
+
}
diff --git a/efi_memtest/memtest86+/logger.h b/efi_memtest/memtest86+/logger.h
index e6d5f00..9c8d6e2 100644
--- a/efi_memtest/memtest86+/logger.h
+++ b/efi_memtest/memtest86+/logger.h
@@ -4,7 +4,7 @@ void init_logger();
void int_to_charr(unsigned long num, char* buffer, int* length);
-//void string_to_charr(char *add, char *output, int *length);
+void string_to_charr(char *add, char *output, int *length);
//void hex_to_charr(unsigned long num, char* arr, int *length);
diff --git a/efi_memtest/memtest86+/main.c b/efi_memtest/memtest86+/main.c
index 621f432..7ea7d66 100644
--- a/efi_memtest/memtest86+/main.c
+++ b/efi_memtest/memtest86+/main.c
@@ -210,7 +210,19 @@ void set_defaults()
restart_flag = 0;
tseq[10].sel = 0;
- alloc_map->length = 0;
+ if(1) {
+ char log[23] = "vv addr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
+ if(1) {
+ char log[23] = "plim_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
}
@@ -428,27 +440,58 @@ void test_start(void)
//parse_command_line(); // TODO not possible yet
if (logflag) print_log("test_start(): Command line parsed, now clear_screen()", 53);
- clear_screen();
+
/* Initialize the barrier so the lock in btrace will work.
* Will get redone later when we know how many CPUs we have */
barrier_init(1);
+
btrace(my_cpu_num, __LINE__, "Begin ", 1, 0, 0);
+
+ if(0) {
+ char log[23] = "pllm_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
+
+
/* Find memory size */
mem_size(); /* must be called before initialise_cpus(); */
+
+ if(0) {
+ char log[23] = "pllm_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
+
+
/* Fill in the CPUID table */
get_cpuid();
/* Startup the other CPUs */
start_seq = 1;
+
//initialise_cpus(); todo smp
btrace(my_cpu_num, __LINE__, "BeforeInit", 1, 0, 0);
/* Draw the screen and get system information */
+ /*
+ * WARNING: do not print anything except btrace before this statement.
+ * Otherwise it will be overwritten.
+ */
init();
/* Set defaults and initialize variables */
set_defaults();
+ if(1) {
+ char log[] = "plim_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
+
if (logflag) print_log("test_start(): set_defaults() finished.", 38);
/* Setup base address for testing, 1 MB */
@@ -562,7 +605,8 @@ void test_start(void)
int_to_charr(cpu_id.fid.bits.lm, log, &length);
print_log(log, length);
}
- setup_mm_modes();
+
+ setup_mm_modes(); // TODO do we need it anymore? Since we already start in 64 bit mode
/* Get the memory Speed with all CPUs */
//get_mem_speed(my_cpu_num, num_cpus);
@@ -1010,6 +1054,13 @@ int do_test(int my_ord)
cprint(LINE_PAT, COL_MID+25, " ");
}*/
+ if (logflag) {
+ char log[41] = ">>>>>>>>>>>>>>>>>>>> ";
+ int length = 21;
+ int_to_charr(vv->selected_pages, log, &length);
+ print_log(log, length);
+ }
+
/* Update display of memory segments being tested */
p0 = page_of(vv->map[0].start);
p1 = page_of(vv->map[segs-1].end);
@@ -1049,7 +1100,9 @@ int do_test(int my_ord)
print_log(log, length);
}
- for (int i = 0; i < vv->msegs; i++) {
+ //for (int i = 0; i < vv->msegs; i++) {
+ for (int j = 0; j < 10; j++) {
+ int i = 5;
ulong * p = (ulong *) (vv->pmap[i].start * 4096);
ulong page_no = ((ulong) vv->pmap[i].end - (ulong) vv->pmap[i].start);
@@ -1635,21 +1688,7 @@ static int compute_segments(struct pmap win, int me)
int_to_charr((unsigned long)vv->map[sg].end, log, &length);
print_log(log, length);
}
-#if 0
- hprint(LINE_SCROLL+(sg+1), 0, sg);
- hprint(LINE_SCROLL+(sg+1), 12, vv->map[sg].pbase_addr);
- hprint(LINE_SCROLL+(sg+1), 22, start);
- hprint(LINE_SCROLL+(sg+1), 32, end);
- hprint(LINE_SCROLL+(sg+1), 42, mapping(start));
- hprint(LINE_SCROLL+(sg+1), 52, emapping(end));
- cprint(LINE_SCROLL+(sg+2), 0,
- " "
- " ");
-#endif
-#if 0
- cprint(LINE_SCROLL+(2*i+1), 54, ", sg=");
- hprint(LINE_SCROLL+(2*i+1), 59, sg);
-#endif
+
sg++;
}
}
diff --git a/efi_memtest/memtest86+/memsize.c b/efi_memtest/memtest86+/memsize.c
index aebbd0b..4a83793 100644
--- a/efi_memtest/memtest86+/memsize.c
+++ b/efi_memtest/memtest86+/memsize.c
@@ -19,13 +19,23 @@ static struct e820entry e820[E820MAX];
static void sort_pmap(void);
+extern short logflag;
+extern short log_pmap;
+
/*
* Find out how much memory there is.
*/
-#pragma GCC push_options
-#pragma GCC optimize ("O0")
+//#pragma GCC push_options
+//#pragma GCC optimize ("O0")
void mem_size(void)
{
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvmaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
int i = 0, flag = 0;
vv->test_pages = 0;
@@ -48,19 +58,98 @@ void mem_size(void)
}
}
+ if(logflag && log_pmap) {
+ char log[23] = "vvmaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
get_mem_size(flag, e820_nr, e820);
+ if(logflag && log_pmap) {
+ char log[23] = "pmap.end = ";
+ int length = 11;
+ int_to_charr(vv->pmap[vv->msegs-1].end, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) {
+ char log[23] = "msegs = ";
+ int length = 8;
+ int_to_charr(vv->msegs, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvmaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
/* Guarantee that pmap entries are in ascending order */
sort_pmap();
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvmaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
vv->plim_lower = 0;
vv->plim_upper = vv->pmap[vv->msegs-1].end;
+ if(logflag && log_pmap) {
+ char log[23] = "pmap.end = ";
+ int length = 11;
+ int_to_charr(vv->pmap[vv->msegs-1].end, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) {
+ char log[23] = "msegs = ";
+ int length = 8;
+ int_to_charr(vv->msegs, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) print_pmap();
+
+ if(logflag && log_pmap) {
+ char log[23] = "pmap.end = ";
+ int length = 11;
+ int_to_charr(vv->pmap[vv->msegs-1].end, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) {
+ char log[23] = "msegs = ";
+ int length = 8;
+ int_to_charr(vv->msegs, log, &length);
+ print_log(log, length);
+ }
+
+ if(logflag && log_pmap) {
+ char log[23] = "pffm_upper = ";
+ int length = 13;
+ int_to_charr(vv->plim_upper, log, &length);
+ print_log(log, length);
+ }
+
adj_mem();
}
-#pragma GCC pop_options
+//#pragma GCC pop_options
static void sort_pmap(void)
{
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvpaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
+
int i, j;
/* Do an insertion sort on the pmap, on an already sorted
* list this should be a O(1) algorithm.
@@ -82,4 +171,12 @@ static void sort_pmap(void)
vv->pmap[j] = temp;
}
}
+
+
+ if(logflag && log_pmap) {
+ char log[23] = "vvpaddr = ";
+ int length = 10;
+ int_to_charr((ulong)vv, log, &length);
+ print_log(log, length);
+ }
} \ No newline at end of file
diff --git a/efi_memtest/memtest86+/pci.c b/efi_memtest/memtest86+/pci.c
index 737f24f..39ac02c 100644
--- a/efi_memtest/memtest86+/pci.c
+++ b/efi_memtest/memtest86+/pci.c
@@ -16,6 +16,7 @@
#include "logger.h"
extern short logflag;
+extern short log_pci_conf;
#define PCI_CONF_TYPE_NONE 0
#define PCI_CONF_TYPE_1 1
@@ -35,32 +36,32 @@ static unsigned char pci_conf_type = PCI_CONF_TYPE_NONE;
int pci_conf_read(unsigned bus, unsigned dev, unsigned fn, unsigned reg, unsigned len, unsigned long *value)
{
- if (logflag) {
- char log[68] = "\npci_conf_read() started.\npci_conf_read(): bus = ";
- int length = 48;
- int_to_charr(bus, log, &length);
- print_log(log, length);
+ if (logflag && log_pci_conf) {
+ char log[68] = "\npci_conf_read() started.\npci_conf_read(): bus = ";
+ int length = 48;
+ int_to_charr(bus, log, &length);
+ print_log(log, length);
}
- if (logflag) {
- char log[43] = "pci_conf_read(): dev = ";
- int length = 23;
- int_to_charr(dev, log, &length);
- print_log(log, length);
+ if (logflag && log_pci_conf) {
+ char log[43] = "pci_conf_read(): dev = ";
+ int length = 23;
+ int_to_charr(dev, log, &length);
+ print_log(log, length);
}
- if (logflag) {
- char log[42] = "pci_conf_read(): fn = ";
- int length = 22;
- int_to_charr(fn, log, &length);
- print_log(log, length);
+ if (logflag && log_pci_conf) {
+ char log[42] = "pci_conf_read(): fn = ";
+ int length = 22;
+ int_to_charr(fn, log, &length);
+ print_log(log, length);
}
- if (logflag) {
- char log[43] = "pci_conf_read(): reg = ";
- int length = 23;
- int_to_charr(reg, log, &length);
- print_log(log, length);
+ if (logflag && log_pci_conf) {
+ char log[43] = "pci_conf_read(): reg = ";
+ int length = 23;
+ int_to_charr(reg, log, &length);
+ print_log(log, length);
}
@@ -96,11 +97,11 @@ int pci_conf_read(unsigned bus, unsigned dev, unsigned fn, unsigned reg, unsigne
break;
}
- if (logflag) {
- char log[36] = "pci_conf_read(): result = ";
- int length = 26;
- int_to_charr(result, log, &length);
- print_log(log, length);
+ if (logflag && log_pci_conf) {
+ char log[36] = "pci_conf_read(): result = ";
+ int length = 26;
+ int_to_charr(result, log, &length);
+ print_log(log, length);
}
return result;
diff --git a/efi_memtest/todo b/efi_memtest/todo
deleted file mode 100644
index 674fc79..0000000
--- a/efi_memtest/todo
+++ /dev/null
@@ -1,8 +0,0 @@
-what is AutoGen.obj?
-
-AutoGen.obj has possibly an unwanted link to edk
-
-remove static_library_files.lst
-
-main.c - does -start come from the *.lds file?
-
diff --git a/save/Efi_Defs.c b/save/Efi_Defs.c
new file mode 100644
index 0000000..e0b80b2
--- /dev/null
+++ b/save/Efi_Defs.c
@@ -0,0 +1,168 @@
+#include "Efi_Defs.h"
+#include "Efi_Defs_GUID.h"
+#include "Efi_Defs_Pcd.h"
+#include "Uefi.h"
+#include "Library/BaseLib.h"
+#include "Library/DebugLib.h"
+#include "Library/UefiBootServicesTableLib.h"
+#include "Library/UefiApplicationEntryPoint.h"
+
+//GLOBAL_REMOVE_IF_UNREFERENCED GUID gEfiCallerIdGuid = {0x51d8cae0, 0x272a, 0x661f, {0xa8, 0xd9, 0x84, 0x51, 0xdf, 0xf0, 0xeb, 0xd0}};
+
+CHAR8 *gEfiCallerBaseName = "MemtestEfi";
+
+// Guids
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiMdePkgTokenSpaceGuid = { 0x914AEBE7, 0x4635, 0x459b, { 0xAA, 0x1C, 0x11, 0xE2, 0x19, 0xB0, 0x3A, 0x10 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVTUTF8Guid = { 0xAD15A0D6, 0x8BEC, 0x4ACF, { 0xA0, 0x73, 0xD0, 0x1D, 0xE7, 0x7E, 0x2D, 0x88 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVT100Guid = { 0xDFA66065, 0xB419, 0x11D3, { 0x9A, 0x2D, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVT100PlusGuid = { 0x7BAEC70B, 0x57E0, 0x4C76, { 0x8E, 0x87, 0x2F, 0x9E, 0x28, 0x08, 0x83, 0x43 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPcAnsiGuid = { 0xE0C14753, 0xF9BE, 0x11D2, { 0x9A, 0x0C, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiUartDevicePathGuid = { 0x37499a9d, 0x542f, 0x4c89, { 0xa0, 0x26, 0x35, 0xda, 0x14, 0x20, 0x94, 0xe4 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSasDevicePathGuid = { 0xd487ddb4, 0x008b, 0x11d9, { 0xaf, 0xdc, 0x00, 0x10, 0x83, 0xff, 0xca, 0x4d }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualDiskGuid = { 0x77AB535A, 0x45FC, 0x624B, {0x55, 0x60, 0xF7, 0xB2, 0x81, 0xD1, 0xF9, 0x6E }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiVirtualCdGuid = { 0x3D5ABD30, 0x4175, 0x87CE, {0x6D, 0x64, 0xD2, 0xAD, 0xE5, 0x23, 0xC4, 0xBB }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualDiskGuid = { 0x5CEA02C9, 0x4D07, 0x69D3, {0x26, 0x9F ,0x44, 0x96, 0xFB, 0xE0, 0x96, 0xF9 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiPersistentVirtualCdGuid = { 0x08018188, 0x42CD, 0xBB48, {0x10, 0x0F, 0x53, 0x87, 0xD5, 0x3D, 0xED, 0x3D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiEventReadyToBootGuid = { 0x7CE88FB3, 0x4BD7, 0x4679, { 0x87, 0xA8, 0xA8, 0xD8, 0xDE, 0xE5, 0x0D, 0x2B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiEventLegacyBootGuid = { 0x2A571201, 0x4966, 0x47F6, { 0x8B, 0x86, 0xF3, 0x1E, 0x41, 0xF3, 0x2F, 0x10 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiGlobalVariableGuid = { 0x8BE4DF61, 0x93CA, 0x11D2, { 0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8C }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiAcpi20TableGuid = { 0x8868E871, 0xE4F1, 0x11D3, { 0xBC, 0x22, 0x00, 0x80, 0xC7, 0x3C, 0x88, 0x81 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiAcpi10TableGuid = { 0xEB9D2D30, 0x2D88, 0x11D3, { 0x9A, 0x16, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+
+// Protocols
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDevicePathProtocolGuid = { 0x09576E91, 0x6D3F, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDebugPortProtocolGuid = { 0xEBA4E8D2, 0x3858, 0x41EC, { 0xA2, 0x81, 0x26, 0x47, 0xBA, 0x96, 0x60, 0xD0 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverBindingProtocolGuid = { 0x18A031AB, 0xB443, 0x4D1A, { 0xA5, 0xC0, 0x0C, 0x09, 0x26, 0x1E, 0x9F, 0x71 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSimpleTextOutProtocolGuid = { 0x387477C2, 0x69C7, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiGraphicsOutputProtocolGuid = { 0x9042A9DE, 0x23DC, 0x4A38, { 0x96, 0xFB, 0x7A, 0xDE, 0xD0, 0x80, 0x51, 0x6A }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiHiiFontProtocolGuid = {0xe9ca4775, 0x8657, 0x47fc, {0x97, 0xe7, 0x7e, 0xd6, 0x5a, 0x08, 0x43, 0x24}};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiSimpleFileSystemProtocolGuid = { 0x964E5B22, 0x6459, 0x11D2, { 0x8E, 0x39, 0x00, 0xA0, 0xC9, 0x69, 0x72, 0x3B }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiUgaDrawProtocolGuid = { 0x982C298B, 0xF4FA, 0x41CB, { 0xB8, 0x38, 0x77, 0xAA, 0x68, 0x8F, 0xB8, 0x39 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentNameProtocolGuid = { 0x107A772C, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiComponentName2ProtocolGuid = { 0x6A7A5CFF, 0xE8D9, 0x4F70, { 0xBA, 0xDA, 0x75, 0xAB, 0x30, 0x25, 0xCE, 0x14 }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfigurationProtocolGuid = { 0x107A772B, 0xD5E1, 0x11D4, { 0x9A, 0x46, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverConfiguration2ProtocolGuid = { 0xBFD7DC1D, 0x24F1, 0x40D9, { 0x82, 0xE7, 0x2E, 0x09, 0xBB, 0x6B, 0x4E, 0xBE }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnosticsProtocolGuid = { 0x0784924F, 0xE296, 0x11D4, { 0x9A, 0x49, 0x00, 0x90, 0x27, 0x3F, 0xC1, 0x4D }};
+//GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID gEfiDriverDiagnostics2ProtocolGuid = { 0x4D330321, 0x025F, 0x4AAC, { 0x90, 0xD8, 0x5E, 0xD9, 0x00, 0x17, 0x3B, 0x63 }};
+
+// Definition of SkuId Array
+//GLOBAL_REMOVE_IF_UNREFERENCED UINT64 _gPcd_SkuId_Array[] = {0x0};
+
+extern EFI_STATUS
+EFIAPI
+UefiMain (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+DxeDebugLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiBootServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiRuntimeServicesTableLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+EFI_STATUS
+EFIAPI
+UefiLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+VOID
+EFIAPI
+ProcessLibraryConstructorList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ Status = DxeDebugLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiBootServicesTableLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiRuntimeServicesTableLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+ Status = UefiLibConstructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+}
+
+
+EFI_STATUS
+EFIAPI
+DxeDebugLibDestructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+VOID
+EFIAPI
+ProcessLibraryDestructorList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ Status = DxeDebugLibDestructor (ImageHandle, SystemTable);
+ ASSERT_EFI_ERROR (Status);
+
+}
+
+const UINT32 _gUefiDriverRevision = 0x00000000U;
+
+
+EFI_STATUS
+EFIAPI
+ProcessModuleEntryPointList (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+
+{
+ return UefiMain (ImageHandle, SystemTable);
+}
+
+VOID
+EFIAPI
+ExitDriver (
+ IN EFI_STATUS Status
+ )
+{
+ if (EFI_ERROR (Status)) {
+ ProcessLibraryDestructorList (gImageHandle, gST);
+ }
+ gBS->Exit (gImageHandle, Status, 0, NULL);
+}
+
+GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gDriverUnloadImageCount = 0U;
+
+EFI_STATUS
+EFIAPI
+ProcessModuleUnloadList (
+ IN EFI_HANDLE ImageHandle
+ )
+{
+ return EFI_SUCCESS;
+}
diff --git a/save/Efi_Defs.h b/save/Efi_Defs.h
new file mode 100644
index 0000000..7a098e6
--- /dev/null
+++ b/save/Efi_Defs.h
@@ -0,0 +1,30 @@
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include "Uefi.h"
+
+extern GUID gEfiCallerIdGuid;
+extern CHAR8 *gEfiCallerBaseName;
+
+#define EFI_CALLER_ID_GUID \
+ {0x51d8cae0, 0x272a, 0x661f, {0xa8, 0xd9, 0x84, 0x51, 0xdf, 0xf0, 0xeb, 0xd0}}
+
+
+// Definition of SkuId Array
+/*extern UINT64 _gPcd_SkuId_Array[];
+*/
+
+EFI_STATUS
+EFIAPI
+UefiMain (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ );
+
+
+
+#ifdef __cplusplus
+}
+
+#endif
diff --git a/efi_memtest/memtest86+/efi/Include/AutoGen.h b/save/Efi_Defs_GUID.h
index 78d71dd..d69bb3e 100644
--- a/efi_memtest/memtest86+/efi/Include/AutoGen.h
+++ b/save/Efi_Defs_GUID.h
@@ -1,23 +1,3 @@
-/**
- DO NOT EDIT
- FILE auto-generated
- Module name:
- AutoGen.h
- Abstract: Auto-generated AutoGen.h for building module or library.
-**/
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-#include "Uefi.h"
-
-extern GUID gEfiCallerIdGuid;
-extern CHAR8 *gEfiCallerBaseName;
-
-#define EFI_CALLER_ID_GUID \
- {0x51d8cae0, 0x272a, 0x661f, {0xa8, 0xd9, 0x84, 0x51, 0xdf, 0xf0, 0xeb, 0xd0}}
-
// Guids
extern EFI_GUID gEfiMdePkgTokenSpaceGuid;
extern EFI_GUID gEfiVTUTF8Guid;
@@ -50,26 +30,4 @@ extern EFI_GUID gEfiComponentName2ProtocolGuid;
extern EFI_GUID gEfiDriverConfigurationProtocolGuid;
extern EFI_GUID gEfiDriverConfiguration2ProtocolGuid;
extern EFI_GUID gEfiDriverDiagnosticsProtocolGuid;
-extern EFI_GUID gEfiDriverDiagnostics2ProtocolGuid;
-
-// Definition of SkuId Array
-extern UINT64 _gPcd_SkuId_Array[];
-
-// Definition of PCDs used in libraries is in AutoGen.c
-
-
-EFI_STATUS
-EFIAPI
-UefiMain (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- );
-
-
-
-
-
-#ifdef __cplusplus
-}
-
-#endif
+extern EFI_GUID gEfiDriverDiagnostics2ProtocolGuid; \ No newline at end of file
diff --git a/save/Efi_Defs_Pcd.h b/save/Efi_Defs_Pcd.h
new file mode 100644
index 0000000..6edcc93
--- /dev/null
+++ b/save/Efi_Defs_Pcd.h
@@ -0,0 +1,120 @@
+
+// Definition of PCDs used in libraries
+
+/*#define _PCD_TOKEN_PcdVerifyNodeInList 17U
+#define _PCD_SIZE_PcdVerifyNodeInList 1
+#define _PCD_GET_MODE_SIZE_PcdVerifyNodeInList _PCD_SIZE_PcdVerifyNodeInList
+#define _PCD_VALUE_PcdVerifyNodeInList ((BOOLEAN)0U)
+//GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdVerifyNodeInList = _PCD_VALUE_PcdVerifyNodeInList;
+extern const BOOLEAN _gPcd_FixedAtBuild_PcdVerifyNodeInList;
+#define _PCD_GET_MODE_BOOL_PcdVerifyNodeInList _gPcd_FixedAtBuild_PcdVerifyNodeInList
+//#define _PCD_SET_MODE_BOOL_PcdVerifyNodeInList ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdMaximumLinkedListLength 12U
+#define _PCD_SIZE_PcdMaximumLinkedListLength 4
+#define _PCD_GET_MODE_SIZE_PcdMaximumLinkedListLength _PCD_SIZE_PcdMaximumLinkedListLength
+#define _PCD_VALUE_PcdMaximumLinkedListLength 1000000U
+//GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdMaximumLinkedListLength = _PCD_VALUE_PcdMaximumLinkedListLength;
+extern const UINT32 _gPcd_FixedAtBuild_PcdMaximumLinkedListLength;
+#define _PCD_GET_MODE_32_PcdMaximumLinkedListLength _gPcd_FixedAtBuild_PcdMaximumLinkedListLength
+//#define _PCD_SET_MODE_32_PcdMaximumLinkedListLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdMaximumAsciiStringLength 10U
+#define _PCD_SIZE_PcdMaximumAsciiStringLength 4
+#define _PCD_GET_MODE_SIZE_PcdMaximumAsciiStringLength _PCD_SIZE_PcdMaximumAsciiStringLength */
+#define _PCD_GET_MODE_32_PcdMaximumAsciiStringLength 1000000U /*
+//#define _PCD_SET_MODE_32_PcdMaximumAsciiStringLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdMaximumUnicodeStringLength 13U
+#define _PCD_SIZE_PcdMaximumUnicodeStringLength 4
+#define _PCD_GET_MODE_SIZE_PcdMaximumUnicodeStringLength _PCD_SIZE_PcdMaximumUnicodeStringLength */
+#define _PCD_GET_MODE_32_PcdMaximumUnicodeStringLength 1000000U /*
+//#define _PCD_SET_MODE_32_PcdMaximumUnicodeStringLength ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdControlFlowEnforcementPropertyMask 3U
+#define _PCD_SIZE_PcdControlFlowEnforcementPropertyMask 4
+#define _PCD_GET_MODE_SIZE_PcdControlFlowEnforcementPropertyMask _PCD_SIZE_PcdControlFlowEnforcementPropertyMask
+#define _PCD_VALUE_PcdControlFlowEnforcementPropertyMask 0x0U
+//GLOBAL_REMOVE_IF_UNREFERENCED const UINT32 _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask = _PCD_VALUE_PcdControlFlowEnforcementPropertyMask;
+extern const UINT32 _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask;
+#define _PCD_GET_MODE_32_PcdControlFlowEnforcementPropertyMask _gPcd_FixedAtBuild_PcdControlFlowEnforcementPropertyMask
+//#define _PCD_SET_MODE_32_PcdControlFlowEnforcementPropertyMask ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdSpeculationBarrierType 14U
+#define _PCD_SIZE_PcdSpeculationBarrierType 1
+#define _PCD_GET_MODE_SIZE_PcdSpeculationBarrierType _PCD_SIZE_PcdSpeculationBarrierType
+#define _PCD_VALUE_PcdSpeculationBarrierType 0x01U
+//GLOBAL_REMOVE_IF_UNREFERENCED const UINT8 _gPcd_FixedAtBuild_PcdSpeculationBarrierType = _PCD_VALUE_PcdSpeculationBarrierType;
+extern const UINT8 _gPcd_FixedAtBuild_PcdSpeculationBarrierType;
+#define _PCD_GET_MODE_8_PcdSpeculationBarrierType _gPcd_FixedAtBuild_PcdSpeculationBarrierType
+//#define _PCD_SET_MODE_8_PcdSpeculationBarrierType ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdDebugPrintErrorLevel 5U
+#define _PCD_SIZE_PcdDebugPrintErrorLevel 4
+#define _PCD_GET_MODE_SIZE_PcdDebugPrintErrorLevel _PCD_SIZE_PcdDebugPrintErrorLevel*/
+#define _PCD_GET_MODE_32_PcdDebugPrintErrorLevel 0x80000000U /*
+//#define _PCD_SET_MODE_32_PcdDebugPrintErrorLevel ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdDebugClearMemoryValue 4U
+#define _PCD_SIZE_PcdDebugClearMemoryValue 1
+#define _PCD_GET_MODE_SIZE_PcdDebugClearMemoryValue _PCD_SIZE_PcdDebugClearMemoryValue*/
+#define _PCD_GET_MODE_8_PcdDebugClearMemoryValue 0xAFU /*
+//#define _PCD_SET_MODE_8_PcdDebugClearMemoryValue ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdDebugPropertyMask 6U
+#define _PCD_SIZE_PcdDebugPropertyMask 1
+#define _PCD_GET_MODE_SIZE_PcdDebugPropertyMask _PCD_SIZE_PcdDebugPropertyMask */
+#define _PCD_GET_MODE_8_PcdDebugPropertyMask 0U /*
+//#define _PCD_SET_MODE_8_PcdDebugPropertyMask ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdFixedDebugPrintErrorLevel 9U
+#define _PCD_SIZE_PcdFixedDebugPrintErrorLevel 4
+#define _PCD_GET_MODE_SIZE_PcdFixedDebugPrintErrorLevel _PCD_SIZE_PcdFixedDebugPrintErrorLevel */
+#define _PCD_GET_MODE_32_PcdFixedDebugPrintErrorLevel 0xFFFFFFFFU /*
+//#define _PCD_SET_MODE_32_PcdFixedDebugPrintErrorLevel ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdMaximumDevicePathNodeCount 11U
+#define _PCD_SIZE_PcdMaximumDevicePathNodeCount 4
+#define _PCD_GET_MODE_SIZE_PcdMaximumDevicePathNodeCount _PCD_SIZE_PcdMaximumDevicePathNodeCount */
+#define _PCD_GET_MODE_32_PcdMaximumDevicePathNodeCount 0U /*
+//#define _PCD_SET_MODE_32_PcdMaximumDevicePathNodeCount ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdDriverDiagnosticsDisable 8U
+#define _PCD_SIZE_PcdDriverDiagnosticsDisable 1
+#define _PCD_GET_MODE_SIZE_PcdDriverDiagnosticsDisable _PCD_SIZE_PcdDriverDiagnosticsDisable */
+#define _PCD_GET_MODE_BOOL_PcdDriverDiagnosticsDisable ((BOOLEAN)0U) /*
+//#define _PCD_SET_MODE_BOOL_PcdDriverDiagnosticsDisable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdComponentNameDisable 2U
+#define _PCD_SIZE_PcdComponentNameDisable 1
+#define _PCD_GET_MODE_SIZE_PcdComponentNameDisable _PCD_SIZE_PcdComponentNameDisable */
+#define _PCD_GET_MODE_BOOL_PcdComponentNameDisable ((BOOLEAN)0U) /*
+//#define _PCD_SET_MODE_BOOL_PcdComponentNameDisable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdDriverDiagnostics2Disable 7U
+#define _PCD_SIZE_PcdDriverDiagnostics2Disable 1
+#define _PCD_GET_MODE_SIZE_PcdDriverDiagnostics2Disable _PCD_SIZE_PcdDriverDiagnostics2Disable */
+#define _PCD_GET_MODE_BOOL_PcdDriverDiagnostics2Disable ((BOOLEAN)0U) /*
+//#define _PCD_SET_MODE_BOOL_PcdDriverDiagnostics2Disable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdComponentName2Disable 1U
+#define _PCD_SIZE_PcdComponentName2Disable 1
+#define _PCD_GET_MODE_SIZE_PcdComponentName2Disable _PCD_SIZE_PcdComponentName2Disable
+#define _PCD_VALUE_PcdComponentName2Disable ((BOOLEAN)0U)
+//GLOBAL_REMOVE_IF_UNREFERENCED const BOOLEAN _gPcd_FixedAtBuild_PcdComponentName2Disable = _PCD_VALUE_PcdComponentName2Disable; */
+#define _PCD_GET_MODE_BOOL_PcdComponentName2Disable ((BOOLEAN)0U) /*
+//#define _PCD_SET_MODE_BOOL_PcdComponentName2Disable ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdUgaConsumeSupport 16U
+#define _PCD_SIZE_PcdUgaConsumeSupport 1
+#define _PCD_GET_MODE_SIZE_PcdUgaConsumeSupport _PCD_SIZE_PcdUgaConsumeSupport */
+#define _PCD_GET_MODE_BOOL_PcdUgaConsumeSupport ((BOOLEAN)1U) /*
+//#define _PCD_SET_MODE_BOOL_PcdUgaConsumeSupport ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+#define _PCD_TOKEN_PcdUefiLibMaxPrintBufferSize 15U
+#define _PCD_SIZE_PcdUefiLibMaxPrintBufferSize 4
+#define _PCD_GET_MODE_SIZE_PcdUefiLibMaxPrintBufferSize _PCD_SIZE_PcdUefiLibMaxPrintBufferSize */
+#define _PCD_GET_MODE_32_PcdUefiLibMaxPrintBufferSize 320U /*
+//#define _PCD_SET_MODE_32_PcdUefiLibMaxPrintBufferSize ASSERT(FALSE) // It is not allowed to set value for a FIXED_AT_BUILD PCD
+
+*/ \ No newline at end of file
diff --git a/test_code/hda-contents/MemtestEfi.efi b/test_code/hda-contents/MemtestEfi.efi
deleted file mode 100644
index e56502b..0000000
--- a/test_code/hda-contents/MemtestEfi.efi
+++ /dev/null
Binary files differ
diff --git a/test_code/hdb-contents/MemtestEfi.efi b/test_code/hdb-contents/MemtestEfi.efi
deleted file mode 100644
index faccaca..0000000
--- a/test_code/hdb-contents/MemtestEfi.efi
+++ /dev/null
Binary files differ
diff --git a/test_code/hdb-contents/memtest_log b/test_code/hdb-contents/memtest_log
deleted file mode 100644
index 423156a..0000000
--- a/test_code/hdb-contents/memtest_log
+++ /dev/null
@@ -1 +0,0 @@
-jhgkjhgkjhgjkhgkj
diff --git a/test_code/old_logs/memtest_log_01_Jun_21 b/test_code/old_logs/memtest_log_01_Jun_21
new file mode 100644
index 0000000..f3d1305
--- /dev/null
+++ b/test_code/old_logs/memtest_log_01_Jun_21
@@ -0,0 +1,146 @@
+START LOGGING.
+MemtestEfi started
+test_start(): cpu order = 0
+test_start(): my_cpu_num = 0
+test_start(): my_cpu_ord = 0
+test_start(): Command line parsed, now clear_screen()
+pllm_upper = 0
+vvmaddr = 103571200
+query_memory_table() started.
+vvqaddr = 103571200
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 4096
+NumberOfPages (4K) = 159
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 1048576
+NumberOfPages (4K) = 1792
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 8421376
+NumberOfPages (4K) = 8
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 19922944
+NumberOfPages (4K) = 11318
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 66412544
+NumberOfPages (4K) = 8785
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 103268352
+NumberOfPages (4K) = 54
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 103710720
+NumberOfPages (4K) = 26
+Attribute = 15
+
+query_memory_table(): New EfiConventionalMemory segment found.
+Physical Start = 132120576
+NumberOfPages (4K) = 250
+Attribute = 15
+query_memory_table(): Number of free memory segs = 8
+query_memory_table(): Memory detected in MB = 127
+vvmaddr = 103571200
+pmap.end = 32506
+msegs = 8
+vvmaddr = 103571200
+vvpaddr = 103571200
+vvpaddr = 103571200
+vvmaddr = 103571200
+pmap.end = 32506
+msegs = 8
+print_pmap(): msegs = 8
+vv addr = 103571200
+
+print_pmap(): start = 1
+print_pmap(): end = 160
+
+print_pmap(): start = 256
+print_pmap(): end = 2048
+
+print_pmap(): start = 2056
+print_pmap(): end = 2064
+
+print_pmap(): start = 4864
+print_pmap(): end = 16182
+
+print_pmap(): start = 16214
+print_pmap(): end = 24999
+
+print_pmap(): start = 25212
+print_pmap(): end = 25266
+
+print_pmap(): start = 25320
+print_pmap(): end = 25346
+
+print_pmap(): start = 32256
+print_pmap(): end = 32506
+pmap.end = 32506
+msegs = 8
+pffm_upper = 32506
+vvaaddr = 103571200
+>>>>> 1
+>>>>> 1
+>>>>> 1
+>>>>> 1
+>>>>> 1
+>>>>> 1
+>>>>> 1
+>>>>> 1
+pllm_upper = 32506
+
+get_cpuid() started.
+get_cpuid(): max_cpuid = 13
+get_cpuid(): Vendor ID = G
+finishing get_cpuid().
+
+get_cpuid() started.
+get_cpuid(): max_cpuid = 13
+get_cpuid(): Vendor ID = G
+finishing get_cpuid().
+
+pci_init() started.
+
+pci_conf_read() started.
+pci_conf_read(): bus =0
+pci_conf_read(): dev = 0
+pci_conf_read(): fn = 0
+pci_conf_read(): reg = 10
+pci_conf_read(): result = 0
+pci_check_direct(): pci_conf_type = 1
+get_cache_size() started.
+get_cache_size(): l1_cache = 32
+get_cache_size(): l2_cache = 4096
+get_cache_size(): l3_cache = 16384
+cpu_cache_speed() started.
+init(): vv->fail_safe = 2
+init(): num_cpus = 1
+
+find_controller(): started.
+
+pci_conf_read() started.
+pci_conf_read(): bus =0
+pci_conf_read(): dev = 0
+pci_conf_read(): fn = 0
+pci_conf_read(): reg = 0
+pci_conf_read(): result = 0
+find_controller(): vendor = 32902
+
+pci_conf_read() started.
+pci_conf_read(): bus =0
+pci_conf_read(): dev = 0
+pci_conf_read(): fn = 0
+pci_conf_read(): reg = 2
+pci_conf_read(): result = 0
+find_controller(): device = 4663
+find_controller(): ctrl.index = 127 \ No newline at end of file
diff --git a/test_code/run.sh b/test_code/run.sh
index d86ad42..b2f6f30 100755
--- a/test_code/run.sh
+++ b/test_code/run.sh
@@ -1,22 +1,9 @@
#!/bin/bash
-applications=( "ConfigurationTable.efi"\
- "GetMemoryMap.efi"\
- "GetRootSystemDescriptionPointer.efi"\
- "TextOutput.efi"\
- "ProtocolInformation.efi"\
- "doTest1.efi"\
- "Logger.efi"
- )
-
-#for app in "${applications[@]}"
-#do
-# cp ../../../../edk/edk2/Build/MdeModule/DEBUG_GCC5/X64/$app hda-contents/
-#done
-
#(cd hda-contents; rm memtest_log; echo -n -e '\x00' >> memtest_log)
-sudo kvm -bios OVMF.fd --drive file=fat:rw:hda-contents,index=0,media=disk,format=raw --drive file=fat:rw:hdb-contents,index=1,media=disk,format=raw -no-reboot -net none -cpu host
-#-drive file=vm-disk-5G,format=raw,index=1,media=disk
+sudo kvm -bios OVMF.fd --drive file=fat:rw:hda-contents,index=0,media=disk,format=raw --drive file=fat:rw:hdb-contents,index=1,media=disk,format=raw -net none -cpu host
+#-drive file=vm-disk-2G,format=raw,index=3,media=disk
#-nographic
+#-no-reboot