




У CodeProject есть несколько различных методов, которые вы можете попробовать ... Вы не упомянули, на каких языках вам нужно решение.
Если вы хотите получить к нему доступ через командный файл или что-то в этом роде, вы можете выглядеть как PsGetSid от Sysinternals. Он переводит идентификаторы безопасности в имена и наоборот.
Вы не указали, какой язык вам нужен. Но если вы знакомы с C#, эта статья предлагает как метод WMI, так и более быстрый (хотя и более подробный) метод с использованием Win32 API.
http://www.codeproject.com/KB/cs/processownersid.aspx
Я не думаю, что в настоящее время есть другой способ сделать это без использования WMI или Win32 API.
Это должно дать вам то, что вам нужно:
с использованием System.Security.Principal;
...
var sid = WindowsIdentity.GetCurrent (). Пользователь;
Свойство User объекта WindowsIdentity возвращает идентификатор безопасности для каждого Документы MSDN.
В Win32 вызовите GetTokenInformation, передав дескриптор токена и константу TokenUser. Он заполнит для вас структуру TOKEN_USER. Одним из элементов в нем является SID пользователя. Это BLOB (двоичный), но вы можете превратить его в строку с помощью ConvertSidToStringSid.
Чтобы получить текущий дескриптор токена, используйте OpenThreadToken или OpenProcessToken.
Если вы предпочитаете ATL, у него есть класс CAccessToken, в котором есть много интересного.
.NET имеет свойство Thread.CurrentPrinciple, которое возвращает ссылку IPrincipal. Вы можете получить SID:
IPrincipal principal = Thread.CurrentPrincipal;
WindowsIdentity identity = principal.Identity as WindowsIdentity;
if (identity != null)
Console.WriteLine(identity.User);
Также в .NET вы можете использовать WindowsIdentity.GetCurrent (), которая возвращает текущий идентификатор пользователя:
WindowsIdentity identity = WindowsIdentity.GetCurrent();
if (identity != null)
Console.WriteLine(identity.User);
В C# вы можете использовать либо
using Microsoft.Win32.Security;
...
string username = Environment.UserName + "@" + Environment.GetEnvironmentVariable("USERDNSDOMAIN");
Sid sidUser = new Sid (username);
Или же...
using System.Security.AccessControl;
using System.Security.Principal;
...
WindowsIdentity m_Self = WindowsIdentity.GetCurrent();
SecurityIdentifier m_SID = m_Self.Owner;");
Я нашел другой способ получить SID:
System.Security.Principal.WindowsIdentity id = System.Security.Principal.WindowsIdentity.GetCurrent();
string sid = id.User.AccountDomainSid.ToString();
Это sid домена, а не учетной записи пользователя, используйте id.User.ToString () для sid пользователя
Я считаю, что это самый короткий из них.
UserPrincipal.Current.Sid;
Доступно с .net> = 3.5
ATL::CAccessToken accessToken;
ATL::CSid currentUserSid;
if (accessToken.GetProcessToken(TOKEN_READ | TOKEN_QUERY) &&
accessToken.GetUser(¤tUserSid))
return currentUserSid.Sid();
Это очень лаконично.
И в собственном коде:
function GetCurrentUserSid: string;
hAccessToken: THandle;
userToken: PTokenUser;
dwInfoBufferSize: DWORD;
dw: DWORD;
if not OpenThreadToken(GetCurrentThread, TOKEN_QUERY, True, ref hAccessToken) then
dw <- GetLastError;
if dw <> ERROR_NO_TOKEN then
RaiseLastOSError(dw);
if not OpenProcessToken(GetCurrentProcess, TOKEN_QUERY, ref hAccessToken) then
RaiseLastOSError;
try
userToken <- GetMemory(1024);
try
if not GetTokenInformation(hAccessToken, TokenUser, userToken, 1024, ref dwInfoBufferSize) then
RaiseLastOSError;
Result <- SidToString(userToken.User.Sid);
finally
FreeMemory(userToken);
finally
CloseHandle(hAccessToken);
Этот вопрос помечен как c++, и я отвечаю на языке c++, поэтому я рекомендую использовать инструмент WMI:
Итак, как команды WMI в powershell, следующая команда получает SID пользователя system-pc1:
Get-WmiObject win32_useraccount -Filter "name = 'system-pc1'" | Select-Object sid
Во-первых, вам нужно получить текущий username с помощью нижеуказанного code:
char username[UNLEN+1];
DWORD username_len = UNLEN+1;
GetUserName(username, &username_len);
Теперь вы можете попробовать использовать язык WQL и выполнить этот запрос в c++, как показано ниже (в этом примере я использовал имя пользователя system-pc1 в запросе WQL_WIN32_USERACCOUNT_QUERY:
#define NETWORK_RESOURCE "root\\CIMV2"
#define WQL_LANGUAGE "WQL"
#define WQL_WIN32_USERACCOUNT_QUERY "SELECT * FROM Win32_Useraccount where name='system-pc1'"
#define WQL_SID "SID"
IWbemLocator *pLoc = 0; // Obtain initial locator to WMI to a particular host computer
IWbemServices *pSvc = 0; // To use of connection that created with CoCreateInstance()
ULONG uReturn = 0;
HRESULT hResult = S_OK; // Result when we initializing
IWbemClassObject *pClsObject = NULL; // A class for handle IEnumWbemClassObject objects
IEnumWbemClassObject *pEnumerator = NULL; // To enumerate objects
VARIANT vtSID = { 0 }; // OS name property
// Initialize COM library
hResult = CoInitializeEx(0, COINIT_MULTITHREADED);
if (SUCCEEDED(hResult))
{
// Initialize security
hResult = CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_DEFAULT,
RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, NULL);
if (SUCCEEDED(hResult))
{
// Create only one object on the local system
hResult = CoCreateInstance(CLSID_WbemLocator, 0, CLSCTX_INPROC_SERVER,
IID_IWbemLocator, (LPVOID*)&pLoc);
if (SUCCEEDED(hResult))
{
// Connect to specific host system namespace
hResult = pLoc->ConnectServer(TEXT(NETWORK_RESOURCE), NULL, NULL,
0, NULL, 0, 0, &pSvc);
if (SUCCEEDED(hResult))
{
/* Set the IWbemServices proxy
* So the impersonation of the user will be occurred */
hResult = CoSetProxyBlanket(pSvc, RPC_C_AUTHN_WINNT, RPC_C_AUTHZ_NONE,
NULL, RPC_C_AUTHN_LEVEL_CALL, RPC_C_IMP_LEVEL_IMPERSONATE,
NULL, EOAC_NONE);
if (SUCCEEDED(hResult))
{
/* Use the IWbemServices pointer to make requests of WMI
* For example, query for user account */
hResult = pSvc->ExecQuery(TEXT(WQL_LANGUAGE), TEXT(WQL_WIN32_USERACCOUNT_QUERY),
WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY, NULL, &pEnumerator);
if (SUCCEEDED(hResult))
{
// Go to get the next object from IEnumWbemClassObject
pEnumerator->Next(WBEM_INFINITE, 1, &pClsObject, &uReturn);
if (uReturn != 0)
{
// Get the value of the "sid, ..." property
pClsObject->Get(TEXT(WQL_SID), 0, &vtSID, 0, 0);
VariantClear(&vtSID);
// Print SID
wcout << vtSID.bstrVal;
pClsObject->Release();
pClsObject = NULL;
}
}
}
}
}
}
// Cleanup
pSvc->Release();
pLoc->Release();
pEnumerator->Release();
// Uninitialize COM library
CoUninitialize();
Этот пример работает правильно!
в cmd.exe
whoami /user
если вам это нужно программно, пожалуйста, уточняйте
Опрашивающий конкретно запрашивает решение C++.
Достаточно справедливо, называя system("whoami /user");является технически решением C++, и я должен был указать, что я хотел бы сделать это путем прямого вызова Windows API.
язык программирования / среда?