最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

Is it possible to get a list of UEFI variables in Windows? - Stack Overflow

programmeradmin4浏览0评论

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.

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.

Share Improve this question edited Mar 20 at 23:10 Hilory 2,1417 gold badges14 silver badges30 bronze badges asked Mar 20 at 23:05 Edward FalkEdward Falk 10.2k11 gold badges83 silver badges123 bronze badges
Add a comment  | 

2 Answers 2

Reset to default 2

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;
}

OK, thanks to @RbMm for giving me the clues I needed. I'll summarize my own findings here:

The key API is NTSYSCALLAPI NTSTATUS NTAPI NtEnumerateSystemEnvironmentValuesEx(ULONG InformationClass, PVOID Buffer, PULONG BufferLength); which seems to be undocumented, at least officially. The links that RbMm provided lead to 3rd-party header files that contain the needed definitions. Call once with Buffer=NULL and BufferLength=0 to obtain the actual required buffer length. Then allocate the buffer and call again.

This function is part of the ntdll.dll library which all applications link to.

发布评论

评论列表(0)

  1. 暂无评论