我正在尝试使用 CreateWellKnownSid
获取内置管理员帐户的众所周知的 SID,以便我可以在其他功能中使用它,但我得到的是参数不正确使用 WinAccountAdministratorSid
作为第一个参数时的错误消息;但是,如果我使用 WinBuiltinAdministratorsSid
或 WinBuiltinUsersSid
它会起作用。不知道发生了什么。
代码:
#include <Windows.h>
#include <wchar.h>
#include <LM.h>
#include <locale.h>
#pragma comment(lib, "Netapi32.lib")
#define MAX_NAME 256
VOID ShowError(DWORD errorCode)
{
//FormatMessageW
DWORD flags = FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS;
LPWSTR errorMessage;
DWORD size = 0;
if (!FormatMessageW(flags, NULL, errorCode, 0, (LPWSTR)&errorMessage, size, NULL))
{
fwprintf(stderr, L"Could not get the format message, error code: %u\n", GetLastError());
exit(1);
}
wprintf(L"\n%s", errorMessage);
LocalFree(errorMessage);
}
int wmain(int argc, WCHAR **argv)
{
_wsetlocale(LC_ALL, L"English");
//LocalAlloc
UINT memFlags = LMEM_FIXED; //Allocates fixed memory
DWORD numOfBytes = SECURITY_MAX_SID_SIZE;
PSID builtInAdminSid;
/*Allocating memory to hold the SID for the
built-in administrator user*/
if (!(builtInAdminSid = LocalAlloc(memFlags, numOfBytes)))
{
ShowError(GetLastError());
return 1;
}
//CreateWellKnownSid
WELL_KNOWN_SID_TYPE accountAdminSid = WinAccountAdministratorSid;
PSID domainSid = NULL;
/*We will ask Windows for the well known Admin SID.
If this function fails, we cannot continue*/
if (!CreateWellKnownSid(accountAdminSid, NULL,
builtInAdminSid, &numOfBytes))
{
ShowError(GetLastError());
LocalFree(builtInAdminSid); //Do not forget to free memory!
return 1;
}
return 0;
}
我做错了什么吗?
编辑:
似乎我必须指定 DomainSid
参数,但如何为本地计算机检索它?
最佳答案
有时 CreateWellKnownSid
需要 DomainSid 参数,原因很简单 - 它将 DomainSid 与众所周知的 rid 连接起来(向 sid 添加一个 SubAuthority) .
要获取DomainSid,我们可以使用LsaQueryInformationPolicy
with PolicyAccountDomainInformation - 检索系统帐户域的名称和 SID。 - 此 api 调用返回 POLICY_ACCOUNT_DOMAIN_INFO
DomainSid
#include <Ntsecapi.h>
ULONG CreateSid()
{
LSA_HANDLE PolicyHandle;
static LSA_OBJECT_ATTRIBUTES oa = { sizeof(oa) };
NTSTATUS status = LsaOpenPolicy(0, &oa, POLICY_VIEW_LOCAL_INFORMATION, &PolicyHandle);
if (0 <= status)
{
PPOLICY_ACCOUNT_DOMAIN_INFO ppadi;
if (0 <= (status = LsaQueryInformationPolicy(PolicyHandle, PolicyAccountDomainInformation, (void**)&ppadi)))
{
PSID sid = alloca(MAX_SID_SIZE);
ULONG cbSid = MAX_SID_SIZE;
if (!CreateWellKnownSid(::WinAccountAdministratorSid, ppadi->DomainSid, sid, &cbSid))
{
status = GetLastError();
}
LsaFreeMemory(ppadi);
}
LsaClose(PolicyHandle);
}
return status;
}
关于CreateWellKnownSid 说 WinAccountAdministratorSid 的参数不正确,但适用于 WinBuiltAdministratorsSid,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48285213/