2015-01-17 20:00:57|?次阅读|上传:wustguangh【已有?条评论】发表评论
关键词:C/C++, 网络通信|来源:唯设编程网
CFTP::CFTP(const char* ip, const char* logFile): m_pLogFile(NULL) { //清空 memset(m_ip,0,sizeof(m_ip)); //保存IP地址 strcpy_s(m_ip,ip); WORD wVersionRequested; WSADATA wsaData; int err; wVersionRequested = MAKEWORD( 2, 2 ); /*wVersionRequested参数用于指定准备加载的Winsock库的版本。高位字节指定所需要的 Winsock库的副版本,而低位字节则是主版本。然后,可用宏MAKEWORD( X , Y )(其中,x是 高位字节, y是低位字节)方便地获得wVersionRequested的正确值。*/ if(err = WSAStartup( wVersionRequested, &wsaData )) { std::cout << "Can not initilize winsock.dll" << std::endl; std::cout << "Error Code:" << WSAGetLastError() << std::endl; return; }else{ std::cout << "winsock.dll loded" << std::endl; } /* Confirm that the WinSock DLL supports 2.2.*/ /* Note that if the DLL supports versions greater */ /* than 2.2 in addition to 2.2, it will still return */ /* 2.2 in wVersion since that is the version we */ /* requested. */ if ( LOBYTE( wsaData.wVersion ) != 2 || HIBYTE( wsaData.wVersion ) != 2 ) { /* Tell the user that we could not find a usable */ /* WinSock DLL. */ WSACleanup( ); return; } //打开日志文件 m_pLogFile = fopen(logFile,"ab+"); }
构造函数中我们使用WSAStartup完成对Winsock服务的初始化。Socket的程序在使用Socket之前必须调用WSAStartup函数。该函数的第一个参数指明程序请求使用的Socket版本,其中高位字节指明副版本、低位字节指明主版本;操作系统利用第二个参数返回请求的Socket的版本信息。当一个应用程序调用WSAStartup函数时,操作系统根据请求的Socket版本来搜索相应的Socket库,然后绑定找到的Socket库到该应用程序中。以后应用程序就可以调用所请求的Socket库中的其它Socket函数了。
CFTP::~CFTP(void) { WSACleanup(); //关闭日志文件 if(m_pLogFile != NULL){ fclose(m_pLogFile); m_pLogFile = NULL; } }
应用程序或DLL在使用Windows Sockets服务之前必须要进行一次成功的WSAStartup()调用.当它完成了Windows Sockets的使用后,应用程序或DLL必须调用WSACleanup()将其从Windows Sockets的实现中注销,并且该实现释放为应用程序或DLL分配的任何资源.任何打开的并已建立连接的SOCK_STREAM类型套接口在调用WSACleanup()时会重置; 而已经由closesocket()关闭却仍有要发送的悬而未决数据的套接口则不会受影响- 该数据仍要发送。
对应于一个任务进行的每一次WSAStartup()调用,必须有一个WSACleanup()调用.只有最后的WSACleanup()做实际的清除工作;前面的调用仅仅将Windows Sockets DLL中的内置引用计数递减.一个简单的应用程序为确保WSACleanup()调用了足够的次数,可以在一个循环中不断调用WSACleanup()直至返回WSANOTINITIALISED。