?? ftpservernew.cpp
字號:
// FtpServerNew.cpp : 定義控制臺應用程序的入口點。
//
#include "stdafx.h"
#include "DataStructAndConstant.h"
#include "TreadFunction.h"
CRITICAL_SECTION PerSocketVectorProtection;//作為操作vector的全局互斥量
CRITICAL_SECTION AddIocpProtection;//為了添加完成端口處理socket的全局變量
HANDLE CompetionPort;//作為全局的完成端口的句柄
extern bool DeleteVectorItem(LPPER_HANDLE_DATA pPerHandleData);
PerSocketDataVector cPerSocketDataVector;
int _tmain(int argc, char* argv[])
{
SOCKADDR_IN InternetAddr;
SOCKET Listen,Accept;
SYSTEM_INFO SystenInfo;
DWORD ThreadID;
WSADATA wsadata;
DWORD Ret;
if (Ret = WSAStartup(0x2020,&wsadata) != 0)
{
printf("WSAStartup failed with error %d\n",Ret);
return 0;
}
//打開一個空的完成端口
if ((CompetionPort = CreateIoCompletionPort(INVALID_HANDLE_VALUE,NULL,0,0)) == NULL)
{
printf("CreateIoCompletionPort failed with error %d\n",GetLastError());
return 0;
}
else
{
printf("CreateIoCompletionPort Success……\r\n");
}
GetSystemInfo(&SystenInfo);
// 開啟cpu個數的2倍個的線程
for (ULONG i=0; i < 6+SystenInfo.dwNumberOfProcessors*2; i++)
{
HANDLE ThreadHandle;
//創建服務器工作線程,并且向線程傳送完成端口
if ((ThreadHandle = CreateThread(NULL,0,ServerWorkerThread,CompetionPort,0,&ThreadID)) == NULL)
{
printf("CreateThread failed with error %d\n" ,GetLastError());
return 0;
}
CloseHandle(ThreadHandle);
}
printf("Start %d Threats……\r\n",6+SystenInfo.dwNumberOfProcessors*2);
//打開一個服務器socket
if ((Listen = WSASocket(AF_INET, SOCK_STREAM, 0, NULL, 0, WSA_FLAG_OVERLAPPED)) == INVALID_SOCKET)
{
printf("WSASocket() failed with error %d\n", WSAGetLastError());
return 0;
}
InternetAddr.sin_family = AF_INET;
InternetAddr.sin_addr.S_un.S_addr = htonl(INADDR_ANY);
InternetAddr.sin_port = htons(LISTENPORT);
if (bind(Listen,(LPSOCKADDR)&InternetAddr,sizeof(InternetAddr)) == SOCKET_ERROR)
{
printf("bind failed with error %d\n",WSAGetLastError());
return 0;
}
if (listen(Listen,5) == SOCKET_ERROR)
{
printf("listen failed with error %d\n",WSAGetLastError());
return 0;
}
printf("Ftp Server Start……… \r\n");
InitializeCriticalSection(&PerSocketVectorProtection);
InitializeCriticalSection(&AddIocpProtection);
//接收連接并且分發給完成端口
while (TRUE)
{
if ((Accept = WSAAccept(Listen,NULL,NULL,NULL,0)) == SOCKET_ERROR)
{
printf("WSAAccept failed with error %d\n",WSAGetLastError());
continue;
}
//創建與套接字相關的套接字信息結構
LPPER_SOCKET_DATA pAcceptSocketData=new PER_SOCKET_DATA;
EnterCriticalSection(&PerSocketVectorProtection);
cPerSocketDataVector.push_back(pAcceptSocketData);
LeaveCriticalSection(&PerSocketVectorProtection);
memset((void*)pAcceptSocketData,0,sizeof(PER_SOCKET_DATA));
pAcceptSocketData->cPerHandleData.Socket=Accept;
pAcceptSocketData->cPerHandleData.uHandleInfo.cCtrlInfo.EventDataValid=CreateEvent(NULL,TRUE,FALSE,NULL);
pAcceptSocketData->cPerHandleData.enCurrentHandleType=HandleControl;
pAcceptSocketData->cPerHandleData.uHandleInfo.cCtrlInfo.pDataLinkSocketDataBuffer=(void *)new PER_SOCKET_DATA;
strcpy(pAcceptSocketData->cPerHandleData.uHandleInfo .cCtrlInfo.strCurrentWorkPath,DEFAULTWORKPATH);
//與我們的創建的那個完成端口關聯起來,將關鍵項也與指定的一個完成端口關聯
EnterCriticalSection(&AddIocpProtection);
if ((CreateIoCompletionPort((HANDLE)Accept,CompetionPort,reinterpret_cast<DWORD>(&(pAcceptSocketData->cPerHandleData)),0)) == NULL)
{
printf("CreateIoCompletionPort failed with error%d\n",GetLastError());
LeaveCriticalSection(&AddIocpProtection);
closesocket(Accept);
continue;
}
LeaveCriticalSection(&AddIocpProtection);
int zero = 0;
if ( setsockopt(pAcceptSocketData->cPerHandleData.Socket, SOL_SOCKET, SO_SNDBUF, (char *)&zero, sizeof(zero) ) == SOCKET_ERROR )
{
printf("Set socket option Error %d",WSAGetLastError());
}
zero = 0;
if ( setsockopt(pAcceptSocketData->cPerHandleData.Socket, SOL_SOCKET, SO_RCVBUF, (char *)&zero, sizeof(zero) ) == SOCKET_ERROR )
{
printf("Set socket option Error %d",WSAGetLastError());
}
// 創建同下面的WSARecv調用相關的IO套接字信息結構體
pAcceptSocketData->cPerIoData.cBuffer.buf=pAcceptSocketData->cPerIoData.stBuffer;
strcpy(pAcceptSocketData->cPerIoData.cBuffer.buf,"220 Welcome to Access BlackBeast FTP Server...\r\n");
pAcceptSocketData->cPerIoData.cBuffer.len=(DWORD)strlen(pAcceptSocketData->cPerIoData.cBuffer.buf);
pAcceptSocketData->cPerIoData.IoType=ControlIoSend;
pAcceptSocketData->cPerIoData.uIoInfo.cControlIoSendInfo.enNextToDo=ToReceive;
DWORD SendBytes=0;
if (WSASend(pAcceptSocketData->cPerHandleData.Socket,&(pAcceptSocketData->cPerIoData.cBuffer),1,&SendBytes,0,&(pAcceptSocketData->cPerIoData.Overlapped),NULL) ==SOCKET_ERROR )
{
if (WSAGetLastError() != ERROR_IO_PENDING)
{
printf("WSASend() fialed with error %d\n",WSAGetLastError());
DeleteVectorItem(&(pAcceptSocketData->cPerHandleData));
closesocket(Accept);
continue;
}
}
}
return 0;
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -