⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 csock.cpp

📁 早期的WINDOWS编程,适合刚接触WINDOWS编程的初学者
💻 CPP
📖 第 1 页 / 共 2 页
字号:
#include "stdhdrs.h"
#include "common.h"

#include "WSockRes.h"
#include "csock.h"

unsigned long CWinSock::m_ulCWinSockInitialized = 0;
BOOL CWinSock::m_bRegisteredWinSockMsgs = FALSE;

//CWinSock Constructor
//Initializes Winsock
//Your application should check m_eCurrentSocketState
//If m_eCurrentSocketState == eSocketUninitialized then Winsock could not be initialized
//                         == eWSStarted then Winsock was started but does not 
//										 support the requested version
//						   == eWSInitialized then all is well
//
//If you compile with WS_USE_WINDOWS_MSGS then the constructor will also register
//the window messages, otherwise the constants in csock.h will be used
//
CWinSock::CWinSock(UINT uMajorVersion, UINT uMinorVersion)
{
	WORD	wVersionRequested;
	int		err;

	//Since we currently have no socket, mark the CurrentSocket as Invalid
	//and the current state as Uninitialized
	m_sockCurrentSocket = INVALID_SOCKET;
	m_eCurrentSocketState = eSocketUninitialized;

	//When asked to create a socket we will default to AF_INET for the family
	//and INADDR_ANY for the address
	m_SockAddrIn.sin_family = AF_INET;
	m_SockAddrIn.sin_addr.s_addr = INADDR_ANY;

	#ifdef WS_USE_REGISTERED_MSGS
	//If we wanted to used Registered Windows messages instead of constants
	//we would add the code here
	if (m_bRegisteredWinSockMsgs == FALSE){
		m_uWSA_READ    = RegisterWindowMessage("WSA_READ");
		m_uWSA_WRITE   = RegisterWindowMessage("WSA_WRITE");
		m_uWSA_ACCEPT  = RegisterWindowMessage("WSA_ACCEPT");
		m_uWSA_CONNECT = RegisterWindowMessage("WSA_CONNECT");
		m_uWSA_CLOSE   = RegisterWindowMessage("WSA_CLOSE");
		m_uWSA_OOB     = RegisterWindowMessage("WSA_OOB");
		m_bRegisteredWinSockMsgs = TRUE;
	}
	#endif

   	wVersionRequested = MAKEWORD(uMajorVersion,uMinorVersion);

    //See if we can initialize Winsock
	err = WSAStartup(wVersionRequested, &m_wsaData);

    //If we couldn't initialize Winsock simply return (since we can't return a
    //value from a constructor
	if (err != 0){
		PrintError();
		return;
	}

	//Although we don't know if we can use this version yet,
	//set m_eCurrentSocketState to eWSStarted so that our destructor will
	//call WSACleanup
	
	m_eCurrentSocketState = eWSStarted;

	//LoByte is the Major version number and the HiByte is the minor
	if (LOBYTE(m_wsaData.wVersion) != uMajorVersion ||
		HIBYTE(m_wsaData.wVersion) != uMinorVersion){
		return;
	}

	if (LOBYTE(wVersionRequested) < uMajorVersion || 
		(LOBYTE(wVersionRequested) == uMajorVersion &&
		HIBYTE(wVersionRequested) < uMinorVersion)){
		return;
	}

    //Set the version number info to the version number we are using
	m_wsaData.wVersion = MAKEWORD(uMajorVersion,uMinorVersion);
	m_wsaData.wHighVersion = MAKEWORD(uMajorVersion,uMinorVersion);

#ifdef _WS_VERBOSE_API
	WS_TRACE1(TEXT("WSAData Max sockets %u\n"),(LPCTSTR)m_wsaData.iMaxSockets);
	WS_TRACE1(TEXT("WSAData Datagram size %u\n"),(LPCTSTR)m_wsaData.iMaxUdpDg);
	WS_TRACE1(TEXT("WSAData Description %s\n"),m_wsaData.szDescription);
	WS_TRACE1(TEXT("WSAData Status %s\n"),m_wsaData.szSystemStatus);
	if (m_wsaData.lpVendorInfo == NULL)
		WS_TRACE0("WSAData lpVendorInfo is NULL\n");
	else
		WS_TRACE0("WSAData lpVendorInfo is not NULL\n");
#endif

    //The initialization was successful so set m_eCurrentSocketState to initialized
	m_eCurrentSocketState = eWSInitialized;

    //Increment a counter of the number of Winsock initializes (we must uninitialize
    //until this is zero)
	m_ulCWinSockInitialized++;
}

//CWinsock destructor
//Closes the socket if the socket is open
//Calls WSACleanup if Winsock was successfully started
//
CWinSock::~CWinSock()
{
	//Close the socket if it's open
	if (GetCurrentSocketState() == eSocketOpened)
		closesocket();

	//If Winsock was initialized we need to call WSACleanup
	if (m_eCurrentSocketState != eSocketUninitialized)
		WSACleanup();

	//Decrement our counter
	if (m_ulCWinSockInitialized > 0)
		m_ulCWinSockInitialized--;
}

//The debug statement which follows is not terminated until the #endif at the end of 
//this file
//
#ifdef _DEBUG

//Debug version of accept
//See CSock.h for variations on accept
SOCKET	CWinSock::accept(SOCKET s, struct sockaddr FAR *addr, int FAR *addrlen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::accept\n");
#endif

        //Call the native Winsock accept statement
		SOCKET	sockRet = ::accept(s, addr,addrlen);

        //Save the error returned from accept (if any)
		m_iLastError = ::GetLastError();
		if (sockRet == INVALID_SOCKET){
			WS_TRACE0("accept error:");
			PrintError(m_iLastError);
		}
		return sockRet;
}

//Debug version of bind
//See CSock.h for variations on bind
int CWinSock::bind(SOCKET s, const struct sockaddr FAR *name, int namelen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::bind\n");
#endif
        //Call the native Winsock bind statement
		int iBind = ::bind(s, name, namelen);

        //Save the returned error code if any
		m_iLastError = ::GetLastError();
		if (iBind == SOCKET_ERROR){
			WS_TRACE0("bind error:");
			PrintError(m_iLastError);
		}
		return iBind;
}

//Debug version of closesocket
//See Csock.h for variations on closesocket
int CWinSock::closesocket(SOCKET s)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::closesocket\n");
#endif

        //Call the native Winsock closesocket statement
		int iclose = ::closesocket(s);

        //Save the last error code if any
		m_iLastError = ::GetLastError();
		if (iclose == SOCKET_ERROR){
			WS_TRACE0("closesocket error:");
			PrintError(m_iLastError);
		} else {
            //Change the state of the socket to closed if the 
            //socket was successfully closed
			m_eCurrentSocketState = eSocketClosed;
		}
		return iclose;
}

//Debug version of connect
//See Csock.h for variations on connect
int CWinSock::connect(SOCKET s, const struct sockaddr FAR *name, int namelen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::connect\n");
#endif

        //Call the native Winsock connect statement
		int iconnect = ::connect(s,name,namelen);

        //Save the last error if any
		m_iLastError = ::GetLastError();
		if (iconnect == SOCKET_ERROR){
			WS_TRACE0("connect error:");
			PrintError(m_iLastError);
		} else {
            //Change the state of the socket to closed
            //if the connect
			m_eCurrentSocketState = eSocketClosed;
		}
		return iconnect;
}

//Debug version of getpeername
//See CSock.h for variations on getpeername
int CWinSock::getpeername(SOCKET s, struct sockaddr FAR* name, int FAR* namelen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::getpeername\n");
#endif
		int ipeername = ::getpeername(s,name,namelen);
		m_iLastError = ::GetLastError();
		if (ipeername == SOCKET_ERROR){
			WS_TRACE0("getpeername error:");
			PrintError(m_iLastError);
		}
		return ipeername;
}

//Debug version of getsockname
//See CSock.h for variations on getsockname
int CWinSock::getsockname(SOCKET s, struct sockaddr FAR*name, int FAR* namelen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::getpeername\n");
#endif
		int isockname = ::getsockname(s,name,namelen);
		m_iLastError = ::GetLastError();
		if (isockname == SOCKET_ERROR){
			WS_TRACE0("getsockname error:");
			PrintError(m_iLastError);
		}
		return isockname;
}

//Debug version of getsockopt
//See CSock.h for variations on getsockopt
int CWinSock::getsockopt(SOCKET s, int level, int optname, LPTSTR optval, 
                  		int FAR* optlen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::getsockopt\n");
#endif
		int isockopt = ::getsockopt(s,level,optname,optval,optlen);
		m_iLastError = ::GetLastError();
		if (isockopt == SOCKET_ERROR){
			WS_TRACE0("getsockopt error:");
			PrintError(m_iLastError);
		}
		return isockopt;
}

//Debug version of htonl (Host TO Network Long)
u_long CWinSock::htonl(u_long hostlong)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::htonl\n");
#endif
		return ::htonl(hostlong);
}

//Debug version of htons (Host TO Network Short)
u_short CWinSock::htons(u_short hostshort)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::htons\n");
#endif
		return ::htons(hostshort);
}

//Debug version of inet_addr
//CSock.h also provides an MFC definition which uses CString instead of LPCSTR
unsigned long CWinSock::inet_addr(LPCSTR cp)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::inet_addr\n");
#endif
		return ::inet_addr(cp);
}

//Debug version of inet_ntoa
LPTSTR CWinSock::inet_ntoa(struct in_addr in)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::inet_ntoa\n");
#endif
		return ::inet_ntoa(in);
}

//Debug version of ioctlsocket
//See CSock.h for variations on ioctlsocket
int CWinSock::ioctlsocket(SOCKET s, long cmd, u_long FAR* argp)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::ioctlsocket\n");
#endif
		int iioctl = ::ioctlsocket(s,cmd, argp);
		m_iLastError = ::GetLastError();
		if (iioctl == SOCKET_ERROR){
			WS_TRACE0("ioctlsocket error:");
			PrintError(m_iLastError);
		}
		return iioctl;
}

//Debug version of listen
//See CSock.h for variations on listen
int CWinSock::listen(SOCKET s, int backlong)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::listen\n");
#endif
		int ilisten = ::listen(s,backlong);
		m_iLastError = ::GetLastError();
		if (ilisten == SOCKET_ERROR){
			WS_TRACE0("listen error:");
			PrintError(m_iLastError);
		}
		return ilisten;
}

//Debug version of ntohl (Network TO Host Long)
u_long CWinSock::ntohl(u_long netlong)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::ntohl\n");
#endif
		return ::ntohl(netlong);
}

//Debug version of ntohs (Network TO Host Short)
u_short CWinSock::ntohs(u_short netshort)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::ntohs\n");
#endif
		return ::ntohs(netshort);
}

//Debug version of recv
//See CSock.h for variations of recv
int CWinSock::recv(SOCKET s, LPTSTR buf, int len, int flags)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::recv\n");
#endif
		int irecv = ::recv(s,buf,len,flags);
		m_iLastError = ::GetLastError();
		if (irecv == SOCKET_ERROR){
			WS_TRACE0("recv error:");
			PrintError(m_iLastError);
		}
		return irecv;
}

//Debug version of recvfrom
//See CSock.h for variations of recvfrom
int CWinSock::recvfrom(SOCKET s, LPTSTR buf, int len, int flags, 
      struct sockaddr FAR *from, int FAR *fromlen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::recvfrom\n");
#endif
		int irecvfrom = ::recvfrom(s,buf,len,flags,from,fromlen);
		m_iLastError = ::GetLastError();
		if (irecvfrom == SOCKET_ERROR){
			WS_TRACE0("recvfrom error:");
			PrintError(m_iLastError);
		}
		return irecvfrom;
}

//Debug version of select
long CWinSock::select(int nfds, fd_set FAR* readfds, 
                                fd_set FAR* writefds, 
                                fd_set FAR* exceptfds,
                                const struct timeval FAR* timeout)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::select\n");
#endif
		int iselect = ::select(nfds, readfds, writefds, exceptfds, timeout);
		m_iLastError = ::GetLastError();
		if (iselect == SOCKET_ERROR){
			WS_TRACE0("select error:");
			PrintError(m_iLastError);
		}
		return iselect;
}

//Debug version of send
//See CSock.h for variations of send
//See CSock.h for an MFC definition of send using a CString instead of an LPCSTR
int CWinSock::send(SOCKET s, LPCSTR buf, int len, int flags)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::send\n");
#endif
		int isend = ::send(s,buf,len,flags);
		m_iLastError = ::GetLastError();
		if (isend == SOCKET_ERROR){
			WS_TRACE0("send error:");
			PrintError(m_iLastError);
		}
		return isend;
}

//Debug version of sendto
//See CSock.h for variations of sendto
//See CSock.h for an MFC definition of sendto using a CString instead of an LPCSTR
int CWinSock::sendto(SOCKET s, LPCSTR buf, int len, int flags,
                     const struct sockaddr FAR *to, int tolen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::sendto\n");
#endif
		int isendto = ::sendto(s,buf,len,flags,to,tolen);
		m_iLastError = ::GetLastError();
		if (isendto == SOCKET_ERROR){
			WS_TRACE0("sendto error:");
			PrintError(m_iLastError);
		}
		return isendto;
}

//Debug version of setsockopt
//See CSock.h for variations of setsockopt
int CWinSock::setsockopt(SOCKET s,int level, int optname, LPCSTR optval, int optlen)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::setsockopt\n");
#endif
		int isockopt = ::setsockopt(s,level,optname,optval,optlen);
		m_iLastError = ::GetLastError();
		if (isockopt == SOCKET_ERROR){
			WS_TRACE0("setsockopt error:");
			PrintError(m_iLastError);
		}
		return isockopt;
}

//Debug version of shutdown
//See CSock.h for variations of shutdown
int CWinSock::shutdown(SOCKET s, int how)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::shutdown\n");
#endif
		int ishutdown = ::shutdown(s,how);
		m_iLastError = ::GetLastError();
		if (ishutdown == SOCKET_ERROR){
			WS_TRACE0("shutdown error:");
			PrintError(m_iLastError);
		} else {
			m_eCurrentSocketState = eSocketClosed;
		}
		return ishutdown;
}

//Debug version of socket
//See CSock.h for default values of af, type, and protocol
//Also notice that m_sockCurrentSocket is set (which is used by other functions
// when you do not provide a socket) and the socket state is changed
SOCKET CWinSock::socket(int af, int type, int protocol)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::socket\n");
#endif
		SOCKET sock = ::socket(af,type,protocol);
		m_iLastError = ::GetLastError();
		if (sock == INVALID_SOCKET){
			WS_TRACE0("socket error:");
			PrintError(m_iLastError);
		} else {
			m_sockCurrentSocket = sock;
			m_eCurrentSocketState = eSocketOpened;
		}
		return sock;
}

//Debug version of gethostbyaddr
//See CSock.h for an MFC definition using CString instead of LPCSTR
PHOSTENT CWinSock::gethostbyaddr(LPCSTR addr, int len, int type)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::gethostbyaddr\n");
#endif
		PHOSTENT phostent = ::gethostbyaddr(addr,len,type);
		m_iLastError = ::GetLastError();
		if (phostent == NULL){
			WS_TRACE0("gethostbyaddr error:");
			PrintError(m_iLastError);
		}
		return phostent;
}

//Debug version of gethostbyname
//See CSock.h for an MFC definition using CString instead of LPCSTR
PHOSTENT CWinSock::gethostbyname(LPCSTR name)
{
#ifdef _WS_VERBOSE_API
		WS_TRACE0("CWinSock::gethostbyname\n");
#endif
		PHOSTENT phostent = ::gethostbyname(name);
		m_iLastError = ::GetLastError();
		if (phostent == NULL){
			WS_TRACE0("gethostbyname error:");
			PrintError(m_iLastError);
		}
		return phostent;
}

//Debug version of gethostname
//See CSock.h for an MFC definition using CString instead of LPCSTR
int CWinSock::gethostname(LPTSTR name, int namelen)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -