search

LEMON BLOG

How Compromised GitHub Repositories Turned Packagist Projects Into Cloud-Based Scanners

A recent software supply-chain incident exposed an unusual way of abusing trusted developer infrastructure. Attackers compromised GitHub repositories linked to several Packagist packages and inserted malicious GitHub Actions workflows that transformed temporary cloud runners into internet-scanning machines.

The PHP packages themselves were not carrying conventional malware that executed when developers installed them. Instead, the real attack mechanism was hidden inside each repository's .github/workflows/ directory.

Whenever activity triggered one of those workflows, GitHub automatically created a temporary Ubuntu virtual machine. The attacker then used that runner to download an external executable, scan internet-facing cPanel and WHM servers, attempt exploitation and send collected information back to their infrastructure.

The incident shows why software supply-chain security can no longer focus only on package contents. Repository automation, maintainer access and CI/CD configuration have become equally important parts of the attack surface.

The Packages Were Not the Part That Executed the Attack

The campaign involved malicious development versions across ten Packagist packages associated with a PHP and DevOps developer known as dinushchathurya.

After gaining access to the related GitHub repositories, the attacker added large numbers of workflow files beneath .github/workflows/ and pushed the changes to branches synchronised by Packagist.

This caused Packagist to publish development versions reflecting the compromised repository state.

At first glance, that could make the packages appear to be the source of the attack. However, researchers found that the PHP libraries themselves contained ordinary reference data and lookup functions.

They did not include obvious install-time execution hooks, shell commands or outbound network connections.

Installing one of the affected packages could copy the suspicious workflow files into a project's dependency directory, but that alone would not execute them.

GitHub does not run workflow files located inside Composer's vendor directory, and simply cloning the repository locally would not launch the payload either.

The workflows were activated only inside the original compromised repositories when a qualifying GitHub event occurred.

GitHub Actions Became the Attacker's Infrastructure

GitHub Actions is designed to automate legitimate development work such as building applications, running tests, publishing releases and checking code quality.

When a configured event occurs, GitHub provisions a temporary runner to execute the workflow.

The attacker turned that convenience into disposable scanning infrastructure.

The malicious workflow files were configured to start whenever code was pushed to any branch. They could also be launched manually through GitHub's workflow_dispatch feature.

Once triggered, GitHub created an Ubuntu runner with outbound internet access. The workflow then identified the runner's processor architecture, downloaded a matching Linux executable, made it executable and launched it with attacker-supplied arguments.

Separate payloads were available for 32-bit and 64-bit x86 systems as well as 32-bit and 64-bit ARM environments.

Instead of paying for or maintaining a permanent scanning network, the attacker effectively borrowed short-lived computing resources from GitHub.

Each new workflow run created a fresh environment capable of reaching external targets.

Hundreds of Workflow Files Increased the Available Execution Paths

Researchers identified between 55 and 62 malicious workflow files in each affected package version.

Across the ten packages, there were reportedly 583 workflow files in total. One development version alone contained 59.

The workflows were largely repetitive, but duplicating them created more opportunities for execution.

Normal development activity could trigger multiple jobs, while the manual-run capability allowed the operator to start additional scans when required.

The presence of dozens of nearly identical files also complicated review. A developer inspecting one or two workflows might not immediately recognise the scale of the compromise.

However, the number of workflow files does not prove that every one ran successfully. Public analysis has not established how many jobs completed, how much scanning occurred or how many external systems were affected.

Temporary Runners Reduced Persistence, Not External Risk

GitHub-hosted runners are normally destroyed when a workflow finishes.

That design limits persistence inside the runner because files and processes disappear with the virtual machine.

However, the temporary nature of the environment did not protect the systems being scanned.

During its lifetime, the runner still had processing power and outbound network access. It could download an executable, contact internet-facing servers and transmit results before GitHub removed it.

This created a useful operating model for the attacker:

The attacker retained the collected data even though the temporary machine no longer existed.

This is an important reminder that ephemeral infrastructure reduces some forms of persistence but does not prevent abuse during the period when the system is active.

The Campaign Focused on cPanel and WHM Systems

The downloaded executable scanned ports commonly associated with websites, alternate HTTPS services and cPanel or WHM administration interfaces.

The campaign reportedly attempted to exploit CVE-2026-41940, described as an authentication-bypass vulnerability affecting cPanel and WHM.

These systems are attractive targets because they often manage much more than a single website.

A cPanel account may provide access to:

WHM operates at a broader server-management level. A successful WHM compromise could potentially expose several hosted customers from one administrative environment.

The risk can also spread beyond the hosting platform.

Configuration files and environment variables may contain credentials for cloud services, source-control systems, email platforms, payment providers and external APIs.

One compromised hosting account could therefore become the starting point for several additional attacks.

The Workflow Managed Monitoring and Data Exfiltration

