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

📄 asyncsocketexlayer.cpp

📁 一个支持FTP,SFTP的客户端程序
💻 CPP
📖 第 1 页 / 共 2 页
字号:
		if (bResult)
		{
			if (m_nFamily == AF_INET6)
			{
				rPeerPort = ntohs(((SOCKADDR_IN6*)sockAddr)->sin6_port);
				LPTSTR buf = Inet6AddrToString(((SOCKADDR_IN6*)sockAddr)->sin6_addr);
				rPeerAddress = buf;
				delete [] buf;
			} 
			else if (m_nFamily == AF_INET)
			{
				rPeerPort = ntohs(((SOCKADDR_IN*)sockAddr)->sin_port);
				rPeerAddress = inet_ntoa(((SOCKADDR_IN*)sockAddr)->sin_addr);
			}
			else
			{
				delete sockAddr;
				return FALSE;
			}
		}
		delete sockAddr;

		return bResult;
	}
}

#endif //_AFX

BOOL CAsyncSocketExLayer::GetPeerName( SOCKADDR* lpSockAddr, int* lpSockAddrLen )
{
	return GetPeerNameNext(lpSockAddr, lpSockAddrLen);
}

BOOL CAsyncSocketExLayer::GetPeerNameNext( SOCKADDR* lpSockAddr, int* lpSockAddrLen )
{
	if (m_pNextLayer)
		return m_pNextLayer->GetPeerName(lpSockAddr, lpSockAddrLen);
	else
	{
		ASSERT(m_pOwnerSocket);
		if ( !getpeername(m_pOwnerSocket->GetSocketHandle(), lpSockAddr, lpSockAddrLen) )
			return TRUE;
		else
			return FALSE;
	}
}

//Gets the address of the sock socket to which the socket is connected
#ifdef _AFX

BOOL CAsyncSocketExLayer::GetSockName( CString& rSockAddress, UINT& rSockPort )
{
	return GetSockNameNext(rSockAddress, rSockPort);
}

BOOL CAsyncSocketExLayer::GetSockNameNext( CString& rSockAddress, UINT& rSockPort )
{
	if (m_pNextLayer)
		return m_pNextLayer->GetSockName(rSockAddress, rSockPort);
	else
	{
		SOCKADDR* sockAddr;
		int nSockAddrLen;

		if (m_nFamily == AF_INET6)
		{
			sockAddr = (SOCKADDR*)new SOCKADDR_IN6;
			nSockAddrLen = sizeof(SOCKADDR_IN6);
		}
		else if (m_nFamily == AF_INET)
		{
			sockAddr = (SOCKADDR*)new SOCKADDR_IN;
			nSockAddrLen = sizeof(SOCKADDR_IN);
		}

		memset(sockAddr, 0, nSockAddrLen);

		BOOL bResult = GetSockName(sockAddr, &nSockAddrLen);

		if (bResult)
		{
			if (m_nFamily == AF_INET6)
			{
				rSockPort = ntohs(((SOCKADDR_IN6*)sockAddr)->sin6_port);
				LPTSTR buf = Inet6AddrToString(((SOCKADDR_IN6*)sockAddr)->sin6_addr);
				rSockAddress = buf;
				delete [] buf;
			} 
			else if (m_nFamily == AF_INET)
			{
				rSockPort = ntohs(((SOCKADDR_IN*)sockAddr)->sin_port);
				rSockAddress = inet_ntoa(((SOCKADDR_IN*)sockAddr)->sin_addr);
			}
			else
			{
				delete sockAddr;
				return FALSE;
			}
		}
		delete sockAddr;

		return bResult;
	}
}

#endif //_AFX

BOOL CAsyncSocketExLayer::GetSockName( SOCKADDR* lpSockAddr, int* lpSockAddrLen )
{
	return GetSockNameNext(lpSockAddr, lpSockAddrLen);
}

BOOL CAsyncSocketExLayer::GetSockNameNext( SOCKADDR* lpSockAddr, int* lpSockAddrLen )
{
	if (m_pNextLayer)
		return m_pNextLayer->GetSockName(lpSockAddr, lpSockAddrLen);
	else
	{
		ASSERT(m_pOwnerSocket);
		if ( !getsockname(m_pOwnerSocket->GetSocketHandle(), lpSockAddr, lpSockAddrLen) )
			return TRUE;
		else
			return FALSE;
	}
}

