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

📄 udpserver.cpp

📁 linux下使用C++编程
💻 CPP
字号:
#include "UdpServer.h"

/////////////////////////////////////////////////////////////////////////////
CUdpServer::CUdpServer()
{
	m_nPort = 0;
	m_nType = SOCK_DGRAM;
	
	memset(m_FileDir,0,sizeof(m_FileDir));
	//memset( m_pszBuffer, 0, sizeof(m_pszBuffer) );
	//m_nBufferEnd = 0;
	m_hSocket = INVALID_SOCKET;
	m_bReceiveRun = false;
	m_bProcessRun = false;
}
/////////////////////////////////////////////////////////////////////////////
CUdpServer::~CUdpServer()
{
	m_bWillExit = true;
	m_ThreadMutex.UnLock();
	m_ProcessEvent.SetEvent();
	while(m_bReceiveRun || m_bProcessRun)
		MilliSleep(200);
	if( m_hSocket != INVALID_SOCKET )
	{
		closesocket( m_hSocket );
		m_hSocket = INVALID_SOCKET;
	}
}
SOCKET CUdpServer::Socket(int nDomain, int nType, int nProtocol)
{
	m_hSocket = socket(nDomain, nType, nProtocol);
	m_nType = nType;
	int nLength = 640000;
	setsockopt(m_hSocket,SOL_SOCKET,SO_RCVBUF,(const 	char*)&nLength,sizeof(nLength));
	setsockopt(m_hSocket,SOL_SOCKET,SO_SNDBUF,(const char*)&nLength,sizeof(nLength));
	return m_hSocket;
}
/////////////////////////////////////////////////////////////////////////////
bool CUdpServer::Init( char* path,UINT nPort )
{
	m_nPort = nPort;

	strcat(m_FileDir,path);
	strcat(m_FileDir,"/data");
//	CreateDirectory(m_FileDir);

	sockaddr_in	sockAddr;
	sockAddr.sin_port = htons( m_nPort );
	sockAddr.sin_family = AF_INET;
	sockAddr.sin_addr.s_addr = htonl( INADDR_ANY );
	
	Socket( AF_INET, SOCK_DGRAM, 0 );
	if( m_hSocket == INVALID_SOCKET )
		return false;
	
	int cRet = bind( m_hSocket, (sockaddr *)(&sockAddr), sizeof(sockAddr) );
	if( cRet == SOCKET_ERROR )
	{
		if( errno != EINPROGRESS )
		{
			closesocket( m_hSocket );
			m_hSocket = INVALID_SOCKET;
			return false;
		}
	}
	int bOpt;

	if( m_nPort == 0 )
		return true;
	
    	bool bRet = CreateThreadEx(ReceiveThread, this);
    	if( bRet == false )
	{
		closesocket( m_hSocket );
		m_hSocket = INVALID_SOCKET;
        	return false;
    	}

	/*暂时仅用一个线程处理.
    	bRet = CreateThreadEx(ProcessThread, this);
    	if( bRet == false )
	{
		closesocket( m_hSocket );
		m_hSocket = INVALID_SOCKET;
        	return false;
    	}
        */
	return true;
}
/////////////////////////////////////////////////////////////////////////////
ThreadFuncRet CUdpServer::ReceiveThread(LPVOID pUdpWorker)
{
	CUdpServer * pThis = (CUdpServer *)pUdpWorker;

	sockaddr_in sockFrom;
	socklen_t nAddrLength = sizeof(sockaddr);
	fd_set rfds;
	pThis->m_bReceiveRun = true;	char buffer[RCV_BUFFER_SIZE];
	while( !pThis->m_bWillExit ) 
	{
		struct timeval tv = {0, 300000};
		FD_ZERO(&rfds);
		FD_SET(pThis->m_hSocket, &rfds);		
		if( select(pThis->m_hSocket+1, &rfds, NULL, NULL, &tv) > 0 )		{
			int iCount = recvfrom(pThis->m_hSocket,buffer,sizeof(buffer),0,(sockaddr *)&sockFrom,&nAddrLength);
			if( iCount >0 )
			{				
				//处理报文
				pThis->process(buffer);
			}
		}
		else if( pThis->m_bWillExit )
			break;
		else
			continue;
	}
	pThis->m_bReceiveRun = false;

	return 0;
}
bool	CUdpServer::process(char* buffer){
	int ai_number = 0;
	int di_number = 0;        int length =0;        int jz_no = 0;        int systime;
	char PacketType[5];
	bool isValid = false;
	memcpy(PacketType,buffer,4);        PacketType[4]=0;	//printf("PacketType is %s\n",PacketType);	//fflush(stdout);
	
	if(strcmp(PacketType,"REAL")==0){
		isValid = true;
	}
	if(isValid)	{
		memcpy(&jz_no,buffer+8,4);                memcpy(&ai_number,buffer+20,4);
		memcpy(&di_number,buffer+24,4);                memcpy(&systime,buffer+16,4);
		//写实时文件
		length = 30+ai_number*4+di_number*1;
		FILE *fp;
		char real_file[MAX_PATH],his_file[MAX_PATH];
		sprintf(real_file,"%s/realtime%d.txt",m_FileDir,jz_no);
		sprintf(his_file,"%s/unit%d/%d.txt",m_FileDir,jz_no,systime);//nowInSecond()
		if((fp=fopen(real_file,"wb"))!=NULL)		{
			fwrite(buffer,length,1,fp);
			fclose(fp);
			//写历史文件
			DeleteFile(his_file);
			CopyFile(real_file,his_file);
		}
		printf("recieve ok\n");		fflush(stdout);
	}	else	{		FILE *fplog;		char log_file[MAX_PATH];		sprintf(log_file,"%s/log.txt",m_FileDir);                SYSTEMTIME SysTime;		GetLocalTime( SysTime);		if((fplog=fopen(log_file,"a+"))!=NULL)		{
			fprintf(fplog,"%d-%d-%d %d:%d:%d  recieve data format error!\n",SysTime.wYear,SysTime.wMonth,SysTime.wDay,SysTime.wHour,SysTime.wMinute,SysTime.wSecond);
			fclose(fplog);
			//写历史文件
		}
		printf("UDPrecv:recv error data.\n");
		fflush(stdout);		
	}	
	return true;
}
/////////////////////////////////////////////////////////////////////////////
ThreadFuncRet CUdpServer::ProcessThread(LPVOID pUdpWorker)
{
	CUdpServer * pThis = (CUdpServer *)pUdpWorker;
	pThis->m_bProcessRun = true;
	while( !pThis->m_bWillExit ) 
	{
		//以下代码作测试用
		MilliSleep(2000);
		char buff[1024];
		int ai_num = 2;
		int di_num = 2;
		float ai_value = 1.23;
		short di_value = 1;
		int checksum = 4;
		memcpy(buff,&ai_num,4);
		memcpy(buff+4,&di_num,4);
		memcpy(buff+8,&ai_value,4);
		memcpy(buff+12,&ai_value,4);
		memcpy(buff+16,&di_value,2);
		memcpy(buff+18,&di_value,2);
		memcpy(buff+20,&checksum,4);
		pThis->Test(buff,24);
	}
	pThis->m_bProcessRun = false;
	return 0;
}

bool CUdpServer::Test(char * pBuffer,int buf_size)
{
	sockaddr_in sockAddr;
	sockAddr.sin_port = htons( m_nPort );
	sockAddr.sin_family = AF_INET;
	int nAddrSize = sizeof(sockaddr);
	sockAddr.sin_addr.s_addr = inet_addr( "127.0.0.1" );
	sendto(m_hSocket, pBuffer,buf_size , 0, (sockaddr *)&sockAddr, nAddrSize);
	return true;
}

⌨️ 快捷键说明

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