📄 liteproxyserverview.cpp
字号:
CString str;
str.Format("%s %s:%d", sAppProtocolTypes[pRequest->nAppProtocol], pRequest->strHost, pRequest->nPort);
pRequest->nLogID = gpView->Log(pRequest, str);
}
sockaddr_in host;
host.sin_family = AF_INET;
host.sin_port = htons(pRequest->nPort);
if(inet_addr(pRequest->strHost) == INADDR_NONE ) // connect to the appropriate server
{
hostent* hp = gethostbyname(pRequest->strHost); // server address is a DNS name
if(hp == NULL)
{
gpView->UpdateLog(pRequest->nLogID, 7, "Failed to resolve "+pRequest->strHost);
return false;
}
host.sin_addr.s_addr = *((unsigned long *) hp->h_addr);
}
else
host.sin_addr.s_addr = inet_addr(pRequest->strHost); // directly use the IP address
gpView->UpdateLog(pRequest->nLogID, 7, "Connecting "+pRequest->strHost);
if(connect(s, (sockaddr*)&host, sizeof(host)) == SOCKET_ERROR)
{
gpView->UpdateLog(pRequest->nLogID, 7, "Failed to Connect " + pRequest->strHost);
return false;
}
return true;
}
void HostPort(CString &strHost, INTERNET_PORT &nPort)
{
int nIndex;
if((nIndex = strHost.Find(':')) != -1)
{
nPort = atoi(strHost.Mid(nIndex+1));
strHost = strHost.Left(nIndex);
}
}
UINT StartRequest(void* lpv)
{
Request *pRequest = (Request *)lpv;
pRequest->nTime = ::GetTickCount();
SOCKET SocketClient = pRequest->socket;
try
{
SOCKET SocketHost = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
pRequest->strIP = inet_ntoa(pRequest->address.sin_addr);
bool bFtpPortCmd = pRequest->pListener->nAppProtocol == Listener::ApplicationProtocol::TYPE_FTP_PORT;
int nIndex;
CString str;
if(pRequest->pListener->strNextServerIP.IsEmpty() == false)
{
pRequest->strHost = pRequest->pListener->strNextServerIP;
pRequest->nPort = pRequest->pListener->nNextServerPort;
if(ConnectHost(SocketHost, pRequest) == false)
goto END_REQUEST;
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_HTTP)
{
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_FTP)
{
send(SocketClient, "220 FTP Virtual Server\r\n", 24, 0);
pRequest->nPort = 21;
CString strPass;
while(true)
{
pRequest->nLength = recv(SocketClient, str.GetBuffer(1024), 1024, 0);
str.ReleaseBuffer(pRequest->nLength);
if(memicmp(str, "USER", 4) == 0)
{
if((nIndex = str.Find("@")) != -1)
{
pRequest->strHost = str.Mid(nIndex+1);
pRequest->strHost.TrimRight();
HostPort(pRequest->strHost, pRequest->nPort);
pRequest->strRequest = str.Left(nIndex)+"\r\n";
break;
}
else
{
pRequest->strRequest = str;
str.TrimRight();
if(str.GetLength() == 4)
pRequest->strRequest.Insert(5, "anonymous");
// if host still not found then ask for login password
send(SocketClient, "331 send password.\r\n", 20, 0);
}
}
else if(memicmp(str, "SITE", 4) == 0 || memicmp(str, "OPEN", 4) == 0)
{
if((nIndex = str.Find(" ")) == -1)
goto END_REQUEST;
pRequest->strHost = str.Mid(nIndex+1);
pRequest->strHost.TrimRight();
HostPort(pRequest->strHost, pRequest->nPort);
break;
}
else if(memicmp(str, "PASS", 4) == 0)
{
strPass = str;
send(SocketClient, "230 Login OK. Proceed.\r\n", 24, 0);
}
else
break;
}
// connect to ftp server
if(ConnectHost(SocketHost, pRequest) == false)
goto END_REQUEST;
if(pRequest->strRequest.IsEmpty() == false)
{
// Receive ready command
RequestRecv(pRequest, SocketHost, str.GetBuffer(1024), 1024);
// send USER command
RequestSend(pRequest, SocketHost, pRequest->strRequest.GetBuffer(0), pRequest->strRequest.GetLength());
if(strPass.IsEmpty() == false)
{
// Receive reply of USER command
nIndex = RequestRecv(pRequest, SocketHost, str.GetBuffer(1024), 1024);
str.ReleaseBuffer(nIndex);
// send password
RequestSend(pRequest, SocketHost, strPass.GetBuffer(0), strPass.GetLength());
}
}
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_NNTP)
{
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_DNS)
{
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_SMTP_SERVER)
{
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_SOCKS4)
{
}
else if(pRequest->nAppProtocol == Listener::ApplicationProtocol::TYPE_SOCKS5)
{
}
gpView->UpdateLog(pRequest->nLogID, 7, "In progress...");
// gets ready to relay traffic on both directions
AfxBeginThread(TwoWayThread, new TwoWayStruct(SocketHost, SocketClient, !bFtpPortCmd, pRequest));
AfxBeginThread(TwoWayThread, new TwoWayStruct(SocketClient, SocketHost, bFtpPortCmd, pRequest));
return 0;
}
catch(...)
{
}
END_REQUEST:
shutdown(SocketClient, 2);
closesocket(SocketClient);
gpView->UpdateLog(pRequest->nLogID, 8, Commas(::GetTickCount()-pRequest->nTime));
delete pRequest;
return 1;
}
UINT StartListenThread(void* lpv)
{
CString str;
Listener* pListener = (Listener*)lpv;
int nType;
if(pListener->nTransProtocol == Listener::TransportProtocol::TYPE_TCP)
nType = SOCK_STREAM;
else if(pListener->nTransProtocol == Listener::TransportProtocol::TYPE_UDP)
nType = SOCK_DGRAM;
pListener->socketServer = socket(AF_INET, nType, 0);
if(pListener->socketServer == INVALID_SOCKET)
{
pListener->pThread = NULL;
if(pListener->IsTemp() == false)
AfxMessageBox("Fail to create listener socket");
return 1;
}
sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = INADDR_ANY;
addr.sin_port = htons((u_short)pListener->nPort); // listen this port
if(bind(pListener->socketServer, (sockaddr *)&addr, sizeof(addr)) != 0)
{
pListener->pThread = NULL;
str.Format("Socket bind failed: port %d", pListener->nPort);
if(pListener->IsTemp() == false)
AfxMessageBox(str);
return 1;
}
if(pListener->nTransProtocol == Listener::TransportProtocol::TYPE_TCP)
if(listen(pListener->socketServer, SOMAXCONN) != 0)
{
pListener->pThread = NULL;
str.Format("Fail to start listening: port %d", pListener->nPort);
if(pListener->IsTemp() == false)
AfxMessageBox(str);
return 1;
}
int nLength;
do
{
Request *pRequest = new Request;
pRequest->pListener = pListener;
pRequest->nAppProtocol = pListener->nAppProtocol;
pRequest->nTransProtocol = pListener->nTransProtocol;
nLength = sizeof(pRequest->address);
if(pListener->nTransProtocol == Listener::TransportProtocol::TYPE_TCP)
{
if((pRequest->socket = accept(pListener->socketServer, (sockaddr*)&pRequest->address, &nLength)) != INVALID_SOCKET && pListener->pThread)
AfxBeginThread(StartRequest, (LPVOID)pRequest);
}
else if(pListener->nTransProtocol == Listener::TransportProtocol::TYPE_UDP)
{
}
else
break;
}
while(pListener->pThread && pListener->IsTemp() == false);
pListener->pThread = NULL;
return 0;
}
void Listener::StartListen()
{
if(pThread)
return;
pThread = AfxBeginThread(StartListenThread, this);
}
void Listener::StopListen()
{
if(pThread == NULL)
return;
shutdown(socketServer, 2);
closesocket(socketServer);
if(pThread)
{
::TerminateThread(pThread, 0);
pThread = NULL;
}
}
int CLiteProxyServerView::Log(Request* pRequest, LPCSTR lpcsLog)
{
int nItemCount = m_pList->GetItemCount();
try
{
CString str;
str.Format("%s", Commas(nItemCount+1));
m_pList->InsertItem(nItemCount, str, pRequest->nAppProtocol ? pRequest->nAppProtocol : -1);
m_pList->SetItemText(nItemCount, 1, CTime::GetCurrentTime().Format("%c"));
m_pList->SetItemText(nItemCount, 2, pRequest->strIP);
m_pList->SetItemText(nItemCount, 3, lpcsLog);
if(m_bEnsureVisible)
m_pList->EnsureVisible(nItemCount, FALSE);
}
catch(...)
{
}
return nItemCount;
}
void CLiteProxyServerView::UpdateLog(int nLogID, int nCol, int nLength)
{
if(nLogID < 0 || nLogID >= m_pList->GetItemCount())
return;
m_pList->SetItemText(nLogID, nCol, Commas(nLength));
}
void CLiteProxyServerView::UpdateLog(int nLogID, int nCol, LPCSTR lpcs)
{
if(nLogID < 0 || nLogID >= m_pList->GetItemCount())
return;
m_pList->SetItemText(nLogID, nCol, lpcs);
}
void CLiteProxyServerView::OnFileNew()
{
theApp.m_nInProgress = 0;
m_pList->DeleteAllItems();
}
void CLiteProxyServerView::OnUpdate(CView* pSender, LPARAM lHint, CObject* pHint)
{
if(lHint == 0)
{
if(m_pListener != NULL)
delete m_pListener;
m_pListener = new Listener;
m_pListener->nAppProtocol = Listener::ApplicationProtocol::TYPE_FTP;
m_pListener->nTransProtocol = Listener::TransportProtocol::TYPE_TCP;
m_pListener->nPort = 21;
m_pListener->StartListen();
}
else if(lHint == 1)
{
delete m_pListener;
m_pListener = NULL;
}
}
void CLiteProxyServerView::GetNetworkParams()
{
try
{
m_strArrayDNS.RemoveAll();
ULONG pOutBufLen = 0;
::GetNetworkParams(NULL, &pOutBufLen);
FIXED_INFO* pInfo = new FIXED_INFO[pOutBufLen/sizeof(FIXED_INFO)+1];
if(ERROR_SUCCESS == ::GetNetworkParams(pInfo, &pOutBufLen))
{
IP_ADDR_STRING* pNext = &pInfo[0].DnsServerList;
do m_strArrayDNS.Add(pNext->IpAddress.String);
while(pNext = pNext->Next);
}
delete []pInfo;
m_strArrayIP.RemoveAll();
DWORD dwError;
ULONG pdwSize = 0;
GetIpAddrTable(NULL, &pdwSize, TRUE);
PMIB_IPADDRTABLE pIpAddrTable = new MIB_IPADDRTABLE[pdwSize/sizeof(MIB_IPADDRTABLE)+1];
if((dwError = GetIpAddrTable(pIpAddrTable, &pdwSize, TRUE)) == NO_ERROR)
for(int nIndex = 0; nIndex < (int)pIpAddrTable[0].dwNumEntries; nIndex++)
{
CString strIP = inet_ntoa((in_addr&)pIpAddrTable[0].table[nIndex].dwAddr);
if(strIP != "127.0.0.1" && strIP != "0.0.0.0")
m_strArrayIP.Add(strIP);
}
delete []pIpAddrTable;
}
catch(...)
{
AfxMessageBox("Failed in GetNetworkParams()");
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -