http隧道版lcx

3人阅读 评论(0) 收藏 举报
分类:

httplcx.cpp

/*
************************************************************************************
* 
* lcx.cpp

* : [option:]
* : -listen 
* : -slave 
*
************************************************************************************
*/
#include "stdafx.h"
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <errno.h>
#include <io.h>
#include "MyHttpPipeBase.h"


#define VERSION "1.00"
#define TIMEOUT 300
#define MAXSIZE 20480
#define HOSTLEN 40
#define CONNECTNUM 5

// define 2 socket struct
struct transocket 
{
	SOCKET fd1;
	SOCKET fd2;
};

struct httptransocket 
{
	SOCKET SoRecv;
	SOCKET SoSend;
	SOCKET fd2;
};

struct httptransocket2 
{
	void   *MyPipe;
	SOCKET fd2;
};

// define function 
void ver();
void usage(char *prog);
void closeallfd();
void getctrlc(int j);
void makelog(char *buffer, int length);
void bind2bind(int port1, int port2);
int create_socket();
int create_server(int sockfd, int port);
int client_connect(int sockfd, char* server, int port);
void httpLocaltransmit(LPVOID data);
void httpRemotetransmit(LPVOID data);
void httpbind2bind(int port1, int port2);
void httpconn2conn(char *host1, int port1, char *host2, int port2);
// define GLOBAL variable here
extern int errno;
FILE *fp;
int method=0;
int connectnum=0;

//************************************************************************************
// 
// function main
//
//************************************************************************************
VOID main(int argc, char* argv[])
{
	char **p;
	char sConnectHost[HOSTLEN], sTransmitHost[HOSTLEN];
	int iConnectPort=0, iTransmitPort=0;
	char *logfile=NULL;
	
	ver();
	memset(sConnectHost, 0, HOSTLEN);
	memset(sTransmitHost, 0, HOSTLEN);
	
	p=argv;
	
	// Win Start Winsock.
	WSADATA wsadata;
	WSAStartup(MAKEWORD(1, 1), &wsadata);
	
	signal(SIGINT, &getctrlc);
	
	if(argc > 2)
	{
		if(stricmp(argv[1], "-listen") == 0 && argc >= 4)
		{
			iConnectPort = atoi(argv[2]);
			iTransmitPort = atoi(argv[3]);
			method = 1;
		}
		else if(stricmp(argv[1], "-slave") == 0 && argc >= 6)
		{
			strncpy(sConnectHost, argv[2], HOSTLEN);
			iConnectPort = atoi(argv[3]);
			strncpy(sTransmitHost, argv[4], HOSTLEN);
			iTransmitPort = atoi(argv[5]);
			method = 3;
		}
		
	}
	
	switch(method)
	{
	case 1:
		httpbind2bind(iConnectPort, iTransmitPort);
		break;
	case 3:
		httpconn2conn(sConnectHost, iConnectPort, sTransmitHost, iTransmitPort);
		break;
	default:
		usage(argv[0]);
		break;
	}
	
	if(method)
	{
		closeallfd();
	}
	
	WSACleanup();
	
	return;
}


//************************************************************************************
// 
// print version message
//
//************************************************************************************
VOID ver() 
{ 
	printf("======================== Transmit Tool for HTTPTunnel V%s =======================\r\n", VERSION);
}

//************************************************************************************
// 
// print usage message
//
//************************************************************************************
VOID usage(char* prog) 
{ 
	printf("[Usage of Packet Transmit:]\r\n");
	printf("[option:]\n");
	printf(" -listen localport1 localport2\n");
	printf(" -slave localIp localport2 remoteIp remoteport\n\n");
	return;
}


SOCKET StartTcp(WORD Port)
{
	SOCKET		Sck;	
	sockaddr_in addr;
	int			optval =  600 * 1000;
	
	memset(&addr,0,sizeof(addr));
	addr.sin_family = AF_INET;
	addr.sin_port = htons(Port);
	
	Sck = socket(AF_INET, SOCK_STREAM, 0);
	if(Sck==INVALID_SOCKET)
		return NULL;
	
	if(bind(Sck, (sockaddr*)&addr, sizeof(addr)) 
		== SOCKET_ERROR)
	{
		closesocket(Sck);
		return NULL;
	}
	
	if(setsockopt(Sck,SOL_SOCKET,SO_SNDTIMEO,
		(char * )&optval,sizeof(optval)) 
		== SOCKET_ERROR)
	{
		closesocket(Sck);
		return NULL;
	}
	
	if(setsockopt(Sck,SOL_SOCKET,SO_RCVTIMEO,
		(char * )&optval,sizeof(optval)) 
		== SOCKET_ERROR)
	{
		closesocket(Sck);
		return NULL;
	}
	
	if(listen(Sck, SOMAXCONN) == SOCKET_ERROR)
	{
		closesocket(Sck);
		return NULL;
	}
	
	return Sck;
}


int AcceptClientMain(SOCKET s)
{
	char ch = 0;
	int  nlinelen = 0;
	int  ret = 0;
	char slinedata[8192] = {0};
	//接收一行数据
	while(1)
	{
		//接收一个字符
		ret = recv(s,&ch,1,0);
		if(ret == 0 || ret == SOCKET_ERROR )
			return -1;
		
		//提取数据
		slinedata[nlinelen] = ch;
		if(nlinelen >= 4 &&
			slinedata[nlinelen] == '\n' &&
			slinedata[nlinelen - 1] == '\r' &&
			slinedata[nlinelen - 2] == '\n' &&
			slinedata[nlinelen - 3] == '\r')
		{			
			return 0;
		}
		
		if(nlinelen++ > 8000)
			return -1;
	}
	return 0;		
}

//接收数据
BOOL RecvData(SOCKET s, char *data, int len)
{
	char * p = data;
	int i = 0;
	int k = len;
	int ret = 0;
	
	if(len <= 0) return TRUE;
	while(1)
	{
		ret = recv(s,p,k,0);
		if(ret == 0 || ret == SOCKET_ERROR)
		{
			return FALSE;
		}
		i += ret;
		p += ret;
		k -= ret;
		if(i >= len) break;
	}
	return TRUE;
}

//发送数据
BOOL SendData(SOCKET s, char *data, int len)
{
	char * p = data;
	int i = 0;
	int k = len;
	int ret = 0;
	
	if(len <= 0) return TRUE;
	while(1)
	{
		ret = send(s,p,k,0);
		if(ret == 0 || ret == SOCKET_ERROR )
		{
//			TRACE("SendData OUT,%d\n",WSAGetLastError());
			return FALSE;
		}
		i += ret;
		p += ret;
		k -= ret;
		if(i >= len) break;
	}
	return TRUE;
}

BOOL ReadBag(SOCKET s, char* Data, int& Len)
{	
	//接收长度
	if(!RecvData(s, (char*) &Len, sizeof(DWORD)))
		return FALSE;
	
	//查看数据长度
	if(Len <= 0) return TRUE;
	
	//接收数据
	if(!RecvData(s, Data, Len)) return FALSE;
	
	
	return TRUE;
}

BOOL SendBag(SOCKET s, char* Data, int &Len)
{	
	//发送长度
	if(!SendData(s, (char*) &Len, sizeof(DWORD)))
		return FALSE;
	
	//查看数据长度
	if(Len <= 0) return TRUE;
	
	
	//发送数据
	if(!SendData(s, Data, Len)) return FALSE;
	
	return TRUE;
}

bool SendKeepAlive(SOCKET s)
{
	char m_sCommand[512] = {0};
	char m_Strlen[256];
	strcpy(m_sCommand,"HTTP/1.1 200 OK\r\n");
	strcat(m_sCommand,"Server: Microsoft-IIS/5.0\r\n");
	
	SYSTEMTIME stime;
	GetLocalTime(&stime);

	sprintf(m_Strlen,"Date:  %d %02d %02d %02d:%02d:%02d GMT\r\n",
		stime.wYear,stime.wMonth,stime.wDay,stime.wHour,stime.wMinute,stime.wSecond);
	strcat(m_sCommand,m_Strlen);
	sprintf(m_Strlen,"Content-Length: %d\r\n"
		,1024 * 1024 * 1024);
	strcat(m_sCommand,m_Strlen);
	strcat(m_sCommand,"Connection: Close\r\n");
	strcat(m_sCommand,"Cache-Control: no-cache\r\n\r\n");
	if(!SendData(s,m_sCommand,strlen(m_sCommand)))
	{
		closesocket(s);
		return false;
	}
	return true;
}

void httpbind2bind(int port1, int port2)
{
	SOCKET fd1,fd2, sockfd2;
	SOCKET SoSend, SoRecv;
	struct sockaddr_in client1,client2;
	int size1,size2;
	int nCmd;

	HANDLE hThread=NULL;
	httptransocket hsock;
	DWORD dwThreadID;
	
	if((fd1=create_socket())==0) return;
	if((fd2=create_socket())==0) return;
	
	printf("[+] Listening port %d ......\r\n",port1);
	fflush(stdout);
	
	if( (fd1 = StartTcp(port1))==SOCKET_ERROR)
	{
		closesocket(fd1);
		return;
	}
	
	printf("[+] Listen OK!\r\n");
	printf("[+] Listening port %d ......\r\n",port2);
	fflush(stdout);
	if(create_server(fd2, port2)==0)
	{
		closesocket(fd2);
		return;
	}
	
	
	printf("[+] Listen OK!\r\n");
	size1=size2=sizeof(struct sockaddr);
	while(1)
	{		
		printf("[+] Waiting for Client on port:%d ......\r\n",port1);
		//接收通道
		if((SoSend = accept(fd1,(struct sockaddr *)&client1,&size1))<0)
		{
			printf("[-] Accept Recv Socket error.\r\n");
			continue;
		}

		nCmd = AcceptClientMain(SoSend);
		if(nCmd == -1){ 
			closesocket(SoSend); 
			printf("[-] Accept Recv Socket error.\r\n");
			continue; 
		}


		if( !SendKeepAlive(SoSend) )			
		{
			closesocket(SoSend);
			printf("[-] Accept Recv Socket error.\r\n");
			continue;
		}
		
		
		printf("[+] Accept a Recv Socket on port %d from %s ......\r\n", port1, inet_ntoa(client1.sin_addr));

		//发送通道
		if((SoRecv = accept(fd1,(struct sockaddr *)&client1,&size1))<0)
		{
			printf("[-] Accept Send Socket error.\r\n");
			closesocket(SoRecv);
			continue;
		}

		nCmd = AcceptClientMain(SoRecv);
		if(nCmd == -1){ 
			closesocket(SoRecv);
			closesocket(SoSend);
			printf("[-] Accept Send Socket error.\r\n");
			continue; 
		}

		printf("[+] Accept a Send Socket on port %d from %s ......\r\n", port1, inet_ntoa(client1.sin_addr));

		//还要有一个接收通道		
		printf("[+] Waiting another Client on port:%d....\r\n", port2);
		if((sockfd2 = accept(fd2, (struct sockaddr *)&client2, &size2))<0)
		{
			printf("[-] Accept2 error.\r\n");
			closesocket(SoRecv);
			closesocket(SoSend);
			continue;
		}
		
		printf("[+] Accept a Client on port %d from %s\r\n",port2, inet_ntoa(client2.sin_addr));
		printf("[+] Accept Connect OK!\r\n");
		
		hsock.SoSend = SoSend;
		hsock.SoRecv = SoRecv;
		hsock.fd2    = sockfd2;
		
		HANDLE hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)httpLocaltransmit, (LPVOID)&hsock, 0, &dwThreadID); 
		if(hThread == NULL) 
		{
			TerminateThread(hThread, 0);
			return;
		}
		
		Sleep(1000);
		printf("[+] CreateThread OK!\r\n\n");
	}
}


void httpconn2conn(char *host1,int port1,char *host2,int port2)
{
		
	SOCKET sockfd2;
	
	HANDLE hThread=NULL;
	httptransocket2 sock;
	DWORD dwThreadID;

	

	DWORD l;
	char buffer[MAXSIZE];
			
	while(1)
	{		
		if((sockfd2=create_socket())==0) return;

		printf("[+] Make a Connection to %s:%d....\r\n",host1,port1);
		fflush(stdout);

		CMyHttpPipeBase *MyPipe = new CMyHttpPipeBase;									
		//创建接收和发送管道		
		if(!MyPipe->StartWork(host1, port1) ) 
		{
			MyPipe->StopWork();
			continue;
		}
		
		// if host1:port1 recved data, than connect to host2,port2
		l=0;
		memset(buffer,0,MAXSIZE);
		while(1)
		{
			if( !MyPipe->ReadBag(buffer,l) )
				break;

			if(l==0) 
			{ 
				Sleep(5);
				continue;
			}

			break;
		}
		
		if(l<=0) 
		{ 
			printf("[-] There is a error...Create a new connection.\r\n");
			MyPipe->StopWork();
			continue;
		}
			
		while(1)
		{
			printf("[+] Connect OK!\r\n");
			printf("[+] Make a Connection to %s:%d....\r\n", host2,port2);
			fflush(stdout);

			if(client_connect(sockfd2,host2,port2)==0) 
			{
				closesocket(sockfd2);
				continue;
			}
			
			if( !SendData(sockfd2,buffer,(int&)l) )
			{ 
				printf("[-] Send failed.\r\n");
				continue;
			}
			
			l=0;
			memset(buffer,0,MAXSIZE);
			break;
		}
		
		printf("[+] All Connect OK!\r\n");
		
		sock.MyPipe = (void *)MyPipe;
		sock.fd2    = sockfd2;
		
		hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)httpRemotetransmit, (LPVOID)&sock, 0, &dwThreadID); 
		if(hThread == NULL) 
		{
			TerminateThread(hThread, 0);
			return;
		}
		
		connectnum++;
		
		Sleep(1000);
		printf("[+] CreateThread OK!\r\n\n");
		WaitForSingleObject(hThread, INFINITE);
	}
}

void httpReadBag(LPVOID data)
{
	SOCKET fd2;
	httptransocket2 *hsock;

	int i=0;
	char read_in1[MAXSIZE],send_out1[MAXSIZE];

	int read1=0,totalread1=0,send1=0;
	int sendcount1;

	int structsize1;
	int port1=0,port2=0;
	
	hsock = (httptransocket2 *)data;
	CMyHttpPipeBase *MyPipe = (CMyHttpPipeBase *)hsock->MyPipe;
	fd2    = hsock->fd2;

	structsize1=sizeof(struct sockaddr);
	
	memset(read_in1,0,MAXSIZE);
	memset(send_out1,0,MAXSIZE);

	while(1)
	{
		/* must < MAXSIZE-totalread1, otherwise send_out1 will flow */
		if(totalread1 < MAXSIZE) {
			if(!MyPipe->ReadBag(read_in1,(DWORD &)read1))
			{
				printf("[-] ReadBag data error,maybe close?\r\n");
				break;
			}
			
			if( read1 > 0 )
			{
				memcpy(send_out1+totalread1,read_in1,read1);
				printf(" ReadBag %5d bytes\r\n", read1);				
				totalread1+=read1;
				memset(read_in1,0,MAXSIZE);
			}		
		}
													
		int err=0;
		sendcount1=0;
		while(totalread1>0)
		{
			send1=send(fd2, send_out1+sendcount1, totalread1, 0);
			if(send1==0)break;
			if((send1<0) && (errno!=EINTR))
			{
				printf("[-] Send to fd2 unknow error.\r\n");
				err=1;
				break;
			}
			
			if((send1<0) && (errno==ENOSPC)) break;
			sendcount1+=send1;
			totalread1-=send1;
			
			printf(" Send %5d bytes\r\n", send1);
		}
		
		if(err==1) break;
		if((totalread1>0) && (sendcount1>0))
		{
			/* move not sended data to start addr */
			memcpy(send_out1,send_out1+sendcount1,totalread1);
			memset(send_out1+totalread1,0,MAXSIZE-totalread1);
		}
		else
			memset(send_out1,0,MAXSIZE);
											
		Sleep(5);
	}

	closesocket(fd2);
	MyPipe->StopWork();
}

