Вывод в "чужую" консоль

Тема в разделе "WASM.WIN32", создана пользователем set, 29 апр 2007.

  1. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    asmfan
    с импортом нестандартных библиотек, конечно, придется повозиться)

    вот улучшенный код.
    Функция DWORD TransferProgramEx(HANDLE hProcess) переносит код программы в чужое адресное пространство. Если там адреса заняты, выбирается первый свободный участок достаточного размера и туда переносится программа с применением фиксапов (собирать, конечно, нужно с ними).
    Возвращает дельту в базах, 0 - если загружено по тому же адресу, -1 если загрузка не удалась.

    Код (Text):
    1. // Get VA
    2. #define RVATOVA( base, offset )(((DWORD)(base) + (DWORD)(offset)))
    3.  
    4. // Move program's memory
    5. void __CopyMemoryAcrossProcesses( HANDLE hProcess, char* pMemLocal, char* pMemRemote )
    6. {
    7.     DWORD dwOldProt, dwNumBytes, i;
    8.     MEMORY_BASIC_INFORMATION mbi;
    9.      
    10.     VirtualQueryEx(hProcess, pMemRemote, &mbi, sizeof(MEMORY_BASIC_INFORMATION));
    11.     while (mbi.Protect!=PAGE_NOACCESS && mbi.RegionSize!=0)
    12.     {
    13.         if (!(mbi.Protect & PAGE_GUARD))
    14.         {
    15.             for (i = 0; i < mbi.RegionSize; i += 0x1000)
    16.             {
    17.                 VirtualProtectEx(hProcess, pMemRemote + i, 0x1000,PAGE_EXECUTE_READWRITE, &dwOldProt);
    18.                 WriteProcessMemory(hProcess, pMemRemote + i, pMemLocal + i, 0x1000, &dwNumBytes);
    19.             }
    20.         }
    21.         pMemLocal += mbi.RegionSize;
    22.         pMemRemote += mbi.RegionSize;
    23.         VirtualQueryEx(hProcess, pMemRemote, &mbi, sizeof(MEMORY_BASIC_INFORMATION));  
    24.     }
    25. }
    26.  
    27. DWORD TransferProgramEx(HANDLE hProcess)
    28. /*
    29.  Return value: image base delta, -1 on error
    30. */
    31. {
    32.     HMODULE hmodule = GetModuleHandle(0);
    33.     DWORD dwSize = ((PIMAGE_OPTIONAL_HEADER)((LPVOID)((BYTE *)(hmodule) + ((PIMAGE_DOS_HEADER)(hmodule))->e_lfanew +
    34.         sizeof(DWORD) + sizeof(IMAGE_FILE_HEADER))))->SizeOfImage;
    35.  
    36.     MEMORY_BASIC_INFORMATION mbi = {0};
    37.     VirtualQueryEx( hProcess, hmodule, &mbi, sizeof(mbi) );
    38.  
    39.     LPVOID Allocated;
    40.  
    41.     // Memory isn't free, relocate
    42.     if( mbi.Protect!=PAGE_NOACCESS && mbi.RegionSize!=0 )
    43.     {
    44. __try_relocate:
    45.         LPVOID DesiredAddress = hmodule;
    46.         *(DWORD*)&DesiredAddress += mbi.RegionSize;
    47.  
    48.         for(;;)
    49.         {
    50.             Allocated = VirtualAllocEx( hProcess, DesiredAddress, dwSize, MEM_RESERVE|MEM_COMMIT, PAGE_EXECUTE_READWRITE );
    51.             if( Allocated )
    52.                 break;
    53.             *(DWORD*)&DesiredAddress += dwSize;
    54.         }
    55.     }
    56.     else
    57.     {
    58.         Allocated = VirtualAllocEx( hProcess, hmodule, dwSize, MEM_RESERVE|MEM_COMMIT, PAGE_EXECUTE_READWRITE );
    59.         if( !Allocated )
    60.             goto __try_relocate;
    61.     }
    62.  
    63.     // move memory
    64.     __CopyMemoryAcrossProcesses( hProcess, (char*) hmodule, (char*) Allocated );
    65.  
    66.     DWORD ImageBaseDelta = (DWORD)Allocated - (DWORD)hmodule;
    67.  
    68.     // Nonzero imagebase delta
    69.     if( ImageBaseDelta )
    70.     {
    71.         // Apply fixups
    72.         typedef struct
    73.         {
    74.             WORD    Offset:12;
    75.             WORD    Type:4;
    76.         } IMAGE_FIXUP_ENTRY, *PIMAGE_FIXUP_ENTRY;
    77.  
    78.         PIMAGE_OPTIONAL_HEADER poh =
    79.             (PIMAGE_OPTIONAL_HEADER)(
    80.                 (DWORD)hmodule
    81.                 + ((PIMAGE_DOS_HEADER)hmodule)->e_lfanew
    82.                 + sizeof(IMAGE_NT_SIGNATURE)
    83.                 + sizeof(IMAGE_FILE_HEADER)
    84.             );
    85.  
    86.         // No fixups?
    87.         if( !poh->DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress )
    88.         {
    89.             VirtualFreeEx( hProcess, Allocated, dwSize, MEM_DECOMMIT );
    90.             VirtualFreeEx( hProcess, Allocated, dwSize, MEM_RELEASE  );
    91.             return -1;
    92.         }
    93.  
    94.         PIMAGE_BASE_RELOCATION Reloc = (PIMAGE_BASE_RELOCATION) RVATOVA(poh->DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress, hmodule);
    95.         int i = 0;
    96.  
    97.         // Process fixups
    98.         for( PIMAGE_FIXUP_ENTRY Fixup = (PIMAGE_FIXUP_ENTRY)( (DWORD)Reloc + sizeof(IMAGE_BASE_RELOCATION) );
    99.              (DWORD)Fixup < (DWORD)Reloc + Reloc->SizeOfBlock -2;
    100.              Fixup ++, i ++
    101.                  )
    102.         {
    103.             if( Fixup->Type == IMAGE_REL_BASED_HIGHLOW )
    104.             {
    105.                 DWORD* Patch = (DWORD*)RVATOVA( Reloc->VirtualAddress + Fixup->Offset, Allocated );
    106.                
    107.                 DWORD t, r;
    108.                 BOOL b = 1;
    109.  
    110.                 // correct fixup
    111.                 b &= ReadProcessMemory( hProcess, Patch, &t, 4, &r );
    112.                 t += ImageBaseDelta;
    113.                 b &= WriteProcessMemory( hProcess, Patch, &t, 4, &r );
    114.  
    115.                 if( !b )
    116.                 {
    117.                     // smth wrong
    118.                     VirtualFreeEx( hProcess, Allocated, dwSize, MEM_DECOMMIT );
    119.                     VirtualFreeEx( hProcess, Allocated, dwSize, MEM_RELEASE  );
    120.                     return -1;
    121.                 }
    122.             }
    123.             else
    124.             {
    125.                 // unsupported fixup type
    126.                 VirtualFreeEx( hProcess, Allocated, dwSize, MEM_DECOMMIT );
    127.                 VirtualFreeEx( hProcess, Allocated, dwSize, MEM_RELEASE  );
    128.                 return -1;
    129.             }
    130.         }
    131.     }
    132.  
    133.     return ImageBaseDelta;
    134. }
     
  2. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    А не достаточно ли проверять State - MEM_FREE и RegionSize >= требуемый размер, а не атрибуты защиты страниц?
     
  3. set

    set New Member

    Публикаций:
    0
    Регистрация:
    13 янв 2006
    Сообщения:
    27
    Можно спросить, а для чего нам копировать всю программу?
     
  4. rmn

    rmn Well-Known Member

    Публикаций:
    0
    Регистрация:
    23 ноя 2004
    Сообщения:
    2.348
    set
    например,
    msdn:
    (для XP)
     
  5. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    для удобства =) если не нравится, копируй только код поточной функции + данные + импорт, и корректируй фиксапы для потока

    asmfan
    имхо без ощутимой разницы)
     
  6. set

    set New Member

    Публикаций:
    0
    Регистрация:
    13 янв 2006
    Сообщения:
    27
    rmn
    Во красавец! Спасибо.
    2Great:
    Видишь а ты велосипед устраивал.
     
  7. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    И кстати поиск свободного места совершенно необязателен, ибо VirtualAllocEx
    Этим занимается система.
     
  8. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    asmfan
    не знаю как оно ищет, у меня получались весьма странные результаты=\
     
  9. Freeman

    Freeman New Member

    Публикаций:
    0
    Регистрация:
    10 фев 2005
    Сообщения:
    1.385
    Адрес:
    Ukraine
    еще стоит при инжекте всего образа с фиксапами после корректировки фиксапов делоть корректировку импорта и подгрузку нужных либ. так как может оказаться что какаято либа будет загружена не по тому же адресу(я не про кернел), либо быть вообще не загруженной.
    и вся обработка может быть засунута в инжектируемый код, что позволит лишний раз не юзать write/readprocmem
     
  10. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    Great
    Самих Reloc блоков может присутствовать столько, что каждый покрывает 4К пространство, поэтому не только fixup'ы надо считать, но и к-во IMAGE_BASE_RELOCATION.
     
  11. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    asmfan
    не понял, это ты к чему
     
  12. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    Код (Text):
    1. PIMAGE_BASE_RELOCATION Reloc = (PIMAGE_BASE_RELOCATION) RVATOVA(poh->DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress, hmodule);
    И далее считаешь к-во fixup'ов в данном блоке. Блоков может быть много, т.к. 12битовое смещение каждого фиксапа в данном блоке (Fixup->Offset) адресует 4К памяти.
     
  13. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    хм в смысле их может быть много. а как тогда обработать все фиксапы то?
     
  14. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    В таблице директорий общий размер всех блоков и смещений, блоки распологаются последовательно, т.е. каждый следующий блок распологается после смещений предыдущего.
    [added]
    Как пример этого всего, посмотри под Hiew екзешку (f8->f10->fixups).
     
  15. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    хек. не знал) сенкс.
     
  16. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    Это всё актуально, если у тебя кода в твоей проге на 4К... А так и с одним блоком прокатит.
     
  17. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    asmfan
    просто мне один раз надо было большую прогу перенести, фиксапнул только первый блок (про другие не знал) и удивлялся, почему не все адреса поменялись :))
     
  18. Freeman

    Freeman New Member

    Публикаций:
    0
    Регистрация:
    10 фев 2005
    Сообщения:
    1.385
    Адрес:
    Ukraine
    таблицу директорий вобще не трогал. просто смотрел когда нули пойдут.
     
  19. asmfan

    asmfan New Member

    Публикаций:
    0
    Регистрация:
    10 июл 2006
    Сообщения:
    1.004
    Адрес:
    Abaddon
    Не выход абсолютно, релоки не обязаны находиться в отдельной секции, а как следствие нет выравнивания нулями. (пример директива DATA FIXUPS в фасме - в любом месте может быть прописана)
     
  20. gribodemon

    gribodemon New Member

    Публикаций:
    0
    Регистрация:
    17 июн 2009
    Сообщения:
    138
    Great
    Чёто нигде не видел пофиксеный вариант твоего кодеса.
    Выкладываю:

    Код (Text):
    1.         PIMAGE_BASE_RELOCATION Reloc = (PIMAGE_BASE_RELOCATION) RVATOVA(poh->DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress, hmodule);
    2.         // Process fixups
    3.  
    4.         for (; Reloc->VirtualAddress > 0; )
    5.         {
    6.             PIMAGE_FIXUP_ENTRY Fixup = (PIMAGE_FIXUP_ENTRY)( (DWORD)Reloc + sizeof(IMAGE_BASE_RELOCATION) );
    7.             for (DWORD i=0; i<((Reloc->SizeOfBlock-sizeof(IMAGE_BASE_RELOCATION)) / 2); i++, Fixup++)
    8.             {
    9.                 if( Fixup->Type == IMAGE_REL_BASED_HIGHLOW )
    10.                 {
    11.                     DWORD* Patch = (DWORD*)RVATOVA( Reloc->VirtualAddress + Fixup->Offset, Allocated );
    12.                     DWORD t, r;
    13.                     BOOL b = 1;
    14.  
    15.                     // correct fixup
    16.                     b &= ReadProcessMemory( hProcess, Patch, &t, 4, &r );
    17.                     t += ImageBaseDelta;
    18.                     b &= WriteProcessMemory( hProcess, Patch, &t, 4, &r );
    19.  
    20.                     if( !b )
    21.                     {
    22.                         // smth wrong
    23.                         VirtualFreeEx( hProcess, Allocated, dwSize, MEM_DECOMMIT );
    24.                         VirtualFreeEx( hProcess, Allocated, dwSize, MEM_RELEASE  );
    25.                         return -1;
    26.                     }
    27.                 }
    28.                 else
    29.                 {
    30.                     // unsupported fixup type
    31.                     VirtualFreeEx( hProcess, Allocated, dwSize, MEM_DECOMMIT );
    32.                     VirtualFreeEx( hProcess, Allocated, dwSize, MEM_RELEASE  );
    33.                     return -1;
    34.                 }
    35.             }
    36.  
    37.             Reloc = (PIMAGE_BASE_RELOCATION)(((DWORD)Reloc) + Reloc->SizeOfBlock);
    38.         }