void CAsyncSocketExLayer::Init(CAsyncSocketExLayer *pPrevLayer, CAsyncSocketEx *pOwnerSocket)
{
	ASSERT(pOwnerSocket);
	m_pPrevLayer=pPrevLayer;
	m_pOwnerSocket=pOwnerSocket;
	m_pNextLayer=0;
#ifndef NOSOCKETSTATES
	SetLayerState(pOwnerSocket->GetState());
#endif //NOSOCKETSTATES
}

int CAsyncSocketExLayer::GetLayerState()
{
	return m_nLayerState;
}

void CAsyncSocketExLayer::SetLayerState(int nLayerState)
{
	ASSERT(m_pOwnerSocket);
	int nOldLayerState=GetLayerState();
	m_nLayerState=nLayerState;
	if (nOldLayerState!=nLayerState)
		DoLayerCallback(LAYERCALLBACK_STATECHANGE, GetLayerState(), nOldLayerState);
}

void CAsyncSocketExLayer::CallEvent(int nEvent, int nErrorCode)
{
	if (m_nCriticalError)
		return;
	m_nCriticalError = nErrorCode;
	switch (nEvent)
	{
	case FD_READ:
	case FD_FORCEREAD:
		if (GetLayerState()==connecting && !nErrorCode)
		{
			m_nPendingEvents |= nEvent;
			break;
		}
		else if (GetLayerState()==attached)
			SetLayerState(connected);
		if (nEvent & FD_READ)
			m_nPendingEvents &= ~FD_READ;
		else
			m_nPendingEvents &= ~FD_FORCEREAD;
		if (GetLayerState()==connected || nErrorCode)
		{
			if (nErrorCode)
				SetLayerState(aborted);
			OnReceive(nErrorCode);
		}
		break;
	case FD_WRITE:
		if (GetLayerState()==connecting && !nErrorCode)
		{
			m_nPendingEvents |= nEvent;
			break;
		}
		else if (GetLayerState()==attached)
			SetLayerState(connected);
		m_nPendingEvents &= ~FD_WRITE;
		if (GetLayerState()==connected || nErrorCode)
		{
			if (nErrorCode)
				SetLayerState(aborted);
			OnSend(nErrorCode);
		}
		break;
	case FD_CONNECT:
		if (GetLayerState()==connecting || GetLayerState() == attached)
		{
			if (!nErrorCode)
				SetLayerState(connected);
			else
			{
				if (!m_pNextLayer && m_nextAddr)
					if (TryNextProtocol())
					{
						m_nCriticalError = 0;
						return;
					}
				SetLayerState(aborted);
			}
			m_nPendingEvents &= ~FD_CONNECT;
			OnConnect(nErrorCode);

			if (!nErrorCode)
			{
				if ((m_nPendingEvents & FD_READ) && GetLayerState()==connected)
					OnReceive(0);
				if ((m_nPendingEvents & FD_FORCEREAD) && GetLayerState()==connected)
					OnReceive(0);
				if ((m_nPendingEvents & FD_WRITE) && GetLayerState()==connected)
					OnSend(0);
			}
			m_nPendingEvents = 0;
		}
		break;
	case FD_ACCEPT:
		if (GetLayerState()==listening)
		{
			if (nErrorCode)
				SetLayerState(aborted);
			m_nPendingEvents &= ~FD_ACCEPT;
			OnAccept(nErrorCode);
		}
		break;
	case FD_CLOSE:
		if (GetLayerState()==connected || GetLayerState()==attached)
		{
			if (nErrorCode)
				SetLayerState(aborted);
			else
				SetLayerState(closed);
			m_nPendingEvents &= ~FD_CLOSE;
			OnClose(nErrorCode);
		}
		break;
	}
}

//Creates a socket
BOOL CAsyncSocketExLayer::Create(UINT nSocketPort, int nSocketType,
			long lEvent, LPCTSTR lpszSocketAddress, int nFamily /*=AF_INET*/)
{
	return CreateNext(nSocketPort, nSocketType, lEvent, lpszSocketAddress, nFamily);
}

BOOL CAsyncSocketExLayer::CreateNext(UINT nSocketPort, int nSocketType, long lEvent, LPCTSTR lpszSocketAddress, int nFamily /*=AF_INET*/)
{
	ASSERT(GetLayerState()==notsock);
	BOOL res = FALSE;

	m_nFamily = nFamily;
	
	if (m_pNextLayer)
		res = m_pNextLayer->Create(nSocketPort, nSocketType, lEvent, lpszSocketAddress, nFamily);
	else if (m_nFamily == AF_UNSPEC)
	{
		m_lEvent = lEvent;
		delete [] m_lpszSocketAddress;
		if (lpszSocketAddress)
		{
			m_lpszSocketAddress = new TCHAR[_tcslen(lpszSocketAddress) + 1];
			_tcscpy(m_lpszSocketAddress, lpszSocketAddress);
		}
		else
			m_lpszSocketAddress = 0;
		m_nSocketPort = nSocketPort;
		res = TRUE;
	}
	else
	{
		SOCKET hSocket=socket(nFamily, nSocketType, 0);
		if (hSocket == INVALID_SOCKET)
		{
			m_pOwnerSocket->Close();
			return FALSE;
		}
		m_pOwnerSocket->m_SocketData.hSocket=hSocket;
		m_pOwnerSocket->AttachHandle(hSocket);
		if (!m_pOwnerSocket->AsyncSelect(lEvent))
		{
			m_pOwnerSocket->Close();
			return FALSE;
		}
		if (m_pOwnerSocket->m_pFirstLayer)
		{
			if (WSAAsyncSelect(m_pOwnerSocket->m_SocketData.hSocket, m_pOwnerSocket->GetHelperWindowHandle(), m_pOwnerSocket->m_SocketData.nSocketIndex+WM_SOCKETEX_NOTIFY, FD_READ | FD_WRITE | FD_OOB | FD_ACCEPT | FD_CONNECT | FD_CLOSE) )
			{
				m_pOwnerSocket->Close();
				return FALSE;
			}
		}
		if (!m_pOwnerSocket->Bind(nSocketPort, lpszSocketAddress))
		{
			m_pOwnerSocket->Close();
			return FALSE;
		}
		res = TRUE;
	}
	if (res)
		SetLayerState(unconnected);
	return res;
}

int CAsyncSocketExLayer::DoLayerCallback(int nType, int nParam1, int nParam2, char* str /*=0*/)
{
	if (!m_pOwnerSocket)
		return 0;

	int nError = WSAGetLastError();

	t_callbackMsg msg;
	msg.pLayer = this;
	msg.nType = nType;
	msg.nParam1 = nParam1;
	msg.nParam2 = nParam2;
	msg.str = str;

	m_pOwnerSocket->AddCallbackNotification(msg);

	WSASetLastError(nError);

	return 0;
}

BOOL CAsyncSocketExLayer::Listen( int nConnectionBacklog)
{
	return ListenNext( nConnectionBacklog);
}

BOOL CAsyncSocketExLayer::ListenNext( int nConnectionBacklog)
{
	ASSERT(GetLayerState()==unconnected);
	BOOL res;
	if (m_pNextLayer)
		res=m_pNextLayer->Listen(nConnectionBacklog);
	else
		res=listen(m_pOwnerSocket->GetSocketHandle(), nConnectionBacklog);
	if (res!=SOCKET_ERROR)
	{
		SetLayerState(listening);
	}
	return res!=SOCKET_ERROR;
}

BOOL CAsyncSocketExLayer::Accept( CAsyncSocketEx& rConnectedSocket, SOCKADDR* lpSockAddr /*=NULL*/, int* lpSockAddrLen /*=NULL*/ )
{
	return AcceptNext(rConnectedSocket, lpSockAddr, lpSockAddrLen);
}

BOOL CAsyncSocketExLayer::AcceptNext( CAsyncSocketEx& rConnectedSocket, SOCKADDR* lpSockAddr /*=NULL*/, int* lpSockAddrLen /*=NULL*/ )
{
	ASSERT(GetLayerState()==listening);
	BOOL res;
	if (m_pNextLayer)
		res=m_pNextLayer->Accept(rConnectedSocket, lpSockAddr, lpSockAddrLen);
	else
	{
		SOCKET hTemp = accept(m_pOwnerSocket->m_SocketData.hSocket, lpSockAddr, lpSockAddrLen);

		if (hTemp == INVALID_SOCKET)
			return FALSE;
		VERIFY(rConnectedSocket.InitAsyncSocketExInstance());
		rConnectedSocket.m_SocketData.hSocket=hTemp;
		rConnectedSocket.AttachHandle(hTemp);
		rConnectedSocket.SetFamily(GetFamily());
#ifndef NOSOCKETSTATES
		rConnectedSocket.SetState(connected);
#endif //NOSOCKETSTATES
	}
	return TRUE;
}

BOOL CAsyncSocketExLayer::ShutDown(int nHow /*=sends*/)
{
	return ShutDownNext(nHow);
}

BOOL CAsyncSocketExLayer::ShutDownNext(int nHow /*=sends*/)
{
	if (m_nCriticalError)
	{
		WSASetLastError(m_nCriticalError);
		return FALSE;
	}
	else if (GetLayerState()==notsock)
	{
		WSASetLastError(WSAENOTSOCK);
		return FALSE;
	}
	else if (GetLayerState()==unconnected || GetLayerState()==connecting || GetLayerState()==listening)
	{
		WSASetLastError(WSAENOTCONN);
		return FALSE;
	}

	if (!m_pNextLayer)
	{
		ASSERT(m_pOwnerSocket);
		return shutdown(m_pOwnerSocket->GetSocketHandle(), nHow);
	}
	else
		return m_pNextLayer->ShutDownNext(nHow);
}

int CAsyncSocketExLayer::GetFamily() const
{
	return m_nFamily;
}

bool CAsyncSocketExLayer::SetFamily(int nFamily)
{
	if (m_nFamily != AF_UNSPEC)
		return false;
	
	m_nFamily = nFamily;
	return true;
}

bool CAsyncSocketExLayer::TryNextProtocol()
{
	m_pOwnerSocket->DetachHandle(m_pOwnerSocket->m_SocketData.hSocket);
	closesocket(m_pOwnerSocket->m_SocketData.hSocket);
	m_pOwnerSocket->m_SocketData.hSocket = INVALID_SOCKET;

	BOOL ret = FALSE;
	for (; m_nextAddr; m_nextAddr = m_nextAddr->ai_next)
	{
		m_pOwnerSocket->m_SocketData.hSocket = socket(m_nextAddr->ai_family, m_nextAddr->ai_socktype, m_nextAddr->ai_protocol);

		if (m_pOwnerSocket->m_SocketData.hSocket == INVALID_SOCKET)
			continue;

		m_pOwnerSocket->AttachHandle(m_pOwnerSocket->m_SocketData.hSocket);
		if (!m_pOwnerSocket->AsyncSelect(m_lEvent))
		{
			m_pOwnerSocket->DetachHandle(m_pOwnerSocket->m_SocketData.hSocket);
			closesocket(m_pOwnerSocket->m_SocketData.hSocket);
			m_pOwnerSocket->m_SocketData.hSocket = INVALID_SOCKET;
			continue;
		}

#ifndef NOLAYERS
		if (m_pOwnerSocket->m_pFirstLayer)
		{
			if (WSAAsyncSelect(m_pOwnerSocket->m_SocketData.hSocket, m_pOwnerSocket->GetHelperWindowHandle(), m_pOwnerSocket->m_SocketData.nSocketIndex+WM_SOCKETEX_NOTIFY, FD_READ | FD_WRITE | FD_OOB | FD_ACCEPT | FD_CONNECT | FD_CLOSE))
			{
				m_pOwnerSocket->DetachHandle(m_pOwnerSocket->m_SocketData.hSocket);
				closesocket(m_pOwnerSocket->m_SocketData.hSocket);
				m_pOwnerSocket->m_SocketData.hSocket = INVALID_SOCKET;
				continue;
			}
		}
#endif //NOLAYERS

		m_pOwnerSocket->m_SocketData.nFamily = m_nextAddr->ai_family;
		m_nFamily = m_nextAddr->ai_family;
		if (!m_pOwnerSocket->Bind(m_nSocketPort, m_lpszSocketAddress))
		{ 
			m_pOwnerSocket->DetachHandle(m_pOwnerSocket->m_SocketData.hSocket);
			closesocket(m_pOwnerSocket->m_SocketData.hSocket);
			m_pOwnerSocket->m_SocketData.hSocket = INVALID_SOCKET;
			continue; 
		}

		if (connect(m_pOwnerSocket->GetSocketHandle(), m_nextAddr->ai_addr, m_nextAddr->ai_addrlen) == SOCKET_ERROR && WSAGetLastError() != WSAEWOULDBLOCK)
		{
			m_pOwnerSocket->DetachHandle(m_pOwnerSocket->m_SocketData.hSocket);
			closesocket(m_pOwnerSocket->m_SocketData.hSocket);
			m_pOwnerSocket->m_SocketData.hSocket = INVALID_SOCKET;
			continue;
		}

		SetLayerState(connecting);

		ret = true;
		break;
	}

	if (m_nextAddr)
		m_nextAddr = m_nextAddr->ai_next;

	if (!m_nextAddr)
	{
		m_pOwnerSocket->p_freeaddrinfo(m_addrInfo);
		m_nextAddr = 0;
		m_addrInfo = 0;
	}

	if (m_pOwnerSocket->m_SocketData.hSocket == INVALID_SOCKET || !ret)
		return FALSE;
	else
		return TRUE;
}

⌨️ 快捷键说明

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