{
	"id": "e9a3ca27-1d6d-45bf-85fe-996fc1bcb351",
	"created_at": "2026-04-06T00:10:46.287377Z",
	"updated_at": "2026-04-10T13:12:31.61766Z",
	"deleted_at": null,
	"sha1_hash": "c71238d03b010f7f3aab4a16111e55dd063c91d4",
	"title": "Quick analysis note about GuLoader (or CloudEyE)",
	"llm_title": "",
	"authors": "",
	"file_creation_date": "0001-01-01T00:00:00Z",
	"file_modification_date": "0001-01-01T00:00:00Z",
	"file_size": 1164156,
	"plain_text": "Quick analysis note about GuLoader (or CloudEyE)\r\nPublished: 2020-06-27 · Archived: 2026-04-05 20:25:55 UTC\r\nRecently, I’ve supported a foreign friend on Twitter during the analysis one of GuLoader (or CloudEyE) variant\r\nsample. Although, he have read these articles (1, 2) but still stuck and I know that feeling.\r\nThe discussion between us was quite long, finally I sent him my quick analysis so that he can read and follow.\r\nNow, I put the analysis that we discussed on this blog hoping it will help others like him.\r\n1. Get the GuLoader’s shellcode\r\nGuLoader uses VirtualAlloc api for allocating a new memory section and drop shellcode to the allocated memory.\r\nCall to VirtualAlloc:\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 1 of 9\n\nFill shellcode to the allocated buffer:\r\nContinue trace, will jump to the shellcode. This shellcode may vary with each sample:\r\n2. Debug shellcode for finding the next payload URL\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 2 of 9\n\nThis shellcode uses Heaven’s Gate technique to execute on x64 environment. You can read more about this\r\ntechnique that I wrote here. Preferably, you should debug GuLoader on 32bit Windows VM.\r\nPatch to bypass anti-VM:\r\nBreak on call to EnumWindows (patch if need to bypass call to TerminateProcess):\r\nBreak on call to ZwProtectVirtualMemory (need to patch to bypass anti-attach):\r\nBreak on call to ZwSetInformationThread for hidding thread (need to patch 0xC3 when trace into this\r\ncall or nop this call):\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 3 of 9\n\nDirectly, below will usually be the sub function that call to the CPUID command, nop this call:\r\nCall to get process command line:\r\nCall to shellcode main proc, need to trace into this func:\r\nThis shellcode main proc will do:\r\n_ Get RegAsm’s path (ex: C:\\Windows\\Microsoft.NET\\Framework\\v2.0.50727\\RegAsm.exe)\r\n_ Call to kernel32.CreateProcessInternalW to create RegAsm.exe in suspended state:\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 4 of 9\n\n_ Get msvbvm60.dll‘s path (ex: C:\\Windows\\system32\\msvbvm60.dll) and then replace to \\??\r\n\\C:\\Windows\\system32\\msvbvm60.dll\r\n_ Call to ntdll.ZwOpenFile\r\n_ Call to ntdll.ZwCreateSection with FileHandle of msvbvm60.dll (ex: File,\r\nC:\\Windows\\System32\\msvbvm60.dll, 0x190)\r\n_ Call to ntdll.ZwMapViewOfSection with SectionHandle of msvbvm60.dll and ProcessHandle of RegAsm.exe\r\nsuspended process. For mapping msvbvm60.dll:\r\n_ Allocate RWX memory section on RegAsm.exe suspended process:\r\n_ Then call ZwWriteVirtualMemory for writing the 2nd shellcode to the allocated buffer at RegAsm process.\r\nThe 2nd shellcode same as the 1st shellcode, but its main task is to decode the URL and download the final\r\npayload.\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 5 of 9\n\n_ After that it calls ZwGetContextThread, ZwSetContextThread and then ZwResumeThread. So RegAsm\r\nprocess will return to the normal state and execute the 2nd shellcode to download the final payload.\r\nFor debugging the 2nd shellcode, use ProcessHacker to change bytes of 2nd shellcode to 0xEB 0xFE\r\n(must restore to orginal bytes later. The original bytes is 0xFC 0x81):\r\nLet’s trace over ZwResumeThread:\r\nOpen new debugger and attach RegAsm. F9 then F12, stop at the EB FE. Change back to the original\r\nbytes:\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 6 of 9\n\nDebug the 2nd\r\n shellcode will locate the code decode the URL. For example: Stack ss:\r\n[0056F848]=008D1A2C, (ASCII\r\n“hxxps://www.mediafire.com/file/kgwo4t43b5831fj/origin_geyiApZvCe4.bin/file”)\r\nSometimes, the mediafire / google drive link was blocked by CloudFlare, so need to manually download\r\nand save it. Then let’s the shellcode resolve the wininet_api funcs, use these apis for downloading the\r\nCloudFlare’s content. It will check the size of downloaded content is equal to 0x4B600 (in this case). Must\r\npatch to let’s it think you have downloaded the right binary. Then you trace into the func that will decrypt\r\npayload. My trick is replace the CloudFlare content with the content of encrypted payload. Here is the loop\r\nit try to find 2 bytes that decrypt 2 bytes of payload to MZ signature\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 7 of 9\n\nThen build the xor_key_buffer, buffer length is 0x270 bytes:\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 8 of 9\n\nAfter decrypt loop, get the final payload. It can be a Trojans (RAT) or malware that steals information such\r\nas Agent Tesla, FormBook, NanoCore RAT, Netwire RAT, Remcos RAT, …\r\nEnd!\r\nm4n0w4r\r\nHopefully, in the future, if I have the opportunity to go to Singapore, I will meet him !!\r\nSource: https://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nhttps://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/\r\nPage 9 of 9",
	"extraction_quality": 1,
	"language": "EN",
	"sources": [
		"Malpedia"
	],
	"origins": [
		"web"
	],
	"references": [
		"https://kienmanowar.wordpress.com/2020/06/27/quick-analysis-note-about-guloader-or-cloudeye/"
	],
	"report_names": [
		"quick-analysis-note-about-guloader-or-cloudeye"
	],
	"threat_actors": [],
	"ts_created_at": 1775434246,
	"ts_updated_at": 1775826751,
	"ts_creation_date": 0,
	"ts_modification_date": 0,
	"files": {
		"pdf": "https://archive.orkl.eu/c71238d03b010f7f3aab4a16111e55dd063c91d4.pdf",
		"text": "https://archive.orkl.eu/c71238d03b010f7f3aab4a16111e55dd063c91d4.txt",
		"img": "https://archive.orkl.eu/c71238d03b010f7f3aab4a16111e55dd063c91d4.jpg"
	}
}