The downloaded executable performed the scanning and attempted exploitation, but the workflow files provided the surrounding operational logic.

A background process reportedly contacted an attacker-controlled heartbeat endpoint every 30 seconds.

Each update included information such as the repository name and the most recent scanner log entry. This gave the operator near-real-time visibility into activity occurring within the GitHub Actions job.

The workflow also monitored output files for newly collected content.

The targeted information reportedly included:

Collected content was divided into chunks and sent to a separate results endpoint.

The scripts tracked which lines had already been transmitted, preventing the same data from being sent repeatedly.

Live collection reportedly transferred up to 2,000 new lines per request, while a final stage attempted to send up to 5,000 lines.

Failed Jobs Could Still Leak Data

The collection process was designed to reduce dependence on a perfectly completed scan.

Even when the scanner crashed or the workflow failed before reaching its normal end, information already written to an output file could still be transmitted.

This matters because security teams may assume that a failed GitHub Actions job produced no meaningful result.

In this campaign, a job could be marked unsuccessful while still having completed several dangerous actions:

A red failure indicator in the GitHub Actions interface should therefore not be interpreted as proof that no data left the environment.

Investigators must review network activity, workflow commands and temporary files rather than relying only on the final job status.

Ordinary CI Logs May Not Show the Full Picture

The workflows redirected scanner output into temporary files and then transmitted those files separately.

As a result, the visible GitHub Actions log might not contain everything the payload discovered.

A reviewer could see the workflow start, a binary execute and the job later fail, while the most sensitive output had already been written elsewhere and exfiltrated.

This reinforces the need for outbound network monitoring around CI/CD systems.

Workflow logs are essential, but they are only one source of evidence.

A complete investigation may require correlation between:

Without that correlation, organisations may underestimate what occurred during a compromised workflow run.

The Package Registry Reflected the Compromise but Did Not Execute It

Packagist synchronised the altered branches and exposed the malicious workflow files through development package versions.

However, Packagist did not create the execution environment.

GitHub Actions supplied the runner, downloaded the payload and initiated the external scanning.

This separation is important for incident response.

A team investigating only the Composer package may inspect the PHP code, find nothing executable and conclude that the package is harmless.

The real evidence sits in the linked source repository and its automation history.

Security teams reviewing an affected dependency should inspect:

Supply-chain investigations must follow the package back to its development and publishing infrastructure.

One Compromised Maintainer Account Created a Runner Fleet

The campaign demonstrates the amount of infrastructure an attacker can obtain after compromising a single developer account.

A maintainer with write access may control several repositories. Each repository may contain numerous workflows, and each workflow may generate cloud-hosted runners.

That turns one account compromise into a distributed execution platform.

The attacker does not necessarily need to compromise GitHub itself. They only need sufficient repository permissions to modify workflow files.

Once malicious automation is committed, the platform carries out the remaining steps as though they were legitimate development tasks.

This is why repository write access should be treated as a privileged capability, particularly when it includes permission to modify CI/CD definitions.

The Suspended Account Does Not End the Wider Risk

The GitHub account associated with the affected repositories was reportedly suspended.

That action can stop new jobs from running under the compromised account, but it does not solve every consequence.

Malicious workflows may have been copied into forks or unrelated repositories. Previously collected credentials may still be valid. External cPanel or WHM systems may remain compromised, and stolen tokens could provide continued access to cloud services or source-control platforms.

Suspending an account removes one execution source. It does not automatically:

Affected organisations still need to perform credential rotation, log review and repository cleanup.

Search Results Suggested a Much Wider Operation

Researchers identified a DNS callback hostname embedded in 14 recovered workflows.

The workflows used nslookup against that hostname, allowing the attacker to confirm that commands were executing even when the workflow did not return useful output through other channels.

Searching GitHub for that identifier reportedly produced around 6,100 matching workflow files.

Broader searches using the command-and-control address, scanner command, heartbeat endpoint, credential filenames and exfiltration logic reportedly returned roughly 15,000 to 16,000 matches.

These numbers should not be treated as confirmed victim totals.

One repository may contain dozens of duplicate workflows. Search engines may group or repeat results, and some repositories may be controlled by the attackers themselves.

Nevertheless, the repeated code appearing across unrelated repositories suggests that the Packagist packages were only one visible component of a larger campaign.

Public Search Counts Cannot Establish Real Exposure

Large code-search numbers may attract attention, but they do not reveal how many workflows actually ran or which systems were successfully compromised.

A malicious file can exist in a repository without ever being triggered. A workflow may run but fail to download the payload. A scanner may reach a server without exploiting it, and an exploit attempt may succeed without obtaining useful credentials.

The evidence required to determine actual exposure exists in operational systems.

Organisations should examine whether:

Exposure cannot be measured accurately through GitHub search results alone.

Workflow Changes Need Their Own Approval Gate

The most important governance lesson is that files under .github/workflows/ should receive the same scrutiny as production code.

In some cases, they deserve even stricter controls because workflows can access secrets, obtain tokens and execute commands inside trusted infrastructure.

Repository owners should require review and approval before workflow changes are merged.

Branch-protection rules and code-owner policies can ensure that designated security or platform-engineering personnel approve changes to automation files.

Alerts should be raised when a workflow:

These behaviours are not always malicious, but they justify closer inspection.

GITHUB_TOKEN Permissions Should Be Minimized

GitHub Actions jobs often receive a temporary GITHUB_TOKEN that allows them to interact with the repository.

If the permissions are broader than necessary, a compromised workflow may be able to alter code, publish packages, create releases or access repository information.

Organisations should apply the principle of least privilege.

A workflow that only runs tests may need read-only access to repository contents. It should not automatically receive permission to modify pull requests, publish packages or change workflow files.

Permissions should be defined explicitly rather than relying on broad defaults.

Secrets should also be separated by environment and made available only to jobs that genuinely require them.

Self-Hosted Runners Create Greater Risk

GitHub-hosted runners are temporary, but self-hosted runners may retain files, credentials, network access and cached content after a job finishes.

A malicious workflow running on a self-hosted runner could potentially access internal systems that are unreachable from GitHub's public cloud.

It might also leave persistence behind, inspect other jobs or access credentials stored on the machine.

Self-hosted runners should therefore be treated as sensitive infrastructure.

Strong controls include:

GitHub-hosted runners still require workflow review and egress monitoring, but self-hosted environments can magnify the consequences of a malicious job.

Packagist Users Should Be Careful With Development Versions

Development branches are useful when teams need unreleased functionality, but they carry greater supply-chain risk than stable versions.

A branch can change at any time, and a new commit may introduce unexpected files or behaviour.

Composer users should avoid unreviewed development releases in production environments.

Dependencies should be pinned through a lockfile to known-good commit references. Teams should verify that the resolved commit matches what was previously reviewed.

When an incident affects a package, developers should inspect both the installed code and the corresponding upstream repository state.

A clean PHP library does not necessarily mean its development infrastructure was safe.

cPanel and WHM Operators Should Assume Wider Credential Risk

Operators of internet-facing cPanel and WHM servers should apply the vendor's security guidance for CVE-2026-41940 and review available indicators of compromise.

Where exposure is suspected, simply patching the server may not be enough.

Attackers may already have collected credentials from configuration files, environment variables, email settings or deployment scripts.

Organisations should consider rotating:

They should also review active sessions, administrator accounts, scheduled tasks, modified files and recent authentication activity.

The Real Control Point Is Repository Write Access

The campaign's downloader, scanner launch process and exfiltration logic were all placed inside GitHub Actions workflows.

That means the earliest practical control point was not the external scanner or the cPanel server. It was the moment someone obtained permission to modify the repository.

Maintainer accounts should be protected with phishing-resistant multifactor authentication wherever possible.

Dormant collaborators and unused personal access tokens should be removed. OAuth grants and GitHub App permissions should be reviewed regularly.

High-impact repositories may also benefit from signed commits, protected branches and alerts for unusual geographic or device-based access.

Preventing unauthorised workflow changes is far easier than investigating hundreds of malicious runner jobs after they have executed.

Final Thoughts

This incident was not a conventional malicious-package campaign.

The affected PHP libraries did not automatically execute an attack when installed. Instead, compromised repositories used GitHub Actions as the delivery and execution layer.

That distinction makes the campaign particularly instructive.

Attackers abused the trust relationship between maintainers, package registries and CI/CD platforms. Packagist distributed the repository state, while GitHub supplied temporary runners with computing power and outbound network access.

The lesson for developers is that source code is only one part of repository security. Workflow definitions, maintainer identities, tokens, Apps and automation permissions can be equally valuable to an attacker.

For hosting providers and cPanel operators, the campaign also shows how threats originating in developer infrastructure can reach completely separate downstream systems.

The strongest defence begins with tight control over repository write access and mandatory review of .github/workflows/ changes.

A workflow file may look like routine automation, but in the wrong hands it can become an entire attacker-operated cloud infrastructure.

Malaysia’s Healthcare Digitalisation Is Moving For...
Cisco Open-Sources Antares AI Models to Help Secur...

Related Posts

 

Comments

No comments made yet. Be the first to submit a comment
Sunday, 26 July 2026

Captcha Image

LEMON VIDEO CHANNELS

Step into a world where web design & development, gaming & retro gaming, and guitar covers & shredding collide! Whether you're looking for expert web development insights, nostalgic arcade action, or electrifying guitar solos, this is the place for you. Now also featuring content on TikTok, we’re bringing creativity, music, and tech straight to your screen. Subscribe and join the ride—because the future is bold, fun, and full of possibilities!

My TikTok Video Collection