Shell Script Compiler (shc)
A DFIR.ch analysis of shc (Shell Script Compiler), an open-source tool noted by Microsoft as being used by threat actors to compile shell-based backdoors into obfuscated, encrypted binaries. The post breaks down shc's anti-debugging technique — calling ptrace(PTRACE_TRACEME) so the binary self-kills if already traced by strace — and shows it can be bypassed by attaching a tracer after execution. It also demonstrates that despite the obfuscation, forensic artifacts such as process listings and /proc/<pid>/cmdline still expose the original decrypted command.
What it is
An analysis of shc (Shell Script Compiler, github.com/neurobin/shc), the open-source tool Microsoft flagged as used by threat actors to turn shell-script backdoors into stripped, encrypted binaries. shc is not a real compiler: it wraps the script's encrypted bytes in generated C, compiles that to a native binary, and at runtime decrypts and runs the script via sh -c.
How it works
The attacker builds the "untraceable" variant with the -U flag:
shc -U -f script.sh -o binary-U inserts a ptrace anti-debug guard. The child process calls ptrace(PTRACE_TRACEME, 0, 0, 0); if that returns < 0 — meaning a debugger is already attached — it sends itself an uncatchable SIGKILL:
if (ptrace(PTRACE_TRACEME, 0, 0, 0) < 0) {
kill(getpid(), SIGKILL);
_exit(1);
}Under strace ./binary the process dies (Operation not permitted, killed by SIGKILL) before doing anything useful.
What to do
The ptrace check only runs at startup, so the guard is defeated by attaching after the process is already running rather than launching under the tracer:
strace -p <pid>For dead-box / live triage, the plaintext script survives despite the "encrypted at rest" binary once the process is live — read it from the running process:
cat /proc/<pid>/cmdlineThe original decrypted command also shows up in the process list. Treat a stripped binary that spawns sh -c with an obfuscated body, plus a -U-style ptrace/SIGKILL sequence, as a hunting signature.
Caveats
The page states its own limits: the anti-debug bypass works only when you attach after execution, not before — launching the binary under strace still gets you killed. The forensic recovery of the script depends on catching the process while it is running; the binary remains obfuscated at rest. The author's testing used a netcat bind shell generated from revshells.com, not real captured malware.
Organisations named here
- PTRACE_TRACEME
- SIGKILL
Technologies named here
- shc
- strace
- revshells.com
- Netcat
Techniques named here
- Shell script compilation/obfuscation via shc
- Anti-debugging via ptrace
- Ptrace check bypass
- Forensic recovery via process list and /proc/<pid>/cmdline
- Anti-debugging
Related in Malware & RE
Reverse Engineering the Six Stages of MacSync Stealer and RAT
Post-DEF CON Phishing Uses Malicious Google Doc to Deliver Malware
ClickFix Removes Your Background but Leaves the Malware
