ANTICHAT.XYZ    VIDEO.ANTICHAT.XYZ    НОВЫЕ СООБЩЕНИЯ    ФОРУМ  
Баннер 1   Баннер 2
Antichat снова доступен.
Форум Antichat (Античат) возвращается и снова открыт для пользователей. Здесь обсуждаются безопасность, программирование, технологии и многое другое. Сообщество снова собирается вместе.
Новый адрес: forum.antichat.xyz
Вернуться   Форум АНТИЧАТ > Программирование > С/С++, C#, Delphi, .NET, Asm
   
Ответ
 
Опции темы Поиск в этой теме Опции просмотра

[BC++] Запуск .exe из ресурсов
  #1  
Старый 19.12.2008, 13:22
Аватар для MuForum
MuForum
Новичок
Регистрация: 30.11.2008
Сообщений: 3
Провел на форуме:
15414

Репутация: 0
По умолчанию [BC++] Запуск .exe из ресурсов

Доброе время суток!
- Пишу программу на 'Borland C++ Builder 6.0 SP4';
- Задача: Запустить программу 1.exe из ресурсов моей программу main.exe не извлекая её на диск.
- То есть, необходимо запустить программу main.exe, затем извлечь из ресурсов 1.exe заменяя память другого процесса, чтобы запустилась программа 1.exe;
- Данную схему вроде частично реализовал(Без переноса таблицы импорта и релоков).

# TRFR.cpp:
Код:
#include "TRFR.h"
#include "Main.h"
//---------------------------------------------------------------------------
bool (*pNtdllFunc)(HANDLE, LPVOID);
//---------------------------------------------------------------------------

TRFR::TRFR()
{
    // ----
}
//---------------------------------------------------------------------------

TRFR::~TRFR()
{
    // ----
}
//---------------------------------------------------------------------------

bool __fastcall TRFR::ZwUnmapViewOfSection(HANDLE ProcessHandle, LPVOID BaseAddress)
{
    bool Result = false;
    // -----
    try
    {
        HMODULE hNtdll = LoadLibrary("ntdll.dll");
        if(hNtdll != NULL)
        {
            (FARPROC &)pNtdllFunc = GetProcAddress(hNtdll, "ZwUnmapViewOfSection");
            pNtdllFunc(ProcessHandle, BaseAddress);
            FreeLibrary(hNtdll);
            Result = true;
        }
    }
    catch(...) {}
    // ----
    return Result;
}
//---------------------------------------------------------------------------

ULONG __fastcall TRFR::Protect(ULONG characteristics)
{
    const ULONG mapping[8] = {PAGE_NOACCESS, PAGE_EXECUTE, PAGE_READONLY, PAGE_EXECUTE_READ, PAGE_READWRITE, PAGE_EXECUTE_READWRITE, PAGE_READWRITE, PAGE_EXECUTE_READWRITE};
    return mapping[characteristics >> 29];
}
//---------------------------------------------------------------------------

bool __fastcall TRFR::GetMemoryToSection(HANDLE hProcess, LPVOID Mapping, LPVOID pRes, USHORT NumberOfSections, PIMAGE_SECTION_HEADER pSection)
{
    bool Result = true;
    // ----
    for (USHORT i = 0; i < NumberOfSections; i++)
    {
        Result = WriteProcessMemory(hProcess,
            (LPVOID)(DWORD(Mapping) + pSection[i].VirtualAddress),
            (LPCVOID)(DWORD(pRes) + pSection[i].PointerToRawData),
            pSection[i].SizeOfRawData, NULL);
        // ----
        if(!Result) break;
    }
    // ----
    return Result;
}
//---------------------------------------------------------------------------

