Внедрения ДЛЛ в процесс с режима ядра

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

  1. wworld

    wworld New Member

    Публикаций:
    0
    Регистрация:
    16 фев 2007
    Сообщения:
    6
    Вобщем интересует следущее есть ли у когото сырец по данной теме
    нужно помочь в такой идее есть процесс м когда он порождает дочерний туда надо внедрить либу или кусок бинарного кода
    возможно и то и другое
    вопрос в следующем нужен нормальный маппинг DLL файла в режиме ядра
    поток я создаю сам ZwCreateThread это я научился ) ах да прыжок на LoadlibraryEx, LdrLoadDll не то они не подходять в виду того что либа должна быть немного незаметной .. DllMain я выполняю своим кодом это уже готово я делаю данную вещь в юзмоде там все ок а вот в ядре пока не решаюсь а ещо внедрение происходит на стадии создания процесса а DllMain выполняется перед кодом главной нити проиложения. кто из уважаемой публики по делу может чтото посоветовать?
    бу ду рад любой помощи по данной теме!
    и либы юзает только Kernel32 Ntdll функции
     
  2. n0name

    n0name New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2004
    Сообщения:
    4.336
    Адрес:
    Russia
    поиск по форуму.
     
  3. tylerdurden

    tylerdurden New Member

    Публикаций:
    0
    Регистрация:
    25 фев 2004
    Сообщения:
    322
    Юзай (peb+2d8)=адрес строки с именем dll (в каноническом виде) - это для x64, для x32 1e8. Правда винда иногда грузит shimeng.dll (смотрит ExecuteOptions и в sysmain.sdb) так что лучше замапить себя как \\knowndlls\shimeng.dll (+knowndlls32 для 32б процессов в 64битной винде) и пихать в peb уже shimeng.dll соответственно. В peb писать можно уже на колбэке о создании процесса (который ставится PsSetCreateProcessNotifyRoutine).
     
  4. tylerdurden

    tylerdurden New Member

    Публикаций:
    0
    Регистрация:
    25 фев 2004
    Сообщения:
    322
    Вот код собсно:
    Код (Text):
    1. typedef unsigned long DWORD;
    2. typedef unsigned short WORD;
    3. typedef unsigned char BYTE;
    4.  
    5. __declspec(dllimport) DWORD PsLookupProcessByProcessId(HANDLE ProcessId,PEPROCESS* pProcess);
    6. __declspec(dllimport) DWORD ZwOpenProcess(PHANDLE ProcessHandle,ULONG DesiredAccess,POBJECT_ATTRIBUTES ObjectAttributes,PCLIENT_ID Cid);
    7. __declspec(dllimport) DWORD ZwQueryInformationProcess(HANDLE ProcessHandle,PROCESSINFOCLASS ProcessInformationClass,PVOID ProcessInformation,ULONG ProcessInformationLength,PULONG ReturnLength);
    8. __declspec(dllimport) BYTE *PsGetProcessPeb(PEPROCESS Process);
    9.  
    10. #ifdef _WIN64
    11. #define SHIM_OFFSET 0x2d8
    12. #else
    13. #define SHIM_OFFSET 0x1e8
    14. #endif
    15.  
    16. STATIC_UNICODE_STRING(shimRegRoot,"\\REGISTRY\\MACHINE\\SOFTWARE\\shim");
    17.  
    18. WCHAR shimName[]=L"shimeng.dll";
    19. WCHAR shimSection[]=L"\\knowndlls\\shimeng.dll";
    20. STATIC_UNICODE_STRING(shimDllRegKey,"shimdll");
    21. HANDLE hShimSection;
    22. #ifdef _WIN64
    23. WCHAR shimSection32[]=L"\\knowndlls32\\shimeng.dll";
    24. STATIC_UNICODE_STRING(shimDll32RegKey,"shimdll32");
    25. HANDLE hShimSection32;
    26. #endif
    27.  
    28. void processNotify(HANDLE parentId,HANDLE processId,BOOLEAN createFlag){
    29.     PVOID memAddress=0;
    30.     SIZE_T memSize=sizeof(shimName);
    31.     HANDLE hProcess;
    32.     BYTE *pPeb;
    33.     OBJECT_ATTRIBUTES objAttr;
    34.     CLIENT_ID idClient;
    35.     PEPROCESS pEProcess;
    36.     DWORD ntStatus;
    37.     KAPC_STATE kaps;   
    38.  
    39.     if(createFlag){
    40.         RtlZeroMemory(&objAttr,sizeof(OBJECT_ATTRIBUTES));
    41.         idClient.UniqueProcess=processId;
    42.         idClient.UniqueThread=0;
    43.         if(ZwOpenProcess(&hProcess,PROCESS_DUP_HANDLE,&objAttr,&idClient)!=0){
    44.             return;
    45.         }
    46.         if(PsLookupProcessByProcessId(processId,&pEProcess)!=0){
    47.             return;
    48.         }
    49.         pPeb=PsGetProcessPeb(pEProcess);
    50.         if(pPeb==0){
    51.             return;
    52.         }
    53.         ntStatus=ZwAllocateVirtualMemory(hProcess,&memAddress,0,&memSize,MEM_COMMIT,PAGE_READWRITE);
    54.         if(ntStatus!=0){
    55.             return;
    56.         }      
    57.         KeStackAttachProcess(pEProcess,&kaps);
    58.         __try{
    59.             memcpy(memAddress,shimName,sizeof(shimName));
    60.             *(WCHAR**)(pPeb+SHIM_OFFSET)=memAddress;
    61.         }__except(EXCEPTION_EXECUTE_HANDLER){
    62.         }
    63.         KeUnstackDetachProcess(&kaps);
    64.     }
    65.     return;
    66. }
    67.  
    68. void driverUnload(PDRIVER_OBJECT DriverObject){    
    69.     PsSetCreateProcessNotifyRoutine(processNotify,TRUE);
    70.     ZwClose(hShimSection);
    71. #ifdef _WIN64
    72.     ZwClose(hShimSection32);
    73. #endif
    74. #ifdef SHIM_DEBUG
    75.     DbgPrint("shim injector: unloaded");
    76. #endif
    77.     return;
    78. }
    79.  
    80. NTSTATUS mapShim(HANDLE *pSection,PUNICODE_STRING dllName,WCHAR *sectionName){
    81.     HANDLE hFile;
    82.     OBJECT_ATTRIBUTES objAttr;
    83.     IO_STATUS_BLOCK ioStatusBlock; 
    84.     UNICODE_STRING usFileName;
    85.     DWORD ntStatus;
    86.     HANDLE hRegKey;
    87.     PKEY_VALUE_PARTIAL_INFORMATION regKeyInfo=0;
    88.     DWORD regKeySize=sizeof(KEY_VALUE_PARTIAL_INFORMATION)+0x200;
    89.  
    90.     InitializeObjectAttributes(&objAttr,&shimRegRoot,0,0,0);
    91.     ntStatus=ZwOpenKey(&hRegKey,KEY_QUERY_VALUE,&objAttr);
    92.     if(ntStatus!=STATUS_SUCCESS){
    93.         return ntStatus;
    94.     }
    95.     regKeyInfo=(KEY_VALUE_PARTIAL_INFORMATION*)ExAllocatePoolWithTag(PagedPool,regKeySize,'SHIM');
    96.     if(regKeyInfo==0){
    97.         ZwClose(hRegKey);
    98.         return ntStatus;
    99.     }
    100.     ntStatus=ZwQueryValueKey(hRegKey,dllName,KeyValuePartialInformation,regKeyInfo,regKeySize,&regKeySize);
    101.     ZwClose(hRegKey);
    102.     if(ntStatus!=STATUS_SUCCESS){
    103.         ExFreePool(regKeyInfo);
    104.         return ntStatus;
    105.     }
    106. #ifdef SHIM_DEBUG
    107.     DbgPrint("shim injector: shim %ls added",regKeyInfo->Data);
    108. #endif
    109.     RtlInitUnicodeString(&usFileName,regKeyInfo->Data);
    110.     InitializeObjectAttributes(&objAttr,&usFileName,OBJ_CASE_INSENSITIVE|OBJ_KERNEL_HANDLE,0,0);
    111.     ntStatus=ZwOpenFile(&hFile,FILE_GENERIC_EXECUTE,&objAttr,&ioStatusBlock,FILE_SHARE_READ,FILE_SYNCHRONOUS_IO_NONALERT);
    112.     if(ntStatus!=STATUS_SUCCESS){
    113.         ExFreePool(regKeyInfo);
    114.         return ntStatus;
    115.     }
    116.     RtlInitUnicodeString(&usFileName,sectionName); 
    117.     ntStatus=ZwCreateSection(pSection,SECTION_ALL_ACCESS,&objAttr,0,PAGE_EXECUTE,SEC_IMAGE,hFile);
    118.     ZwClose(hFile);
    119.     ExFreePool(regKeyInfo);
    120.     return ntStatus;
    121. }
    122.  
    123. NTSTATUS DriverEntry(PDRIVER_OBJECT DriverObject,PUNICODE_STRING RegistryPath){
    124.     DWORD ntStatus;
    125. #ifdef SHIM_DEBUG  
    126.     DbgPrint("shim injector: loaded");
    127. #endif
    128.     ntStatus=mapShim(&hShimSection,&shimDllRegKey,shimSection);
    129. #ifdef _WIN64
    130.     if(ntStatus==STATUS_SUCCESS){
    131.         ntStatus=mapShim(&hShimSection32,&shimDll32RegKey,shimSection32);
    132.     }
    133. #endif
    134.     if(ntStatus==STATUS_SUCCESS){
    135.         ntStatus=PsSetCreateProcessNotifyRoutine(processNotify,FALSE);
    136.     }
    137.     if(ntStatus!=STATUS_SUCCESS){
    138.         ZwClose(hShimSection);
    139. #ifdef _WIN64
    140.         ZwClose(hShimSection32);
    141. #endif
    142. #ifdef SHIM_DEBUG
    143.         DbgPrint("shim injector: unloaded (0x%x)",ntStatus);
    144. #endif
    145.     }
    146.     DriverObject->DriverUnload=driverUnload;
    147.     return ntStatus;
     
  5. wworld

    wworld New Member

    Публикаций:
    0
    Регистрация:
    16 фев 2007
    Сообщения:
    6
    ну правда не совсем то что я хотел ....
    либа у меня мапится по типу xLoadLibrary потом вшивается в прцесс а после она там запускается
    тее таким образом в процесс можно вшить любой базо-независимый код

    а ещо таков вопрос каким чудом смотреть адреса экспортируемых ф-ций либ в процессе с ядра?
     
  6. k3internal

    k3internal New Member

    Публикаций:
    0
    Регистрация:
    11 янв 2007
    Сообщения:
    607
    tylerdurden
    <В peb писать можно уже на колбэке о создании процесса (который ставится PsSetCreateProcessNotifyRoutine).>

    Да ну !!! Неужели !!! Так вот. В момент срабатывания колбэка Peb ещё не сформирован. Посмотри сорцы PspCreateProcess. Во всяком случае у меня все попытки прочитать Peb из колбека оканчивались неудачей, потому как отладчик показывал, что память по PsGetProcessPeb вообще ещё не передана. В противном случае вылитаем в синий экран.

    во всяком случае вот сорец. Вытаскивал коммандную строку процесса
    Код (Text):
    1. NTSTATUS iniGetProcessCommandLine(HANDLE ProcessId, PWCHAR us)
    2. {
    3. PVOID               peb      = NULL;
    4. PVOID               eprocess = NULL;
    5. NTSTATUS            ns;
    6. PPROCESS_PARAMETERS pp       = NULL;
    7. KAPC_STATE          ApcState;
    8.  
    9. __try{
    10.       if (KeGetCurrentIrql() > PASSIVE_LEVEL) return STATUS_UNSUCCESSFUL;
    11.     if (osBuildNumber > 3790) return STATUS_UNSUCCESSFUL;
    12.     ns = (*_PsLookupProcessByProcessId)(ProcessId,&eprocess);
    13.         if (!NT_SUCCESS(ns)) return STATUS_UNSUCCESSFUL;
    14.     if (osBuildNumber == 2195) peb = (PVOID)0x7ffdf000;
    15.     if (osBuildNumber > 2195)(DWORD)peb = (* _PsGetProcessPeb)(eprocess);
    16.  
    17.      (*_KeStackAttachProcess)(eprocess, &ApcState);    
    18. if (MmIsAddressValid(peb)) {
    19. (DWORD)pp = *(PDWORD)((DWORD)peb+0x10);
    20. if (MmIsAddressValid(pp)) {
    21. if (pp->CommandLine.Length < MAX_PATH*2)RtlCopyMemory(us,pp->CommandLine.Buffer,pp->CommandLine.Length);
    22.         }
    23.         }; 
    24.     (*_KeUnstackDetachProcess)(&ApcState);
    25. }
    26. __except(EXCEPTION_EXECUTE_HANDLER){return STATUS_UNSUCCESSFUL;};        
    27. return STATUS_SUCCESS;
    28. }
    Не думаю что он косячный.

    wworld
    <а ещо таков вопрос каким чудом смотреть адреса экспортируемых ф-ций либ в процессе с ядра?>
    Тем же самым чудом. Находить Peb, а в нём уже PLDR_DATA_TABLE_ENTRY на список Длл. Затем разбором PE вытаскивать функции. Только не забудь приаттачиться к процессу для начала, а при поиске функций в конкретном модуле залочить память в оперативке.
     
  7. k3internal

    k3internal New Member

    Публикаций:
    0
    Регистрация:
    11 янв 2007
    Сообщения:
    607
    хотя..... может я и натупил
     
  8. wworld

    wworld New Member

    Публикаций:
    0
    Регистрация:
    16 фев 2007
    Сообщения:
    6
    хм ... а если сделать вот так
    смотрим что на вернет ZwCreateProcess or ZwCreateProcessEx
    запоминаем хегл потом при создании потока ZwCreateThread мапим туда либу настраиваем в ней все что нам надо
    и делаем на нее переход? стоит ли так делать? ну ещо предварительно смотрим что за процесс создается
    есть просто идея таким образом систему защиты накатать от разной гадости. на диплом надо ))))

    а может ктото ещо сырцом поделится где реализована ф-ция получения адресса ф-ции
    по типу xGetProcAddress но с ядра тее по базе ДЛЛ файла нужного нам .... там нужно получать лиш ф-ции от kernel32 ntdll все остальное там динамически получается
     
  9. tylerdurden

    tylerdurden New Member

    Публикаций:
    0
    Регистрация:
    25 фев 2004
    Сообщения:
    322
    k3internal Возьми и запусти мой код. Работает везде от хп32 до хп64 и висты

    П.С. Пеб сформирован на момент колбэка. Он не полностью заполнен, но он есть. Поэтому собственно я и делаю мэппинг в knowndlls, kernel32 иногда затирает это указатель указателем на оригинальную shimeng.dll