I know it's possible to read a UEFI
variable with e.g. GetFirmwareEnvironmentVariable()
given the name of the variable and the GUID
of the namespace. But is it possible to get a list of namespaces and names that are available? Say, e.g. I wanted to write a utility to backup or dump all the variables. Reading documentation and googling has found nothing.
for this possible use NtEnumerateSystemEnvironmentValuesEx
and need have SE_SYSTEM_ENVIRONMENT_PRIVILEGE
demo code of dump all:
NTSTATUS DumpSystemEnv()
{
BOOLEAN b;
ULONG cb = 0x1000;
NTSTATUS status = RtlAdjustPrivilege(SE_SYSTEM_ENVIRONMENT_PRIVILEGE, TRUE, FALSE, &b);
do
{
status = STATUS_NO_MEMORY;
if (PVOID Buffer = LocalAlloc(LMEM_FIXED, cb))
{
if (0 <= (status = NtEnumerateSystemEnvironmentValuesEx(SystemEnvironmentValueInformation, Buffer, &cb)))
{
union {
PVOID pv;
PVARIABLE_NAME_AND_VALUE pvna;
ULONG_PTR up;
PBYTE pb;
};
pv = Buffer;
ULONG NextEntryOffset = 0;
do
{
up += NextEntryOffset;
DbgPrint("%08x:{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x} \"%ws\"\n",
pvna->Attributes,
pvna->VendorGuid.Data1,
pvna->VendorGuid.Data2,
pvna->VendorGuid.Data3,
pvna->VendorGuid.Data4[0],
pvna->VendorGuid.Data4[1],
pvna->VendorGuid.Data4[2],
pvna->VendorGuid.Data4[3],
pvna->VendorGuid.Data4[4],
pvna->VendorGuid.Data4[5],
pvna->VendorGuid.Data4[6],
pvna->VendorGuid.Data4[7],
pvna->Name);
PSTR buf = 0;
cb = 0;
while (CryptBinaryToStringA(pb + pvna->ValueOffset, pvna->ValueLength, CRYPT_STRING_HEXASCII, buf, &cb))
{
if (buf)
{
PSTR psz = buf;
ULONG len;
do
{
DbgPrint("%.*s", len = min(0x80, cb), psz);
} while (psz += len, cb -= len);
break;
}
if (!(buf = new char[cb]))
{
break;
}
}
if (buf)
{
delete [] buf;
}
} while (NextEntryOffset = pvna->NextEntryOffset);
}
LocalFree(Buffer);
}
} while (STATUS_BUFFER_TOO_SMALL == status);
return status;
}