DWORD __fastcall TRFR::RunFromResurs(LPTSTR ComLine, LPCTSTR ResName, LPCTSTR ResType)
{
    bool Result = true;
    DWORD pPID = 0;
    // ----
    PROCESS_INFORMATION pi;
    STARTUPINFO si;
    ZeroMemory(&pi, sizeof(pi));
    ZeroMemory(&si, sizeof(si));
    si.cb = sizeof(STARTUPINFO);
    // ----
    PIMAGE_DOS_HEADER pDos = NULL;
    PIMAGE_NT_HEADERS pNt = NULL;
    PIMAGE_FILE_HEADER pFile = NULL;
    PIMAGE_OPTIONAL_HEADER pOptional = NULL;
    PIMAGE_SECTION_HEADER pSection = NULL;
    // ----
    LPVOID x = NULL, pRes = NULL, Mapping = NULL;
    HANDLE hProcess = NULL;
    HMODULE hInst = GetModuleHandle(NULL);
        SIZE_T bsize = 0;
    // ----
    pRes = LockResource(LoadResource(hInst, FindResource(hInst, ResName, ResType)));
    if(pRes != NULL)
    {
        pDos = PIMAGE_DOS_HEADER(pRes);
        if (pDos->e_magic == IMAGE_DOS_SIGNATURE)
        {
            pNt = PIMAGE_NT_HEADERS(PCHAR(pRes) + pDos->e_lfanew);
            if (pNt->Signature == IMAGE_NT_SIGNATURE)
            {
                pFile = &pNt->FileHeader;
                pOptional = &pNt->OptionalHeader;
                pSection = IMAGE_FIRST_SECTION(pNt);
                // ----
                Result = CreateProcess(NULL, ComLine, NULL, NULL, FALSE, CREATE_SUSPENDED, NULL, NULL, &si, &pi);
                if(Result)
                {
                    FMain->WLog("CreateProcess()");
                    hProcess = pi.hProcess;
                    pPID = pi.dwProcessId;
                    CONTEXT context;
                    context.ContextFlags = CONTEXT_FULL;
                    // ----
                    Result = GetThreadContext(pi.hThread, &context);
                    if(Result)
                    {
                        FMain->WLog("GetThreadContext()");
                        Result = ReadProcessMemory(pi.hProcess, (LPCVOID)(context.Ebx + 8), &x, sizeof(x), &bsize);
                        if (Result)
                        {
                            FMain->WLog("ReadProcessMemory()");
                            Result = ZwUnmapViewOfSection(pi.hProcess, x);
                            if(Result)
                            {
                                FMain->WLog("ZwUnmapViewOfSection()");
                                Mapping = VirtualAllocEx(pi.hProcess, (LPVOID)pOptional->ImageBase, pOptional->SizeOfImage, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE);
                                if(Mapping != NULL)
                                {
                                    FMain->WLog("VirtualAllocEx()");
                                    //DWORD previousProtection = 0;
                                    //Result = VirtualProtectEx(pi.hProcess, Mapping, pOptional->SizeOfHeaders, PAGE_EXECUTE_READWRITE, &previousProtection);
                                    Result = WriteProcessMemory(pi.hProcess, Mapping, (LPCVOID)pRes, pOptional->SizeOfHeaders, &bsize);
                                    if(Result)
                                    {
                                        FMain->WLog("WriteProcessMemory()");
                                        Result = GetMemoryToSection(pi.hProcess, Mapping, pRes, pFile->NumberOfSections, pSection);
                                        if(Result)
                                        {
                                            FMain->WLog("GetMemoryToSection()");
                                            Result = WriteProcessMemory(pi.hProcess, (LPVOID)(context.Ebx + 8), &Mapping, sizeof(Mapping), 0);
                                            if(Result)
                                            {
                                                context.Eax = (ULONG)Mapping + pOptional->AddressOfEntryPoint;
                                                // ----
                                                SetThreadContext(pi.hThread, &context);
                                                ResumeThread(pi.hThread);
                                            }
                                        }
                                    }
                                    else FMain->WLog("[WPM1] GetLastError = '" + (String)GetLastError() + "'");
                                }
                                else Result = false;
                            }
                        }
                    }
                    // ----
                    if(!Result && hProcess != NULL) TerminateProcess(hProcess, 0);
                    // ----
                    CloseHandle(pi.hProcess);
                    CloseHandle(pi.hThread);
                }
            }
        }
    }
    // -----
    FreeResource(pRes);
    // ----
    return (Result) ? pPID : 0;
}
//---------------------------------------------------------------------------
# TRFR.h:
Код:
#include <Windows.h>
#include <tlhelp32.h>
#include <stdio.h>
//---------------------------------------------------------------------------
class TRFR
{
    private:
        bool __fastcall ZwUnmapViewOfSection(HANDLE ProcessHandle, LPVOID BaseAddress);
        ULONG __fastcall Protect(ULONG characteristics);
        bool __fastcall GetMemoryToSection(HANDLE hProcess, LPVOID Mapping, LPVOID pRes, USHORT NumberOfSections, PIMAGE_SECTION_HEADER pSection);
    public:
        TRFR();
        ~TRFR();
        DWORD __fastcall RunFromResurs(LPTSTR AppName, LPCTSTR ResName, LPCTSTR ResType);
};
//---------------------------------------------------------------------------
- Проблема в том, что если программу компилировать в режиме 'Debug', то всё нормально, запускается и выполняет свои функции, если скомпилировать в режиме 'Release', то на строчке 128:
Код:
Result = WriteProcessMemory(pi.hProcess, Mapping, (LPCVOID)pRes, pOptional->SizeOfHeaders, &bsize);
- GetLastError() выдаёт ошибку:

ERROR_PARTIAL_COPY
299
0x12B
- Only part of a ReadProcessMemory or WriteProcessMemory request was completed.
- Вроде использую VirtualProtectEx(), вообщем что-то не могу сам допереть...


# Добавлено: У Borland есть удобный класс для извлечения из ресурсов 'TResourceStream', но он мне не очень нравится. (Это так, вода...)


P.S. -> Убедительно прошу, не нужно мне советовать следующее: А чем плох приём извлечения программы на диск с последующим запуском...
- Задача конкретно поставлена. (Файл не должен извлекаться из ресурсов)

Последний раз редактировалось MuForum; 19.12.2008 в 14:21..
 
