NtCreateToken example for creating elevated token without user password

Bala Smart 51 Reputation points
2021-06-15T11:17:06.337+00:00

Hi,

I need elevated token for user, So i can achieve this by using NtCreateToken undocumented API. I'm not able to find any examples to call NtCreateToken.

If anybody knowing usage of [NtCreateToken][1], help me!!!!!!
Developer technologies | C++
{count} votes

3 answers

Sort by: Most helpful
  1. Castorix31 91,066 Reputation points
    2021-06-15T14:04:54.96+00:00

    You can find samples from Google, like
    SeCreateTokenPrivilege.cpp
    But I get STATUS_PRIVILEGE_NOT_HELD as Admin on Windows 10
    (cannot enable SE_CREATE_TOKEN_NAME privilege)


  2. RLWA32 50,576 Reputation points
    2021-06-17T22:29:36.047+00:00

    Well, it can be done. Here's a standard user - Bozo with an elevated Administrator command prompt running.

    106630-ntcreatetoken.png


  3. 杨 承浩睿 0 Reputation points
    2025-08-24T13:14:52.8766667+00:00

    #include <Windows.h>#include <winternl.h>

    #include <sddl.h>

    #include <iostream>

    #include <vector>

    #pragma comment(lib, "advapi32.lib")

    // 来自 ntdll.dll 的 NtCreateToken 声明

    extern "C" NTSTATUS NTAPI NtCreateToken(

    PHANDLE TokenHandle,
    
    ACCESS_MASK DesiredAccess,
    
    POBJECT_ATTRIBUTES ObjectAttributes,
    
    TOKEN_TYPE TokenType,
    
    PLUID AuthenticationId,
    
    PLARGE_INTEGER ExpirationTime,
    
    PTOKEN_USER TokenUser,
    
    PTOKEN_GROUPS TokenGroups,
    
    PTOKEN_PRIVILEGES TokenPrivileges,
    
    PTOKEN_OWNER Owner,
    
    PTOKEN_PRIMARY_GROUP PrimaryGroup,
    
    PTOKEN_DEFAULT_DACL DefaultDacl,
    
    PTOKEN_SOURCE TokenSource
    ```);
    
    // 启用指定特权
    
    BOOL EnablePrivilege(LPCWSTR privName) {
    
    

    HANDLE hToken;

    TOKEN_PRIVILEGES tp;

    LUID luid;

    if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken))

    return FALSE;
    

    if (!LookupPrivilegeValue(NULL, privName, &luid)) {

    CloseHandle(hToken);
    
    return FALSE;
    

    }

    tp.PrivilegeCount = 1;

    tp.Privileges[0].Luid = luid;

    tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

    AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(tp), NULL, NULL);

    CloseHandle(hToken);

    return (GetLastError() == ERROR_SUCCESS);

    
    int wmain() {
    
    

    // 1️⃣ 启用创建令牌的特权

    if (!EnablePrivilege(L"SeCreateTokenPrivilege")) {

    std::wcout << L"[-] 无法启用 SeCreateTokenPrivilege\n";
    
    return 1;
    

    }

    // 2️⃣ 基本对象属性

    OBJECT_ATTRIBUTES objAttr = {};

    objAttr.Length = sizeof(objAttr);

    // 3️⃣ 身份标识符(可自定义)

    LUID authId = { 999, 0 };

    // 4️⃣ 令牌过期时间(-1 = 永不过期)

    LARGE_INTEGER expTime;

    expTime.QuadPart = -1;

    // 5️⃣ 主用户 SID(SYSTEM)

    PSID pUserSid = NULL;

    ConvertStringSidToSid(L"S-1-5-18", &pUserSid); // Local System

    TOKEN_USER tokenUser = {};

    tokenUser.User.Sid = pUserSid;

    tokenUser.User.Attributes = 0;

    // 6️⃣ 用户组(这里示例只加 Administrators)

    std::vector<SID_AND_ATTRIBUTES> groups(1);

    ConvertStringSidToSid(L"S-1-5-32-544", &groups[0].Sid); // Administrators

    groups[0].Attributes = SE_GROUP_ENABLED | SE_GROUP_ENABLED_BY_DEFAULT | SE_GROUP_MANDATORY;

    TOKEN_GROUPS tokenGroups = { (DWORD)groups.size(), groups.data() };

    // 7️⃣ 特权(开启 Debug 权限)

    LUID luid;

    LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &luid);

    TOKEN_PRIVILEGES tokenPrivs = {};

    tokenPrivs.PrivilegeCount = 1;

    tokenPrivs.Privileges[0].Luid = luid;

    tokenPrivs.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

    // 8️⃣ Token Owner

    TOKEN_OWNER tokenOwner = { pUserSid };

    // 9️⃣ Primary Group

    TOKEN_PRIMARY_GROUP primaryGroup = { pUserSid };

    // 🔟 Default DACL(默认访问控制表)

    TOKEN_DEFAULT_DACL defaultDacl = {};

    defaultDacl.DefaultDacl = NULL; // 无默认 DACL

    // 1️⃣1️⃣ Token 来源信息

    TOKEN_SOURCE tokenSource = { "CppTok" };

    AllocateLocallyUniqueId(&tokenSource.SourceIdentifier);

    // 1️⃣2️⃣ 创建令牌

    HANDLE hToken = NULL;

    NTSTATUS status = NtCreateToken(

    &hToken,
    
    TOKEN_ALL_ACCESS,
    
    &objAttr,
    
    TokenPrimary,
    
    &authId,
    
    &expTime,
    
    &tokenUser,
    
    &tokenGroups,
    
    &tokenPrivs,
    
    &tokenOwner,
    
    &primaryGroup,
    
    &defaultDacl,
    
    &tokenSource
    

    );

    if (status == STATUS_SUCCESS) {

    std::wcout << L"[+] 成功创建令牌\n";
    
    // 1️⃣3️⃣ 使用令牌启动 cmd.exe
    
    STARTUPINFO si = { sizeof(si) };
    
    PROCESS_INFORMATION pi;
    
    if (CreateProcessAsUser(hToken, NULL, (LPWSTR)L"C:\\Windows\\System32\\cmd.exe",
    
        NULL, NULL, FALSE, CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
    
        std::wcout << L"[+] 已使用新令牌启动进程\n";
    
        CloseHandle(pi.hProcess);
    
        CloseHandle(pi.hThread);
    
    } else {
    
        std::wcout << L"[-] CreateProcessAsUser 失败,错误码:" << GetLastError() << L"\n";
    
    }
    
    CloseHandle(hToken);
    

    } else {

    std::wcout << L"[-] NtCreateToken 失败,状态码:0x" << std::hex << status << L"\n";
    

    }

    LocalFree(pUserSid);

    return 0;

    0 comments No comments

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.