void httpRemotetransmit(LPVOID data)
{
	SOCKET fd2;
	httptransocket2 *hsock;
	struct timeval timeset;
	fd_set readfd;//,writefd;
	int result,i=0;
	char read_in2[MAXSIZE],send_out2[MAXSIZE];
	int read2=0,totalread2=0,send2=0;


	int structsize2;
	char host1[20],host2[20];
	int port1=0,port2=0;
	
	hsock = (httptransocket2 *)data;
	CMyHttpPipeBase *MyPipe = (CMyHttpPipeBase *)hsock->MyPipe;
	fd2    = hsock->fd2;

	memset(host1,0,20);
	memset(host2,0,20);

	structsize2=sizeof(struct sockaddr);

	memset(read_in2,0,MAXSIZE);
	memset(send_out2,0,MAXSIZE);
	
	timeset.tv_sec=TIMEOUT;
	timeset.tv_usec=0;
	

	//线程:从http隧道读取数据并转发
	DWORD dwThreadID;
	HANDLE hThread = hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)httpReadBag, data, 0, &dwThreadID); 

	//从RemoteProcess读取数据,通过http隧道转发。
	while(1)
	{	
		FD_ZERO(&readfd);
		
		FD_SET((UINT)fd2, &readfd);
				
		result=select(fd2+1,&readfd,NULL,NULL,×et);
		if((result<0) && (errno!=EINTR))
		{
			printf("[-] Select error.\r\n");
			break;
		}
		else if(result==0)
		{
			printf("[-] Socket time out.\r\n");
			break;
		}
													
		if(FD_ISSET(fd2, &readfd))
		{
			if(totalread2 < MAXSIZE) {				
				read2=recv(fd2,read_in2,MAXSIZE-totalread2, 0); 
				if(read2==0)break;
				if((read2<0) && (errno!=EINTR))
				{
					DWORD error = GetLastError();
					printf("[-] Read fd2 data error,maybe close?\r\n\r\n");
					break;
				}
				
				memcpy(send_out2+totalread2,read_in2,read2);

				printf(" Recv %5d bytes\r\n", read2);

				totalread2+=read2;
				memset(read_in2,0,MAXSIZE);

				int err2=0;
				if(totalread2>0)
				{
					if(!MyPipe->SendBag(send_out2, (DWORD &)totalread2))
					{
						printf("[-] Send to fd1 unknow error.\r\n");
						err2=1;
						break;
					}
					
					printf(" Send %5d bytes\r\n", totalread2);
				}
				if(err2==1) break;
				totalread2 = 0;
				
				memset(send_out2,0,MAXSIZE);
				
			}
		}

		
		
		Sleep(5);
	}

	closesocket(fd2);
	MyPipe->StopWork();

	TerminateThread(hThread, 0);
	delete MyPipe;
	

	if(method == 3)
	connectnum --;

	printf("\r\n[+] OK! I Closed The Three Socket.\r\n"); 
}

void httpLocaltransmit(LPVOID data)
{
	SOCKET SoSend, SoRecv, fd2;
	httptransocket *hsock;
	struct timeval timeset;
	fd_set readfd,writefd;
	int result,i=0;
	char read_in1[MAXSIZE],send_out1[MAXSIZE];
	char read_in2[MAXSIZE],send_out2[MAXSIZE];
	int read1=0,totalread1=0,send1=0;
	int read2=0,totalread2=0,send2=0;
	int sendcount1;
	int maxfd;
	struct sockaddr_in client1,client2;
	int structsize1,structsize2;
	char host1[20],host2[20];
	int port1=0,port2=0;
	char tmpbuf[100];
	
	hsock = (httptransocket *)data;
	SoSend = hsock->SoSend;
	SoRecv = hsock->SoRecv;
	fd2    = hsock->fd2;
	
	memset(host1,0,20);
	memset(host2,0,20);
	memset(tmpbuf,0,100);
	
	structsize1=sizeof(struct sockaddr);
	structsize2=sizeof(struct sockaddr);
	
	if(getpeername(SoSend,(struct sockaddr *)&client1,&structsize1)<0)
	{
		strcpy(host1, "fd1");
	}
	else
	{ 
		printf("[+]got, ip:%s, port:%d\r\n",inet_ntoa(client1.sin_addr),ntohs(client1.sin_port));
		strcpy(host1, inet_ntoa(client1.sin_addr));
		port1=ntohs(client1.sin_port);
	}
	
	if(getpeername(fd2,(struct sockaddr *)&client2,&structsize2)<0)
	{
		strcpy(host2,"fd2");
	}
	else
	{ 
		printf("[+]got, ip:%s, port:%d\r\n",inet_ntoa(client2.sin_addr),ntohs(client2.sin_port));
		strcpy(host2, inet_ntoa(client2.sin_addr));
		port2=ntohs(client2.sin_port);
	}
	
	printf("[+] Start Transmit (%s:%d <-> %s:%d) ......\r\n\n", host1, port1, host2, port2);
	
	maxfd=max(max(SoRecv, SoSend),fd2)+1;
	memset(read_in1,0,MAXSIZE);
	memset(read_in2,0,MAXSIZE);
	memset(send_out1,0,MAXSIZE);
	memset(send_out2,0,MAXSIZE);
	
	timeset.tv_sec=TIMEOUT;
	timeset.tv_usec=0;
	
	while(1)
	{
		FD_ZERO(&readfd);
		FD_ZERO(&writefd);
		
		FD_SET((UINT)SoRecv, &readfd);
		FD_SET((UINT)SoSend, &writefd);
		FD_SET((UINT)fd2, &writefd);
		FD_SET((UINT)fd2, &readfd);
		
		result=select(maxfd,&readfd,&writefd,NULL,×et);
		if((result<0) && (errno!=EINTR))
		{
			printf("[-] Select error.\r\n");
			break;
		}
		else if(result==0)
		{
			printf("[-] Socket time out.\r\n");
			break;
		}
		
		if(FD_ISSET(SoRecv, &readfd))
		{
			/* must < MAXSIZE-totalread1, otherwise send_out1 will flow */
			if(totalread1 < MAXSIZE) {
				if( !ReadBag(SoRecv,read_in1,read1) )				
				{
					printf("[-] Read SoRecv data error,maybe close?\r\n");
					break;
				}
				
				if( read1 > 0 )
				{
					memcpy(send_out1+totalread1,read_in1,read1);				
					printf(" Recv %5d bytes %16s:%d\r\n", read1, host1, port1);
					totalread1+=read1;
					memset(read_in1,0,MAXSIZE);
				}
				
			}
		}
		
		if(FD_ISSET(fd2, &writefd))
		{
			int err=0;
			sendcount1=0;
			while(totalread1>0)
			{
				send1=send(fd2, send_out1+sendcount1, totalread1, 0);
				if(send1==0)break;
				if((send1<0) && (errno!=EINTR))
				{
					printf("[-] Send to fd2 unknow error.\r\n");
					err=1;
					break;
				}
				
				if((send1<0) && (errno==ENOSPC)) break;
				sendcount1+=send1;
				totalread1-=send1;
				
				printf(" Send %5d bytes %16s:%d\r\n", send1, host2, port2);
			}
			
			if(err==1) break;
			if((totalread1>0) && (sendcount1>0))
			{
				/* move not sended data to start addr */
				memcpy(send_out1,send_out1+sendcount1,totalread1);
				memset(send_out1+totalread1,0,MAXSIZE-totalread1);
			}
			else
				memset(send_out1,0,MAXSIZE);
		}
		
		if(FD_ISSET(fd2, &readfd))
		{
			if(totalread2 < MAXSIZE) {
				read2=recv(fd2,read_in2,MAXSIZE-totalread2, 0); 
				if(read2==0)break;
				if((read2<0) && (errno!=EINTR))
				{
					printf("[-] Read fd2 data error,maybe close?\r\n\r\n");
					break;
				}
				
				memcpy(send_out2+totalread2,read_in2,read2);
				sprintf(tmpbuf, "\r\nRecv %5d bytes from %s:%d\r\n", read2, host2, port2);
				printf(" Recv %5d bytes %16s:%d\r\n", read2, host2, port2);
				makelog(tmpbuf,strlen(tmpbuf));
				makelog(read_in2,read2);
				totalread2+=read2;
				memset(read_in2,0,MAXSIZE);
			}
		}
		
		if(FD_ISSET(SoSend, &writefd))
		{
			int err2=0;
			if(totalread2>0)
			{
				if( !SendBag(SoSend, send_out2, totalread2) )				
				{
					printf("[-] Send to fd1 unknow error.\r\n");
					err2=1;
					break;
				}			
				
				printf(" Send %5d bytes %16s:%d\r\n", totalread2, host1, port1);
			}
			if(err2==1) break;

			totalread2 = 0;
			memset(send_out2,0,MAXSIZE);
		}
		
		Sleep(5);
	}

	closesocket(SoRecv);
	closesocket(SoSend);
	closesocket(fd2);

	if(method == 3)
	connectnum --;

	printf("\r\n[+] OK! I Closed The Three Socket.\r\n"); 
}



void closeallfd()
{
	int i;
	
	printf("[+] Let me exit ......\r\n");
	fflush(stdout);
	
	for(i=3; i<256; i++)
	{
		closesocket(i); 
	}
	
	if(fp != NULL) 
	{
		fprintf(fp,"\r\n====== Exit ======\r\n");
		fclose(fp);
	}
	
	printf("[+] All Right!\r\n");
}

int create_socket()
{ 
	int sockfd;
	
	sockfd=socket(AF_INET,SOCK_STREAM,0);
	if(sockfd<0)
	{
		printf("[-] Create socket error.\r\n");
		return(0);
	}
	
	return(sockfd); 
}

int create_server(int sockfd,int port)
{
	struct sockaddr_in srvaddr;
	int on=1;
	
	memset(&srvaddr, 0, sizeof(struct sockaddr));
	
	srvaddr.sin_port=htons(port);
	srvaddr.sin_family=AF_INET;
	srvaddr.sin_addr.s_addr=htonl(INADDR_ANY);
	
	setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR, (char*)&on,sizeof(on)); //so I can rebind the port
	
	if(bind(sockfd,(struct sockaddr *)&srvaddr,sizeof(struct sockaddr))<0)
	{
		printf("[-] Socket bind error.\r\n");
		return(0);
	}
	
	if(listen(sockfd,CONNECTNUM)<0)
	{
		printf("[-] Socket Listen error.\r\n");
		return(0);
	}
	
	return(1);
}

int client_connect(int sockfd,char* server,int port)
{
	struct sockaddr_in cliaddr;
	struct hostent *host;
	
	if(!(host=gethostbyname(server)))
	{
		printf("[-] Gethostbyname(%s) error:%s\n",server,strerror(errno));
		return(0);
	}
	
	memset(&cliaddr, 0, sizeof(struct sockaddr));
	cliaddr.sin_family=AF_INET;
	cliaddr.sin_port=htons(port);
	cliaddr.sin_addr=*((struct in_addr *)host->h_addr);
	
	if(connect(sockfd,(struct sockaddr *)&cliaddr,sizeof(struct sockaddr))<0)
	{
		printf("[-] Connect error.\r\n");
		return(0);
	}
	return(1);
}

void makelog(char *buffer,int length)
{
	if(fp !=NULL)
	{	
		write(fileno(fp),buffer,length);
	}
}


void getctrlc(int j)
{
	printf("\r\n[-] Received Ctrl+C\r\n");
	closeallfd();
	exit(0);
}

MyHttpBase.h

// MyHttpBase.h: interface for the CMyHttpBase class.
//
//////////////////////////////////////////////////////////////////////

#if !defined(AFX_MYHTTPBASE_H__8D08074A_C1F4_43E9_9B8B_0CAD734C43BA__INCLUDED_)
#define AFX_MYHTTPBASE_H__8D08074A_C1F4_43E9_9B8B_0CAD734C43BA__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000



class CMyHttpBase  
{
public:

	BOOL ConnectHttpServer( char* m_ServerAddr , 
							int m_ServerPort,
							DWORD nStyle);
	void StopWork();

	HINTERNET	hHttpFp;
	CMyHttpBase();
	virtual ~CMyHttpBase();

private:
	HINTERNET	hHttpIe;
	HINTERNET	hHttpHc;

};

#endif // !defined(AFX_MYHTTPBASE_H__8D08074A_C1F4_43E9_9B8B_0CAD734C43BA__INCLUDED_)

MyHttpBase.cpp

// MyHttpBase.cpp: implementation of the CMyHttpBase class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "MyHttpBase.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CMyHttpBase::CMyHttpBase()
{
	hHttpFp = NULL;
	hHttpIe = NULL;
	hHttpHc = NULL;
}

CMyHttpBase::~CMyHttpBase()
{
	StopWork();
}

void CMyHttpBase::StopWork()
{
	if(hHttpFp != NULL)
	{
		InternetCloseHandle(hHttpFp);
		hHttpFp = NULL;
	}
	if(hHttpHc != NULL)
	{
		InternetCloseHandle(hHttpHc);
		hHttpHc = NULL;
	}
	if(hHttpIe != NULL)
	{
		InternetCloseHandle(hHttpIe);
		hHttpIe = NULL;
	}
}

/*	
**	函数名称:	ConnectHttpServer
**	函数功能:	连接到服务器
**	传入参数:	m_ServerAddr : 服务器IP
				m_ServerPort : 服务器端口
				nCmd		 : 连接类型	
**	传出参数:	无
**	引用函数:	无
**	返回值	:	布尔型
**	备注	:	
*/
BOOL CMyHttpBase::ConnectHttpServer(char* m_ServerAddr , 
									int m_ServerPort,
									DWORD nStyle)
{
	//中断上次连接
	StopWork();

	//检查数据有效性
	if(strlen(m_ServerAddr) == 0
		|| m_ServerPort == 0)
		return FALSE;

	//初始化HTTP环境
	hHttpIe = InternetOpen("Mozilla/4.0 (compatible; MSIE 6.0; "
							"Windows NT 5.0; .NET CLR 1.1.4322)",
							INTERNET_OPEN_TYPE_PRECONFIG,NULL,NULL,0);
	if(!hHttpIe) return FALSE;
		
	//填充主机地址
	hHttpHc = InternetConnect(hHttpIe,
		m_ServerAddr , m_ServerPort , NULL, 
		NULL , INTERNET_SERVICE_HTTP,0,0);	
	if(!hHttpHc)
	{
		StopWork();
		return FALSE;
	}

	//填充上送当前客户信息
	hHttpFp = HttpOpenRequest(hHttpHc,
		"POST","id=1",NULL,NULL,NULL,nStyle,NULL);
	if(!hHttpFp)
	{
		StopWork();
		return FALSE;
	}

	DWORD m_TimeOut = 24 * 3600 * 1000;
	if(!InternetSetOption(hHttpFp,
		INTERNET_OPTION_RECEIVE_TIMEOUT,&m_TimeOut,sizeof(DWORD)))
	{
		StopWork();
		return FALSE;
	}
	return TRUE;
}

MyHttpPipeBase.h

// MyHttpPipeBase.h: interface for the CMyHttpPipeBase class.
//
//////////////////////////////////////////////////////////////////////

#if !defined(AFX_MYHTTPPIPEBASE_H__33524551_7C26_4EE5_BF3D_D8B751B46BD4__INCLUDED_)
#define AFX_MYHTTPPIPEBASE_H__33524551_7C26_4EE5_BF3D_D8B751B46BD4__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#include "MyHttpBase.h"

class CMyHttpPipeBase  
{
public:
	void StopWork();
	virtual BOOL StartWork(char* m_ServerAddr, int m_ServerPort);
	CMyHttpPipeBase();
	virtual ~CMyHttpPipeBase();

	BOOL SendData(char* pData, DWORD nLen);
	BOOL RecvData(char* pData, DWORD nLen);

	BOOL SendBag(char* Data, DWORD &Len);
	BOOL ReadBag(char* Data, DWORD &Len);
private:

	CMyHttpBase m_PipeSend;
	CMyHttpBase m_PipeRecv;
};

#endif // !defined(AFX_MYHTTPPIPEBASE_H__33524551_7C26_4EE5_BF3D_D8B751B46BD4__INCLUDED_)

MyHttpPipeBase.cpp

// MyHttpPipeBase.cpp: implementation of the CMyHttpPipeBase class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "MyHttpPipeBase.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CMyHttpPipeBase::CMyHttpPipeBase()
{

}

CMyHttpPipeBase::~CMyHttpPipeBase()
{
	StopWork();
}

BOOL CMyHttpPipeBase::StartWork(char* m_ServerAddr, int m_ServerPort)
{
	//创建接收管道
	if(!m_PipeRecv.ConnectHttpServer(
		m_ServerAddr, m_ServerPort,
		INTERNET_FLAG_PRAGMA_NOCACHE|
		INTERNET_FLAG_NO_CACHE_WRITE|
		INTERNET_FLAG_RELOAD))
	{
		StopWork();
		return FALSE;
	}

	//连接接收管道
	if(!HttpSendRequest(m_PipeRecv.hHttpFp , NULL , 0 , NULL, 0))
	{
		StopWork();
		return FALSE;
	}

	//创建发送管道
	if(!m_PipeSend.ConnectHttpServer(
		m_ServerAddr, m_ServerPort,
		INTERNET_FLAG_PRAGMA_NOCACHE|
		INTERNET_FLAG_NO_CACHE_WRITE|
		INTERNET_FLAG_RELOAD))
	{
		StopWork();
		return FALSE;
	}

	//连接发送管道
	INTERNET_BUFFERS BufferIn = {0};
    BufferIn.dwStructSize = sizeof( INTERNET_BUFFERS );
	BufferIn.dwBufferTotal = 1024 * 1024 * 1024 + 973741824;
	if(!HttpSendRequestEx(m_PipeSend.hHttpFp,
		&BufferIn,NULL,HSR_INITIATE,0))
	{
		StopWork();
		return FALSE;
	}
	return TRUE;
}

BOOL CMyHttpPipeBase::ReadBag(char* Data, DWORD& Len)
{	
	//接收长度
	if(!RecvData((char*) &Len, sizeof(DWORD)))
		return FALSE;
		
	//查看数据长度
	if(Len <= 0) return TRUE;
	
	//接收数据
	if(!RecvData(Data, Len)) return FALSE;
	

	return TRUE;
}

BOOL CMyHttpPipeBase::SendBag(char* Data, DWORD &Len)
{	
	//发送长度
	if(!SendData((char*) &Len, sizeof(DWORD)))
		return FALSE;
		
	//查看数据长度
	if(Len <= 0) return TRUE;
	
	
	//发送数据
	if(!SendData(Data, Len)) return FALSE;
	
	return TRUE;
}

BOOL CMyHttpPipeBase::SendData(char* pData, DWORD nLen)
{
	//发送数据
	DWORD dwBytesWritten = 0;
	if(!InternetWriteFile(m_PipeSend.hHttpFp , 
		pData , nLen , &dwBytesWritten))
		return FALSE;
	return TRUE;
}

BOOL CMyHttpPipeBase::RecvData(char* pData, DWORD nLen)
{ 
	char *p = (char*) pData;
	DWORD dwNumberOfBytesToRead = nLen;
	DWORD dwNumberOfBytesReaded = 0;
	while(dwNumberOfBytesToRead > 0)
	{
		if(!InternetReadFile(m_PipeRecv.hHttpFp,p,
			dwNumberOfBytesToRead,&dwNumberOfBytesReaded))
			return FALSE;
		
		if(dwNumberOfBytesReaded == 0)
			return FALSE;
		
		p += dwNumberOfBytesReaded;
		dwNumberOfBytesToRead -= dwNumberOfBytesReaded;
	}
	
	//解密
	return TRUE;
}

void CMyHttpPipeBase::StopWork()
{
	m_PipeRecv.StopWork();
	m_PipeSend.StopWork();
}

StdAfx.h

// stdafx.h : include file for standard system include files,
//  or project specific include files that are used frequently, but
//      are changed infrequently
//

#if !defined(AFX_STDAFX_H__BA34C346_10E9_4869_A1B9_9F0B974A6A85__INCLUDED_)
#define AFX_STDAFX_H__BA34C346_10E9_4869_A1B9_9F0B974A6A85__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#define WINVER 0X400
#define _WIN32_IE 0x0500

#include <winsock2.h>
#include <Windows.h>
#include <Wininet.h>
//#include <winsock.h>

#pragma comment(lib, "ws2_32.lib")
#pragma comment(lib, "wininet.lib")

//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.

#endif // !defined(AFX_STDAFX_H__BA34C346_10E9_4869_A1B9_9F0B974A6A85__INCLUDED_)

查看评论

Javaweb开发基础视频教程之http协议

-
  • 1970年01月01日 08:00

linux下的lcx源码,修改无错可用版

http://twi1ight.org/2013/02/42.html   网上关于linux下面的lcx源码很多,大部分在现在的linux环境下编译都存在错误,而且代码本身con2con函数存在...
  • xumaojun
  • xumaojun
  • 2013-10-17 12:00:23
  • 3761

lcx端口转发工具的使用

Linux版lcx端口转发工具使用 0x01 前言 在实际情况中,web应用服务通常会被运行在内网机器上,然后通过端口映射到外网,供外网用户进行访问。如果我们已经攻破网站,拿到内网机器权限,通...
  • qq_33411563
  • qq_33411563
  • 2016-12-13 11:47:14
  • 2013

内网打洞,类似于lcx 但是比他更加强大

经常有朋友用lcx的,但是由于很多原因可能都不好使,例如 : 1.linux下能用lcx,有时只能拿msf出来。(golang的程序跨平台,甚至嵌入式linux都支持。) 2.不免杀  (基本上目前g...
  • yatere
  • yatere
  • 2015-04-28 18:06:00
  • 2971

linux下内网端口转发工具:linux版lcx 使用方法

这个工具以前使用的初衷是内网渗透,需要将内网ssh端口转发到外网服务器上。但这个工具同样适用于运维工程师进行远程内网维护。 当然这一切的前提是内网可以访问外网,检测方法当然就是直接ping 一个外网I...
  • wyvbboy
  • wyvbboy
  • 2017-03-14 10:19:46
  • 2586

HTTP代理原理以及HTTP隧道技术(经典)

通过HTTP协议与代理服务器建立连接,协议信令中包含要连接到的远程主机的IP和端口号,如果有需要身份验证的话还需要加上授权信息,服务器收到信令后首先进行身份验证,通过后便与远程主机建立连接,连接成功之...
  • zhangxinrun
  • zhangxinrun
  • 2010-10-14 16:08:00
  • 10599

Http与HTTP隧道技术

HTTP是一个客户端和服务端请求和应答的标准(TCP)客户端是终端用户,服务器端是网站。通过使用Web浏览器、网络爬虫或者其它的工具,客户端发起一个到服务器上指定端口(默认端口为80)的HTTP请求。...
  • SauceJ
  • SauceJ
  • 2015-03-12 16:40:23
  • 1901

使用LCX进行内网端口转发

局域网中的某台计算机仅仅开放了Web服务,该服务仅能供内网用户使用,而外网用户根本没有办法直接访问。因此要想让外网用户能够访问局域网中的系统服务,这必须进行端口映射等操作才行。端口映射在入侵内网的时候...
  • xiaoshan812613234
  • xiaoshan812613234
  • 2014-08-11 16:47:23
  • 2934

HTTP——网关、隧道、中继、Agent代理

随着时间流逝,人们已经从网上浏览静态资源,发展到共享更复杂的资源,比如数据库内容或动态生成的页面,因此,本篇文章介绍几种用HTTP访问不同资源的方法。 网关 网关是资源和应用程序之间的粘合剂,可以...
  • StubbornPotatoes
  • StubbornPotatoes
  • 2014-03-05 19:50:18
  • 4399

c实现HTTP 隧道

HTTP 隧道 (HTTP代理Socket客户)----------------------------------------------------------------------------...
  • yangdelong
  • yangdelong
  • 2007-04-25 14:56:00
  • 2527
    个人资料
    持之以恒
    等级:
    访问量: 16万+
    积分: 2653
    排名: 1万+
    博客专栏
    友情链接
    最新评论