Ответить с цитированием

  #2  
Старый 19.12.2008, 14:13
Аватар для izlesa
izlesa
Участник форума
Регистрация: 03.01.2008
Сообщений: 156
Провел на форуме:
414311

Репутация: 110
Отправить сообщение для izlesa с помощью ICQ
По умолчанию

Не помню, имеет ли процесс создаваемый с атрибутами безопасности по умолчанию права PROCESS_VM_WRITE ... Судя по всему прав для записи не хватает. Нда и у мну начали появлятся смутные подозрения, что атрибуты безопасности по умолчанию для релиза и дебага разные используются ???
Попробуй вручную задать нужные права. Если нет, будем дальше смотреть )).
 
Ответить с цитированием

  #3  
Старый 19.12.2008, 14:21
Аватар для MuForum
MuForum
Новичок
Регистрация: 30.11.2008
Сообщений: 3
Провел на форуме:
15414

Репутация: 0
По умолчанию

Цитата:
Сообщение от izlesa  
Не помню, имеет ли процесс создаваемый с атрибутами безопасности по умолчанию права PROCESS_VM_WRITE ... Судя по всему прав для записи не хватает. Нда и у мну начали появлятся смутные подозрения, что атрибуты безопасности по умолчанию для релиза и дебага разные используются ???
Попробуй вручную задать нужные права. Если нет, будем дальше смотреть )).
- Мои тестирования приводят к тому, что правила безопастности для режимов Debug и Release разные.
- Сейчас посмотрю в инете, покуралесю и отпишусь.


# Добавлено: Что-то я не могу понять, как задать атрибут PROCESS_VM_WRITE через функцию CreateProcess(). (Через OpenProcess Нашел, а вот с Create что-то не могу)
- Метод научного тыка тоже не помог.
- На MSDN касательно структуры: SECURITY_ATTRIBUTES практически ничего не сказано)

Последний раз редактировалось MuForum; 19.12.2008 в 14:43..
 
Ответить с цитированием

  #4  
Старый 19.12.2008, 16:58
Аватар для MuForum
MuForum
Новичок
Регистрация: 30.11.2008
Сообщений: 3
Провел на форуме:
15414

Репутация: 0
По умолчанию

Код:
void TFMain::EnableDebugPriv(void)
{
        String Text = "";
        HANDLE hToken;
        LUID sedebugnameValue;
        TOKEN_PRIVILEGES tkp;
        // enable the SeDebugPrivilege;
        if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken))
        {
                Text = "OpenProcessToken() failed, Error = %d SeDebugPrivilege is not available. " + (String)GetLastError();
                //wprintf( L"OpenProcessToken() failed, Error = %d SeDebugPrivilege is not available.\n", GetLastError());
                WLog(Text);
                return;
        }
        // ----
        if (!LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &sedebugnameValue))
        {
                Text = "LookupPrivilegeValue() failed, Error = %d SeDebugPrivilege is not available. " + (String)GetLastError();
                //wprintf( L"LookupPrivilegeValue() failed, Error = %d SeDebugPrivilege is not available.\n", GetLastError());
                WLog(Text);
                CloseHandle(hToken);
                return;
        }
        // ----
        tkp.PrivilegeCount = 1;
        tkp.Privileges[0].Luid = sedebugnameValue;
        tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
        // ----
         if (!AdjustTokenPrivileges(hToken, FALSE, &tkp, sizeof tkp, NULL, NULL))
         {
                Text = "AdjustTokenPrivileges() failed, Error = %d SeDebugPrivilege is not available. " + (String)GetLastError();
                //wprintf( L"AdjustTokenPrivileges() failed, Error = %d SeDebugPrivilege is not available.\n", GetLastError());
                WLog(Text);
         }
         // ----
         CloseHandle(hToken);
         WLog("End function...");
}
- Использую эту функцию.
 
Ответить с цитированием

  #5  
Старый 19.12.2008, 21:11
Аватар для izlesa
izlesa
Участник форума
Регистрация: 03.01.2008
Сообщений: 156
Провел на форуме:
414311

Репутация: 110
Отправить сообщение для izlesa с помощью ICQ
По умолчанию

Код:
http://social.msdn.microsoft.com/forums/en-US/windowssecurity/thread/755d47b7-ab7a-42c5-bbaa-e14793b2c4d4/

Processes with the debug privilege will be able to bypass the DACL.

Also, the parent of your process will have that right too.
Наверно в этом дело в дебаге и релизе )).

Вот про права для процесса
http://msdn.microsoft.com/en-us/library/ms684880.aspx
В кратце, можно задать используя специальную функцию для создания процесса, или заполнить секьюрити дескриптор, ктр как раз таки находится в структуре секьюрити аттрибутес. Он не прозрачен и управляется через спец функции
 
Ответить с цитированием
Ответ



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
запуск .exe под linux null_access *nix 4 01.06.2006 14:29



Здесь присутствуют: 1 (пользователей: 0 , гостей: 1)
 


Быстрый переход




ANTICHAT.XYZ