Popular Go Decimal Library Targeted by Long-Running Typosquat with DNS Backdoor
A long-running typosquat of a popular Go decimal library was weaponized to include a DNS-based backdoor. The malicious package, github.com/shopsprint/decimal, uses an init() function to poll a dynamic DNS subdomain via TXT records, executing the returned strings as arbitrary commands on the host system.
Authors: Kush Pandya
Source:Socket
- domaindnslog-cdn-images[.]freemyip[.]comC2 subdomain polled via DNS TXT records for arbitrary command execution.
- md5e3c6ce0440d9acd0f1cef1f0da3cdb5dMD5 hash of the trojanized decimal.go file.
- sha1fd26f4ca4746ee390e22043a5e19ebf2b7fcd1f9SHA-1 hash of the trojanized decimal.go file.
- sha256387d7ea5ca733b1e7219c943f4b461877a8df0148adfef42b1538b6c398fbb41SHA-256 hash of the trojanized decimal.go file.
- sha256dd9c0268c8944e6ddf90d4d0c81aa843785b7a9ee965faa635841ed9fc0ba086SHA-256 hash of the malicious v1.3.3 module zip.
Detection / HunterGoogle
What Happened
Security researchers discovered a malicious software package designed to trick Go developers by mimicking a popular math library. Anyone who accidentally installed the misspelled package ('shopsprint' instead of 'shopspring') had a hidden backdoor installed on their system. This backdoor allows attackers to secretly send and execute commands on the infected computer using the domain name system (DNS). Because the malicious code is cached by the official Go module proxy, it remains a threat even though the original source code was deleted. Developers should check their projects for the misspelled package, remove it immediately, and treat any affected systems as compromised.
Key Takeaways
- A malicious Go module typosquatting 'shopspring/decimal' was weaponized after 6 years of benign presence.
- Version v1.3.3 introduces an init() function that establishes a DNS TXT record C2 channel.
- The backdoor polls dnslog-cdn-images[.]freemyip[.]com every 5 minutes and executes returned TXT values via os/exec.Command.
- Despite the GitHub repository being deleted, the malicious package remains permanently available via the Go Module Proxy.
Affected Systems
- Go development environments
- CI/CD pipelines
- Production hosts running binaries compiled with the malicious github.com/shopsprint/decimal package
Attack Chain
The attack begins when a developer accidentally imports the typosquatted github.com/shopsprint/decimal package instead of the legitimate shopspring version. Upon execution of any compiled binary containing the package, a malicious init() function automatically runs in a background goroutine. This goroutine polls the C2 domain dnslog-cdn-images[.]freemyip[.]com every five minutes using DNS TXT record lookups. Any text returned in the TXT record is passed directly to os/exec.Command and executed on the host system, granting the attacker full remote code execution capabilities.
Detection Availability
- YARA Rules: No
- Sigma Rules: No
- Snort/Suricata Rules: No
- KQL Queries: No
- Splunk SPL Queries: No
- EQL Queries: No
- Other Detection Logic: No
The article does not provide specific detection rules but outlines behavioral heuristics and indicators to scan for in Go binaries and DNS logs.
Detection Engineering Assessment
EDR Visibility: Medium — EDR can detect the child processes spawned by the compiled Go binary via os/exec.Command, but the initial DNS TXT polling might blend in with normal network traffic if DNS logging is not deeply inspected. Network Visibility: Medium — DNS TXT queries to dynamic DNS providers can be spotted, but the payload is hidden within DNS traffic rather than standard HTTP/S C2 channels. Detection Difficulty: Moderate — Detecting the malicious package requires dependency scanning. Detecting the runtime behavior requires correlating DNS TXT lookups to suspicious domains with subsequent anomalous child process creation from a compiled Go binary.
Required Log Sources
- DNS Query Logs
- Process Creation Logs (Event ID 4688 / Sysmon Event ID 1)
Hunting Hypotheses
| Hypothesis | Telemetry | ATT&CK Stage | FP Risk |
|---|---|---|---|
| Compiled Go binaries spawning unexpected child processes, particularly shell commands or system utilities, may indicate a backdoor executing arbitrary commands. | Process Creation Logs | Execution | Medium |
| Frequent, periodic DNS TXT record lookups to free dynamic DNS providers (e.g., freemyip.com) from developer workstations or CI/CD nodes may indicate a DNS-based C2 channel. | DNS Query Logs | Command and Control | Low |
Control Gaps
- Lack of egress filtering for DNS TXT records
- Implicit trust in Go Module Proxy cached packages without verifying upstream repository health
Key Behavioral Indicators
- Simultaneous presence of net.LookupTXT and os/exec.Command symbols in a compiled binary that should only perform math operations
- DNS TXT queries to freemyip.com subdomains from build environments
False Positive Assessment
- Low
Recommendations
Immediate Mitigation
- Verify against your organization's incident response runbook and team escalation paths before acting.
- Audit go.mod and go.sum files across all projects for the presence of github.com/shopsprint/decimal.
- If the malicious package is found, treat the build host or CI runner as compromised and rotate any accessible credentials.
- Add dnslog-cdn-images[.]freemyip[.]com to DNS sinkholes and blocklists.
Infrastructure Hardening
- Consider blocking egress traffic to known free dynamic DNS zones (e.g., freemyip.com, duckdns.org) from build and production environments unless explicitly required.
- Evaluate implementing strict egress controls on CI/CD runners to limit outbound connections to approved repositories and services.
User Protection
- Consider deploying dependency scanning tools that flag typosquatted packages and anomalous package behaviors (like unexpected network or OS execution imports).
Security Awareness
- Educate developers on the risks of typosquatting and the importance of verifying module paths before adding them to projects.
MITRE ATT&CK Mapping
- T1195.002 - Compromise Software Supply Chain
- T1071.004 - Application Layer Protocol: DNS
- T1059 - Command and Scripting Interpreter
- T1583.001 - Acquire Infrastructure: Domains
- T1572 - Protocol Tunneling
- T1568 - Dynamic Resolution
Additional IOCs
- File Hashes:
387d7ea5ca733b1e7219c943f4b461877a8df0148adfef42b1538b6c398fbb41(SHA256) - SHA-256 hash of the trojanized decimal.go file.fd26f4ca4746ee390e22043a5e19ebf2b7fcd1f9(SHA1) - SHA-1 hash of the trojanized decimal.go file.e3c6ce0440d9acd0f1cef1f0da3cdb5d(MD5) - MD5 hash of the trojanized decimal.go file.