{
	"id": "e3375bb9-690e-4a40-9bf7-f9983eb9957f",
	"created_at": "2026-04-06T00:21:15.370198Z",
	"updated_at": "2026-04-10T03:24:37.062642Z",
	"deleted_at": null,
	"sha1_hash": "1f4c31af34263573f191262457eb99bc5edd690e",
	"title": "What BadAudio Reveals About APT24 – Securite360",
	"llm_title": "",
	"authors": "",
	"file_creation_date": "0001-01-01T00:00:00Z",
	"file_modification_date": "0001-01-01T00:00:00Z",
	"file_size": 7867508,
	"plain_text": "What BadAudio Reveals About APT24 – Securite360\r\nBy Muffin\r\nArchived: 2026-04-05 18:44:35 UTC\r\nThis blog post focuses on APT24, a China-linked intrusion set active since at least 2011. Despite its long\r\noperational history, publicly available technical analysis of this group remains limited. A recent Google Cloud\r\nreport shed additional light on APT24’s activities; however, it provided only a brief overview of badAudio, a\r\ndistinctive downloader associated with the group.\r\nAs a sample of this malware became publicly available, we conducted an in-depth reverse engineering analysis to\r\nbetter understand its functionality, cryptographic design, and operational role within APT24’s intrusion chain.\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 1 of 9\n\nFigure: Securite360’s OpenCTI entry for APT24\r\nAs a quick reminder: while APT24’s precise affiliation remains unclear, it is widely tracked as a PRC-nexus actor\r\nand is often assessed as operating in support of Chinese intelligence requirements. Recent victimology—\r\nespecially targeting Taiwan and, in some reporting, the United States—is consistent with that assessment.\r\nThat said, recent reporting emphasizes APT24’s use of custom tooling (for example, the BADAUDIO first-stage\r\ndownloader) rather than highlighting common China-linked families such as PlugX or ShadowPad.\r\nOpen-source literature on APT24 is still limited (and, at times, inconsistent), so a definitive assessment isn’t\r\npossible. There remains a clear open-source intelligence gap.\r\nReconnaissance phase\r\nAs reported by Mandiant, BadAudio collects host-identifying information prior to network communication.\r\nDuring our dynamic analysis, we confirmed that the malware retrieves the current Windows username via\r\nGetUserNameExW , which returns REM in our test environment. We also confirmed that it queries the system\r\nhostname via kernel32!GetComputerNameW , which returns DESKTOP-2C3IQHO . In both cases, execution returns to\r\nbadaudio.dll immediately after the API call, confirming that these values are collected directly by the malware.\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 2 of 9\n\nFigure: reconnaissance phase of BadAudio using Windows API\r\nThe collected host information is then concatenated with an architecture identifier (here, x86) before transmission.\r\nIn the debugger, the assembled tab-delimited string \\tREM\\tDESKTOP-2C3IQHO\\tx86\\tscm is present in memory\r\nand later reused during request construction.\r\nSeveral obfuscation techniques\r\nTo obfuscate strings, badaudio uses stack strings: it reconstructs obfuscated string buffers on the stack (typically\r\n16-byte aligned) and deobfuscates them in place using an SSE-based XOR mask. At runtime, it performs 128-bit\r\nXOR operations in XMM registers (e.g., movaps/movups + xorps), overwriting the stack buffer with plaintext\r\nonly immediately before the value is consumed.\r\nThe malware reuses this SSE XOR primitive across multiple deobfuscation sites with different mask sourcing\r\nmodels. In some cases, the obfuscated string material is built in stack-resident buffers and XOR-unmasked with a\r\n16-byte mask supplied indirectly via a pointer (e.g., [esi+18]).\r\nFigure: XOR-unmasking with a 16-byte mask supplied indirectly via a pointer\r\nIn related header-construction paths, the stack buffers are partially populated with runtime-derived context fields\r\n(e.g., values copied from [esi+10] and other frame fields) prior to the same SSE-based 16-byte XOR unmasking\r\nstep (e.g., xorps xmm0, [mask] / xorps xmm0, [mask+0x10]):\r\nFigure: stack buffers partially populated with runtime-derived context fields\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 3 of 9\n\nAcross multiple observed strings, this 16-byte mask matches the first 16 bytes of the C2 XOR mask, indicating\r\nmask reuse across string families. In other cases—such as the C2 URL—both the ciphertext and the XOR mask\r\nare hardcoded as immediates, reconstructed locally on the stack, and decoded as multiple 16-byte chunks (e.g., 64\r\nbytes decoded via 4×16-byte xorps operations).\r\nFigure: C2 deobfuscation routine (IDA and x32dbg)\r\nC2 XOR mask reconstructed in memory (64 bytes):\r\n6F 44 76 EA 1A 4B 3C 19 EC 6D 65 60 A3 63 DB B1\r\n79 0E 8D A7 88 EC 58 53 76 BE 51 90 39 4E 3E F7\r\nC3 E3 33 56 A6 65 35 D1 F0 5A 65 AA FF 4D D4 A2\r\n7D 4F 40 7C 24 BF EB 02 CA 96 2A 85 D5 DE B1 6A\r\nBy strategically placing a breakpoint at the return function of these routines, it is possible to retrieve several of\r\nthese Xored strings:\r\nfigure: strategic breakpoint to retrieve strings\r\nHere are the decoded strings:\r\n__etag=ID=2b9dd2199;\r\nFMPIS\r\nCookie\r\nUser-Agent\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 4 of 9\n\nMozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like\r\nGecko) Chrome/138.0.0.0 Safari/537.36 Edg/136.0.0.0\r\nAccept\r\napplication/octet-stream\r\nn64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/138.0.0.0\r\nSafari/537.36 Edg/136.0.0.0\r\nAccept-Language\r\nen-US,en;q=0.5\r\nt-stream\r\nCache-Control\r\nno-cache\r\nHeapDestroy\r\nVirtualFree\r\nTerminateThread\r\nExitProcess\r\nInternetCloseHandle\r\nwininet.dll\r\nHttpQueryInfoA\r\nMtNt\r\nwininet.dll\r\nInternetReadFile\r\nwininet.dll\r\nkernel32.dll\r\nInternetOpenA\r\nwininet.dll\r\nkernel32.dll\r\nHere I used floss to retrieve these strings all easily !\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 5 of 9\n\nAs previously reported by Google Cloud, Badaudio also uses AES encryption, notably to encrypt collected data\r\nbefore transmitting it to the C2 server. Several elements in the binary confirm the use of AES, including AES-specific constants and the presence of an S-box.\r\nFigure: AES S-BOX stored in the malware\r\nThe malware embeds a 256-bit AES key in the binary as eight 32-bit constants. This key is allocated at runtime\r\nand the key material is passed unchanged to the AES key expansion routine, confirming that the encryption key is\r\nhardcoded rather than dynamically derived. The encryption routine implements AES-256 in CTR mode.\r\nFigure: Hardcoded AES key\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 6 of 9\n\nBecause this is x86 code and these are stored as 32-bit words in memory, the byte order is little-endian per word.\r\nThe 32-byte key is therefore:\r\nb31b6db8f6f905fc9560f237c7af38515bd2a80d50e079bd1e297a1a9e94c8fe\r\nFigure X: AES MixColumns stage (left) and AES SubBytes transformation / S-box lookup (right)\r\nNetwork:\r\nBadAudio builds and sends an HTTP request using the WinINet API. First, it creates a request with\r\nwininet!HttpOpenRequestA, specifying the HTTP verb « GET » and the object path « /v3.1/current_user/details ».\r\nBefore sending the request, the malware injects a custom Cookie: request header using\r\nwininet!HttpAddRequestHeadersA. The header contains two values, __etag=… and FMPIS=…, which include, as\r\nnoted by Mandiant, an encrypted and encoded version of the information retrieve about the infected machine.\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 7 of 9\n\nFinally, the request is transmitted via wininet!HttpSendRequestA. At the time of the send call, the malware does\r\nnot provide additional headers inline (lpszHeaders = NULL) and does not provide a request body (lpOptional =\r\nNULL, length 0), indicating that the header set (including the Cookie) was pre-attached to the request handle\r\nearlier via HttpAddRequestHeadersA.\r\nFigure: sending HTTP request with encrypted data in the cookie header\r\nAt the time of analysis, the C2 domain returned an NXDOMAIN response from the queried DNS resolver,\r\nindicating that the domain name could not be resolved.\r\nFigure: Wireshark capture\r\nAs shown in the Wireshark capture, the DNS response contains the flag “No such name” and zero answer records.\r\nThis suggests that the domain was either no longer registered, intentionally taken down, or otherwise unavailable\r\nat the time of testing.\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 8 of 9\n\nUsing Cloudflare Workers (workers.dev) can help the operator blend in with legitimate web traffic and benefit\r\nfrom the generally strong reputation of a mainstream CDN/serverless provider. This may reduce the effectiveness\r\nof simple, reputation-based blocklists and make domain-based IoCs more disposable (attackers can rotate\r\nsubdomains easily).\r\nWhile encrypting data prior to transmission may complicate network-level inspection and hinder SOC analysts\r\nfrom quickly determining the nature of exfiltrated data, the use of a hardcoded key significantly weakens the\r\nscheme from a reverse engineering perspective. Once extracted, the key enables offline (and potentially\r\nretroactive) decryption of captured payloads.\r\nA good balance?\r\nIt is always interesting to analyze tools from APTs that are rarely observed in public reporting. In this case, APT24\r\nappears to combine for its malware several “low-cost” evasive measures—XOR-obfuscating API names and\r\nstrings, leveraging workers.dev infrastructure, and encrypting (then Base64-encoding) host/configuration data\r\nbefore embedding it in an HTTP request header. Overall, these choices suggest an attempt to balance operational\r\nsecurity with implementation simplicity/efficiency and cost.\r\nWhile Google describes the component as a “highly obfuscated loader,” the observed obfuscation is primarily\r\ngeared toward evading static detection and quick triage rather than fundamentally preventing reverse engineering.\r\nTaken together, these techniques are consistent with broader reporting on the increasing emphasis on OPSEC\r\namong several China-nexus intrusion sets.\r\nAnyway, APT24 likely doesn’t need to invest in stronger OPSEC to achieve its objectives, and this level of\r\nobfuscation and operational security appears to strike a good balance between stealth, cost, and efficiency.\r\nSource: https://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nhttps://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24\r\nPage 9 of 9",
	"extraction_quality": 1,
	"language": "EN",
	"sources": [
		"Malpedia"
	],
	"references": [
		"https://securite360.net/opsec-on-a-budget-what-badaudio-reveals-about-apt24"
	],
	"report_names": [
		"opsec-on-a-budget-what-badaudio-reveals-about-apt24"
	],
	"threat_actors": [
		{
			"id": "6241b9be-9c59-4164-a7f2-c45844b14a56",
			"created_at": "2023-01-06T13:46:38.321506Z",
			"updated_at": "2026-04-10T02:00:02.926657Z",
			"deleted_at": null,
			"main_name": "APT24",
			"aliases": [
				"PITTY PANDA",
				"G0011",
				"Temp.Pittytiger"
			],
			"source_name": "MISPGALAXY:APT24",
			"tools": [],
			"source_id": "MISPGALAXY",
			"reports": null
		}
	],
	"ts_created_at": 1775434875,
	"ts_updated_at": 1775791477,
	"ts_creation_date": 0,
	"ts_modification_date": 0,
	"files": {
		"pdf": "https://archive.orkl.eu/1f4c31af34263573f191262457eb99bc5edd690e.pdf",
		"text": "https://archive.orkl.eu/1f4c31af34263573f191262457eb99bc5edd690e.txt",
		"img": "https://archive.orkl.eu/1f4c31af34263573f191262457eb99bc5edd690e.jpg"
	}
}