⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 doexec.c

📁 nctool系列源代码
💻 C
字号:


// portions Copyright (C) 1994 Nathaniel W. Mishkin
// code taken from rlogind.exe
 #include <stdlib.h>#include <winsock2.h>
#include <winbase.h>

#ifdef GAPING_SECURITY_HOLE
#define BUFFER_SIZE 200extern char * pr00gie;void holler(char * str, char * p1, char * p2, char * p3, char * p4, char * p5, char * p6);
char smbuff[20];
//// Structure used to describe each session//typedef struct {    //    // These fields are filled in at session creation time    //    HANDLE  ReadPipeHandle;         // Handle to shell stdout pipe    HANDLE  WritePipeHandle;        // Handle to shell stdin pipe    HANDLE  ProcessHandle;          // Handle to shell process    //    //    // These fields are filled in at session connect time and are only    // valid when the session is connected    //    SOCKET  ClientSocket;    HANDLE  ReadShellThreadHandle;  // Handle to session shell-read thread    HANDLE  WriteShellThreadHandle; // Handle to session shell-read thread} SESSION_DATA, *PSESSION_DATA;//// Private prototypes//static HANDLEStartShell(    HANDLE StdinPipeHandle,    HANDLE StdoutPipeHandle    );static VOIDSessionReadShellThreadFn(    LPVOID Parameter    );static VOIDSessionWriteShellThreadFn(    LPVOID Parameter    );// **********************************************************************//// CreateSession//// Creates a new session. Involves creating the shell process and establishing// pipes for communication with it.//// Returns a handle to the session or NULL on failure.//static PSESSION_DATACreateSession(    VOID    ){    PSESSION_DATA Session = NULL;    BOOL Result;    SECURITY_ATTRIBUTES SecurityAttributes;    HANDLE ShellStdinPipe = NULL;    HANDLE ShellStdoutPipe = NULL;    //    // Allocate space for the session data    //    Session = (PSESSION_DATA) malloc(sizeof(SESSION_DATA));    if (Session == NULL) {        return(NULL);    }    //    // Reset fields in preparation for failure    //    Session->ReadPipeHandle  = NULL;    Session->WritePipeHandle = NULL;    //    // Create the I/O pipes for the shell    //    SecurityAttributes.nLength = sizeof(SecurityAttributes);    SecurityAttributes.lpSecurityDescriptor = NULL; // Use default ACL    SecurityAttributes.bInheritHandle = TRUE; // Shell will inherit handles    Result = CreatePipe(&Session->ReadPipeHandle, &ShellStdoutPipe,                          &SecurityAttributes, 0);    if (!Result) {        holler("Failed to create shell stdout pipe, error = %s",
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);        goto Failure;    }    Result = CreatePipe(&ShellStdinPipe, &Session->WritePipeHandle,                        &SecurityAttributes, 0);
    if (!Result) {        holler("Failed to create shell stdin pipe, error = %s",  			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);
        goto Failure;    }    //    // Start the shell    //    Session->ProcessHandle = StartShell(ShellStdinPipe, ShellStdoutPipe);    //    // We're finished with our copy of the shell pipe handles    // Closing the runtime handles will close the pipe handles for us.    //    CloseHandle(ShellStdinPipe);    CloseHandle(ShellStdoutPipe);    //    // Check result of shell start    //    if (Session->ProcessHandle == NULL) {        holler("Failed to execute shell", NULL,
			 NULL, NULL, NULL, NULL, NULL);
			        goto Failure;    }    //    // The session is not connected, initialize variables to indicate that    //    Session->ClientSocket = INVALID_SOCKET;    //    // Success, return the session pointer as a handle    //    return(Session);Failure:    //    // We get here for any failure case.    // Free up any resources and exit    //    if (ShellStdinPipe != NULL)         CloseHandle(ShellStdinPipe);    if (ShellStdoutPipe != NULL)         CloseHandle(ShellStdoutPipe);    if (Session->ReadPipeHandle != NULL)         CloseHandle(Session->ReadPipeHandle);    if (Session->WritePipeHandle != NULL)         CloseHandle(Session->WritePipeHandle);    free(Session);    return(NULL);}BOOLdoexec(    SOCKET  ClientSocket    ){    PSESSION_DATA   Session = CreateSession();    SECURITY_ATTRIBUTES SecurityAttributes;    DWORD ThreadId;    HANDLE HandleArray[3];	int i;
    SecurityAttributes.nLength = sizeof(SecurityAttributes);    SecurityAttributes.lpSecurityDescriptor = NULL; // Use default ACL    SecurityAttributes.bInheritHandle = FALSE; // No inheritance    //    // Store the client socket handle in the session structure so the thread    // can get at it. This also signals that the session is connected.    //    Session->ClientSocket = ClientSocket;    //    // Create the session threads    //    Session->ReadShellThreadHandle =         CreateThread(&SecurityAttributes, 0,                     (LPTHREAD_START_ROUTINE) SessionReadShellThreadFn,                      (LPVOID) Session, 0, &ThreadId);    if (Session->ReadShellThreadHandle == NULL) {        holler("Failed to create ReadShell session thread, error = %s", 
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);
        //        // Reset the client pipe handle to indicate this session is disconnected        //        Session->ClientSocket = INVALID_SOCKET;        return(FALSE);    }    Session->WriteShellThreadHandle =         CreateThread(&SecurityAttributes, 0,                      (LPTHREAD_START_ROUTINE) SessionWriteShellThreadFn,                      (LPVOID) Session, 0, &ThreadId);    if (Session->WriteShellThreadHandle == NULL) {        holler("Failed to create ReadShell session thread, error = %s", 
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);
        //        // Reset the client pipe handle to indicate this session is disconnected        //        Session->ClientSocket = INVALID_SOCKET;        TerminateThread(Session->WriteShellThreadHandle, 0);        return(FALSE);    }    //    // Wait for either thread or the shell process to finish    //    HandleArray[0] = Session->ReadShellThreadHandle;    HandleArray[1] = Session->WriteShellThreadHandle;    HandleArray[2] = Session->ProcessHandle;
	    i = WaitForMultipleObjects(3, HandleArray, FALSE, 0xffffffff);
    
	
	switch (i) {      case WAIT_OBJECT_0 + 0:        TerminateThread(Session->WriteShellThreadHandle, 0);        TerminateProcess(Session->ProcessHandle, 1);        break;      case WAIT_OBJECT_0 + 1:        TerminateThread(Session->ReadShellThreadHandle, 0);        TerminateProcess(Session->ProcessHandle, 1);        break;      case WAIT_OBJECT_0 + 2:        TerminateThread(Session->WriteShellThreadHandle, 0);        TerminateThread(Session->ReadShellThreadHandle, 0);        break; 
	  default:        holler("WaitForMultipleObjects error: %s", 
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);
        break;    }
    // Close my handles to the threads, the shell process, and the shell pipes
  	closesocket(Session->ClientSocket);
	
	DisconnectNamedPipe(Session->ReadPipeHandle);
    CloseHandle(Session->ReadPipeHandle);

	DisconnectNamedPipe(Session->WritePipeHandle);
    CloseHandle(Session->WritePipeHandle);


    CloseHandle(Session->ReadShellThreadHandle);
    CloseHandle(Session->WriteShellThreadHandle);

    CloseHandle(Session->ProcessHandle);
     free(Session);    return(TRUE);}// **********************************************************************//// StartShell//// Execs the shell with the specified handle as stdin, stdout/err//// Returns process handle or NULL on failure//static HANDLEStartShell(    HANDLE ShellStdinPipeHandle,    HANDLE ShellStdoutPipeHandle    ){    PROCESS_INFORMATION ProcessInformation;    STARTUPINFO si;    HANDLE ProcessHandle = NULL;    //    // Initialize process startup info    //    si.cb = sizeof(STARTUPINFO);    si.lpReserved = NULL;    si.lpTitle = NULL;    si.lpDesktop = NULL;    si.dwX = si.dwY = si.dwXSize = si.dwYSize = 0L;    si.wShowWindow = SW_HIDE;    si.lpReserved2 = NULL;    si.cbReserved2 = 0;    si.dwFlags = STARTF_USESTDHANDLES | STARTF_USESHOWWINDOW;    si.hStdInput  = ShellStdinPipeHandle;    si.hStdOutput = ShellStdoutPipeHandle;    DuplicateHandle(GetCurrentProcess(), ShellStdoutPipeHandle,                     GetCurrentProcess(), &si.hStdError,                    DUPLICATE_SAME_ACCESS, TRUE, 0);    if (CreateProcess(NULL, pr00gie, NULL, NULL, TRUE, 0, NULL, NULL,                      &si, &ProcessInformation))     {        ProcessHandle = ProcessInformation.hProcess;        CloseHandle(ProcessInformation.hThread);    }     else         holler("Failed to execute shell, error = %s", 
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);

    return(ProcessHandle);}// **********************************************************************// SessionReadShellThreadFn//// The read thread procedure. Reads from the pipe connected to the shell// process, writes to the socket.//static VOIDSessionReadShellThreadFn(    LPVOID Parameter    ){    PSESSION_DATA Session = Parameter;    BYTE    Buffer[BUFFER_SIZE];    BYTE    Buffer2[BUFFER_SIZE+30];    DWORD   BytesRead;
	// this bogus peek is here because win32 won't let me close the pipe if it is
	// in waiting for input on a read.    while (PeekNamedPipe(Session->ReadPipeHandle, Buffer, sizeof(Buffer), 
                    &BytesRead, NULL, NULL)) 
    {
		DWORD BufferCnt, BytesToWrite;
        BYTE PrevChar = 0;

		if (BytesRead > 0)
		{
			ReadFile(Session->ReadPipeHandle, Buffer, sizeof(Buffer), 
                    &BytesRead, NULL);
		}
		else
		{
			Sleep(50);
			continue;
		}

                //        // Process the data we got from the shell:  replace any naked LF's        // with CR-LF pairs.        //        for (BufferCnt = 0, BytesToWrite = 0; BufferCnt < BytesRead; BufferCnt++) {            if (Buffer[BufferCnt] == '\n' && PrevChar != '\r')                Buffer2[BytesToWrite++] = '\r';            PrevChar = Buffer2[BytesToWrite++] = Buffer[BufferCnt];        }        if (send(Session->ClientSocket, Buffer2, BytesToWrite, 0) <= 0)             break;    }    if (GetLastError() != ERROR_BROKEN_PIPE)        holler("SessionReadShellThreadFn exitted, error = %s", 
			itoa(GetLastError(), smbuff, 10), NULL, NULL, NULL, NULL, NULL);

	ExitThread(0);
}// **********************************************************************// SessionWriteShellThreadFn//// The write thread procedure. Reads from socket, writes to pipe connected// to shell process.  static VOIDSessionWriteShellThreadFn(    LPVOID Parameter    ){    PSESSION_DATA Session = Parameter;    BYTE    RecvBuffer[1];    BYTE    Buffer[BUFFER_SIZE];    BYTE    EchoBuffer[5];    DWORD   BytesWritten;    DWORD   BufferCnt, EchoCnt;    DWORD   TossCnt = 0;    BOOL    PrevWasFF = FALSE;    BufferCnt = 0;    //    // Loop, reading one byte at a time from the socket.        //    while (recv(Session->ClientSocket, RecvBuffer, sizeof(RecvBuffer), 0) != 0) {
        
        EchoCnt = 0;

        Buffer[BufferCnt++] = EchoBuffer[EchoCnt++] = RecvBuffer[0];
        if (RecvBuffer[0] == '\r')
                Buffer[BufferCnt++] = EchoBuffer[EchoCnt++] = '\n';


		// Trap exit as it causes problems
		if (strnicmp(Buffer, "exit\r\n", 6) == 0)
			ExitThread(0);

        //        // If we got a CR, it's time to send what we've buffered up down to the        // shell process.        //        if (RecvBuffer[0] == '\n' || RecvBuffer[0] == '\r') {            if (! WriteFile(Session->WritePipeHandle, Buffer, BufferCnt,                             &BytesWritten, NULL))            {                break;            }            BufferCnt = 0;        }    }

	ExitThread(0);}#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -