Implement SOCKS proxy feature
This commit is contained in:
309
server/2015Remote/proxy/ProxyMapDlg.cpp
Normal file
309
server/2015Remote/proxy/ProxyMapDlg.cpp
Normal file
@@ -0,0 +1,309 @@
|
||||
// ProxyMapDlg.cpp : implementation file
|
||||
//
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "2015Remote.h"
|
||||
#include "ProxyMapDlg.h"
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define new DEBUG_NEW
|
||||
#endif
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CProxyMapDlg dialog
|
||||
|
||||
#define IDM_PROXY_CHROME 8000
|
||||
|
||||
CProxyMapDlg::CProxyMapDlg(CWnd* pParent, ISocketBase* pIOCPServer, ClientContext* pContext)
|
||||
: CDialog(CProxyMapDlg::IDD, pParent)
|
||||
{
|
||||
m_iocpServer = pIOCPServer;
|
||||
m_ContextObject = pContext;
|
||||
m_iocpLocal = NULL;
|
||||
m_hIcon = LoadIcon(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDI_Proxifier));
|
||||
m_bIsClose = false;
|
||||
}
|
||||
|
||||
void CProxyMapDlg::DoDataExchange(CDataExchange* pDX)
|
||||
{
|
||||
CDialog::DoDataExchange(pDX);
|
||||
DDX_Control(pDX, IDC_EDIT, m_Edit);
|
||||
DDX_Control(pDX, IDC_EDIT_OTHER, m_EditOther);
|
||||
}
|
||||
|
||||
BEGIN_MESSAGE_MAP(CProxyMapDlg, CDialog)
|
||||
ON_WM_SYSCOMMAND()
|
||||
ON_WM_SIZE()
|
||||
END_MESSAGE_MAP()
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
BOOL CProxyMapDlg::OnInitDialog()
|
||||
{
|
||||
CDialog::OnInitDialog();
|
||||
|
||||
SetIcon(m_hIcon, TRUE); // Set big icon
|
||||
SetIcon(m_hIcon, FALSE); // Set small icon
|
||||
// TODO: Add extra initialization here
|
||||
m_iocpLocal = new CProxyConnectServer;
|
||||
|
||||
if (m_iocpLocal == NULL) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
m_Edit.SetLimitText(MAXDWORD);
|
||||
m_EditOther.SetLimitText(MAXDWORD);
|
||||
CString str;
|
||||
|
||||
// <20><><EFBFBD><EFBFBD>IPCP<43><50><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
m_nPort = 5543;
|
||||
if (!m_iocpLocal->Initialize(NotifyProc, this, 100000, m_nPort)) {
|
||||
AfxMessageBox("<EFBFBD><EFBFBD>ʼ<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʧ<EFBFBD><EFBFBD>!");
|
||||
return FALSE;
|
||||
}
|
||||
TCHAR ip[256] = {};
|
||||
int len = sizeof(ip);
|
||||
m_iocpLocal->m_TcpServer->GetListenAddress(ip, len, m_nPort);
|
||||
|
||||
CString strString;
|
||||
sockaddr_in ClientAddress;
|
||||
memset(&ClientAddress, 0, sizeof(ClientAddress));
|
||||
int iClientAddressLength = sizeof(ClientAddress);
|
||||
BOOL bResult = getpeername(m_ContextObject->sClientSocket, (SOCKADDR*)&ClientAddress, &iClientAddressLength);
|
||||
strString.Format("%s - <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>", bResult != INVALID_SOCKET ? inet_ntoa(ClientAddress.sin_addr) : "");
|
||||
SetWindowText(strString);
|
||||
|
||||
str.Format(_T("SOCKS <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>÷<EFBFBD><C3B7><EFBFBD><EFBFBD><EFBFBD>Ϊ: <127.0.0.1:%d>\r\n"), m_nPort);
|
||||
AddLog(str.GetBuffer(0));
|
||||
|
||||
CMenu* pSysMenu = GetSystemMenu(FALSE);
|
||||
if (pSysMenu != NULL) {
|
||||
pSysMenu->AppendMenu(MF_SEPARATOR);
|
||||
pSysMenu->AppendMenu(MF_STRING, IDM_PROXY_CHROME, _T("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Chrome(<28><><EFBFBD>ر<EFBFBD><D8B1><EFBFBD><EFBFBD><EFBFBD>Chrome<6D><65><EFBFBD><EFBFBD>)(&P)"));
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void CProxyMapDlg::OnCancel()
|
||||
{
|
||||
if (m_bIsClose) return;
|
||||
|
||||
m_bIsClose = true;
|
||||
m_iocpServer->Disconnect(m_ContextObject);
|
||||
DestroyIcon(m_hIcon);
|
||||
m_iocpLocal->Shutdown();
|
||||
SAFE_DELETE(m_iocpLocal);
|
||||
CancelIo((HANDLE)m_ContextObject->sClientSocket);
|
||||
closesocket(m_ContextObject->sClientSocket);
|
||||
Sleep(50);
|
||||
if (IsWindow(m_hWnd))
|
||||
DestroyWindow();
|
||||
}
|
||||
|
||||
void CALLBACK CProxyMapDlg::NotifyProc(void *user, ClientContext* pContext, UINT nCode)
|
||||
{
|
||||
CProxyMapDlg* g_pProxyMap = (CProxyMapDlg*)user;
|
||||
if (g_pProxyMap->m_bIsClose) return;
|
||||
|
||||
DWORD index = pContext->ID;
|
||||
TCHAR szMsg[200] = { 0 };
|
||||
try {
|
||||
switch (nCode) {
|
||||
case NC_CLIENT_CONNECT:
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>\r\n"), index);
|
||||
break;
|
||||
case NC_CLIENT_DISCONNECT:
|
||||
if (pContext->m_bProxyConnected) {
|
||||
BYTE lpData[5] = "";
|
||||
lpData[0] = COMMAND_PROXY_CLOSE;
|
||||
memcpy(lpData + 1, &index, sizeof(DWORD));
|
||||
g_pProxyMap->m_iocpServer->Send(g_pProxyMap->m_ContextObject, lpData, 5);
|
||||
}
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ӶϿ<D3B6>\r\n"), index);
|
||||
break;
|
||||
case NC_TRANSMIT:
|
||||
break;
|
||||
case NC_RECEIVE:
|
||||
if (pContext->m_bProxyConnected == 2) {
|
||||
g_pProxyMap->m_iocpServer->Send(g_pProxyMap->m_ContextObject, pContext->InDeCompressedBuffer.GetBuffer(0),
|
||||
pContext->InDeCompressedBuffer.GetBufferLength());
|
||||
wsprintf(szMsg, _T("%d <==<3D><> %d bytes\r\n"), index, pContext->InDeCompressedBuffer.GetBufferLength() - 5);
|
||||
} else if (pContext->m_bProxyConnected == 0) {
|
||||
char msg_auth_ok[] = { 0X05, 0X00 }; // VERSION SOCKS, AUTH MODE, OK
|
||||
LPBYTE lpData = pContext->InDeCompressedBuffer.GetBuffer(5);
|
||||
pContext->m_bProxyConnected = 1;
|
||||
g_pProxyMap->m_iocpLocal->Send(pContext, (LPBYTE)msg_auth_ok, sizeof(msg_auth_ok));
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD>ر<EFBFBD>ʾ %d %d %d\r\n"), index, lpData[0], lpData[1], lpData[2]);
|
||||
} else if (pContext->m_bProxyConnected == 1) {
|
||||
LPBYTE lpData = pContext->InDeCompressedBuffer.GetBuffer(5);
|
||||
BYTE buf[11] = {};
|
||||
if (lpData[0] == 5 && lpData[1] == 1 && (pContext->InDeCompressedBuffer.GetBufferLength() > 10)) {
|
||||
if (lpData[3] == 1) { // ipv4
|
||||
buf[0] = COMMAND_PROXY_CONNECT; // 1<><31><EFBFBD>ֽ<EFBFBD> ip v4 <20><><EFBFBD><EFBFBD>
|
||||
memcpy(buf + 1, &index, 4); // <20>ĸ<EFBFBD><C4B8>ֽ<EFBFBD> <20><EFBFBD><D7BD>ֵı<D6B5><C4B1><EFBFBD>
|
||||
memcpy(buf + 5, lpData + 4, 6); // 4<>ֽ<EFBFBD>ip 2<>ֽڶ˿<DAB6>
|
||||
g_pProxyMap->m_iocpServer->Send(g_pProxyMap->m_ContextObject, buf, sizeof(buf));
|
||||
in_addr inaddr = {};
|
||||
inaddr.s_addr = *(DWORD*)(buf + 5);
|
||||
char szmsg1[MAX_PATH];
|
||||
wsprintfA(szmsg1, "%d IPV4 <20><><EFBFBD><EFBFBD> %s:%d...\r\n", index, inet_ntoa(inaddr), ntohs(*(USHORT*)(buf + 9)));
|
||||
} else if (lpData[3] == 3) { // <20><><EFBFBD><EFBFBD>
|
||||
Socks5Info* Socks5Request = (Socks5Info*)lpData;
|
||||
BYTE* HostName = new BYTE[Socks5Request->IP_LEN + 8];
|
||||
ZeroMemory(HostName, Socks5Request->IP_LEN + 8);
|
||||
HostName[0] = COMMAND_PROXY_CONNECT_HOSTNAME;
|
||||
memcpy(HostName + 7, &Socks5Request->szIP, Socks5Request->IP_LEN);
|
||||
memcpy(HostName + 1, &index, 4);
|
||||
memcpy(HostName + 5, &Socks5Request->szIP + Socks5Request->IP_LEN, 2);
|
||||
g_pProxyMap->m_iocpServer->Send(g_pProxyMap->m_ContextObject, HostName, Socks5Request->IP_LEN + 8);
|
||||
SAFE_DELETE_ARRAY(HostName);
|
||||
wsprintf(szMsg, _T("<EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> %d \r\n"), index);
|
||||
} else if (lpData[3] == 4) { //ipv6
|
||||
char msg_ipv6_nok[] = { 0X05, 0X08, 0X00, 0X01, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00 }; // IPv6 not support
|
||||
wsprintf(szMsg, _T("%d IPV6<56><36><EFBFBD><EFBFBD> <20><>֧<EFBFBD><D6A7>..."), index);
|
||||
g_pProxyMap->m_iocpLocal->Send(pContext, (LPBYTE)msg_ipv6_nok, sizeof(msg_ipv6_nok));
|
||||
g_pProxyMap->m_iocpLocal->Disconnect(pContext->m_Socket);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
buf[0] = 5;
|
||||
buf[1] = 7;
|
||||
buf[2] = 0;
|
||||
buf[3] = lpData[3];
|
||||
g_pProxyMap->m_iocpLocal->Send(pContext, buf, sizeof(buf));
|
||||
g_pProxyMap->m_iocpLocal->Disconnect(pContext->m_Socket);
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD><EFBFBD>Ҫ<EFBFBD><D2AA>, <20>Ͽ<EFBFBD> %d %d %d\r\n"), index, lpData[0], lpData[1], lpData[3]);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
} catch (...) {}
|
||||
if (szMsg[0])
|
||||
g_pProxyMap->AddLog_other(szMsg);
|
||||
return;
|
||||
}
|
||||
|
||||
void CProxyMapDlg::OnReceive()
|
||||
{
|
||||
}
|
||||
|
||||
void CProxyMapDlg::OnReceiveComplete()
|
||||
{
|
||||
if (m_iocpLocal == NULL)
|
||||
return;
|
||||
|
||||
if (m_iocpLocal->m_TcpServer->HasStarted() == FALSE || m_bIsClose)
|
||||
return;
|
||||
|
||||
LPBYTE buf = m_ContextObject->m_DeCompressionBuffer.GetBuffer(0);
|
||||
DWORD index = *(DWORD*)&buf[1];
|
||||
TCHAR szMsg[200];
|
||||
switch (buf[0]) {
|
||||
case TOKEN_PROXY_CONNECT_RESULT: {
|
||||
char msg_request_co_ok[] = { 0X05, 0X00, 0X00, 0X01, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00 }; // Request connect OK
|
||||
|
||||
BYTE sendbuf[10] = "";
|
||||
sendbuf[0] = 5;
|
||||
sendbuf[1] = (buf[9] || buf[10]) ? 0 : 5;
|
||||
sendbuf[2] = 0;
|
||||
sendbuf[3] = 1;
|
||||
memcpy(&sendbuf[4], &buf[5], 6);
|
||||
|
||||
ClientContext* pContext_proxy = NULL;
|
||||
if (m_iocpLocal->m_TcpServer->GetConnectionExtra((CONNID)index, (PVOID*)&pContext_proxy) && pContext_proxy != nullptr) {
|
||||
if (sendbuf[1] == 0) {
|
||||
pContext_proxy->m_bProxyConnected = 2;
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD>ӳɹ<D3B3>\r\n"), index);
|
||||
} else
|
||||
wsprintf(szMsg, _T("%d <20><><EFBFBD><EFBFBD>ʧ<EFBFBD><CAA7>\r\n"), index);
|
||||
m_iocpLocal->Send(pContext_proxy, sendbuf, sizeof(sendbuf));
|
||||
AddLog(szMsg);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case TOKEN_PROXY_BIND_RESULT:
|
||||
break;
|
||||
case TOKEN_PROXY_CLOSE: {
|
||||
wsprintf(szMsg, _T("%d TOKEN_PROXY_CLOSE\r\n"), index);
|
||||
|
||||
m_iocpLocal->Disconnect(index);
|
||||
AddLog(szMsg);
|
||||
}
|
||||
break;
|
||||
case TOKEN_PROXY_DATA: {
|
||||
ClientContext* pContext_proxy = NULL;
|
||||
BOOL ok = FALSE;
|
||||
if (m_iocpLocal->m_TcpServer->GetConnectionExtra((CONNID)index, (PVOID*)&pContext_proxy) && pContext_proxy != nullptr) {
|
||||
ok = m_iocpLocal->Send(pContext_proxy, &buf[5], m_ContextObject->m_DeCompressionBuffer.GetBufferLength() - 5);
|
||||
if (ok == FALSE) {
|
||||
wsprintf(szMsg, _T("%d TOKEN_PROXY_CLOSE\r\n"), index);
|
||||
m_iocpLocal->Disconnect(index);
|
||||
AddLog(szMsg);
|
||||
return;
|
||||
}
|
||||
wsprintf(szMsg, _T("%d ==><3E><> %d bytes\r\n"), index, m_ContextObject->m_DeCompressionBuffer.GetBufferLength() - 5);
|
||||
AddLog(szMsg);
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
// <20><><EFBFBD>䷢<EFBFBD><E4B7A2><EFBFBD>쳣<EFBFBD><ECB3A3><EFBFBD><EFBFBD>
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void CProxyMapDlg::AddLog(TCHAR* lpText)
|
||||
{
|
||||
if (m_bIsClose == TRUE) return;
|
||||
m_Edit.SetSel(-1, -1);
|
||||
m_Edit.ReplaceSel(lpText);
|
||||
}
|
||||
|
||||
void CProxyMapDlg::AddLog_other(TCHAR* lpText)
|
||||
{
|
||||
if (m_bIsClose == TRUE) return;
|
||||
m_EditOther.SetSel(-1, -1);
|
||||
m_EditOther.ReplaceSel(lpText);
|
||||
}
|
||||
|
||||
void CProxyMapDlg::OnSize(UINT nType, int cx, int cy)
|
||||
{
|
||||
CDialog::OnSize(nType, cx, cy);
|
||||
|
||||
// TODO: Add your message handler code here
|
||||
if (!IsWindowVisible())
|
||||
return;
|
||||
|
||||
RECT rectClient;
|
||||
RECT rectEdit = {};
|
||||
GetClientRect(&rectClient);
|
||||
rectEdit.left = 0;
|
||||
rectEdit.top = 0;
|
||||
rectEdit.right = rectClient.right;
|
||||
rectEdit.bottom = rectClient.bottom;
|
||||
m_Edit.MoveWindow(&rectEdit);
|
||||
}
|
||||
|
||||
void CProxyMapDlg::PostNcDestroy()
|
||||
{
|
||||
if (!m_bIsClose)
|
||||
OnCancel();
|
||||
CDialog::PostNcDestroy();
|
||||
delete this;
|
||||
}
|
||||
|
||||
|
||||
void CProxyMapDlg::OnSysCommand(UINT nID, LPARAM lParam)
|
||||
{
|
||||
CMenu* pSysMenu = GetSystemMenu(FALSE);
|
||||
switch (nID) {
|
||||
case IDM_PROXY_CHROME: {
|
||||
CString strCommand;
|
||||
strCommand.Format(_T(" /c start chrome.exe --show-app-list --proxy-server=\"SOCKS5://127.0.0.1:%d\""), m_nPort);
|
||||
ShellExecute(NULL, _T("open"), _T("cmd.exe"), strCommand, NULL, SW_SHOW);
|
||||
}
|
||||
break;
|
||||
}
|
||||
CDialog::OnSysCommand(nID, lParam);
|
||||
}
|
||||
Reference in New Issue
Block a user