By using memfd_create to create file pointer to an in-memory file and execveat to execute a file pointer like a regular file, we are able to execute a binary that is entirely stored in memory
Proof of concept reflective (in-memory) loader with encryption. Supports loading a binary securely either via stdio (from a parent process) or a TCP socket. The use case is to allow secure execution of processes directly into memory (ie without creating a file on disk or downloading in cleartext with wget). This could be used as a means for secure delpoyment of a beacon/second-stage in a red-team scenario. The compiled loader is only 25KB in size.
- Crypto functionality utilised from TweetNaCl and it uses Box (public/private key encryption mechanism that uses curve25519 and salsa20poly1305)
- dietlibc is used to create very small statically linked binaries ~25KB
- Key functions:
- memfd_create - create a file pointer to a fake in-memory file that behaves like a regular
FILE *
(note in this implementation this is implemented with syscalls as dietlibc didn't support it) execveat(<fp>, "", <argv>, <env>, AT_EMPTY_PATH);
- allows executing aFILE *
instead of a filepath
- memfd_create - create a file pointer to a fake in-memory file that behaves like a regular
Sends encrypted binary over TCP, decrypts and executes in memory.
- Compile tcp loader & test binary (see below)
- Start server
python3 server.py
- Run compiled loader
./main
Sends encrypted binary to a subprocess, decrypts and executes in memory.
- Compile stdio loader & test binary (see below)
- Start stager
python3 stager.py
apt install dietlibc-dev
pip3 install pynacl
-
Run from either
/stdio_loader
or/tcp_loader
directoriesdiet -Os gcc -o main main.c execveat.S tweetnacl.c -Wall -s
-Os
- optimise diet compiler for size-s
- strip debug symbols-Wall
- show all warnings
-
Run from
/test
directorygcc -o main main.c