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

📄 cisserver.cpp

📁 液晶电视完整代码可实现人机界面
💻 CPP
字号:
#include "CisPub.hpp"#include "BepsSend.h"/*******************************************************************************      CisServer.bin的功能说明**      多进程管理**      接收从柜台发来的业务*****************************************************************************/#ifndef BOOL#endif#ifndef TRUE        #define TRUE 1#endif//全局数据tagMyGlobe *myglobe = new tagMyGlobe;ComSocket_wzSer *comSocket;BepsPub sBepsPub;SybServer m_clsSybServer;//格式化字符串int     StrTrimChar( char *in_data ,char c){        int i,j = 0;        char tmp[1024];        memset(tmp,0,sizeof(tmp));        for(i = 0;i < strlen(in_data);i++)        {                if(in_data[i] != c)                        tmp[j++] = in_data[i];        }	strcpy( in_data , tmp);        return TRUE;}//主函数int main(int argc, char* argv[]){	//使主进程成为守护进程	pid_t main_pid =0;	main_pid = fork();	if(0!= main_pid)	{		exit(0);	}	//调用初始全局数据函数	int iRetval;	ComSocket_wzSer com;	comSocket = &com;		if(!InitGlobeData())	{		errlog( "[CisServer.bin] 初始全局失败,程序退出" );		exit (-1);	}        	//通讯插件开始工作	iRetval = comSocket->Open();	if(iRetval != 0)	{		errlog( "[CisServer.bin]通讯端口失败, 程序退出");		exit(-1);	}	while(1) //开始服务	{		//进程控制		MonitorWorkFlag();			//子进程管理函数 在这里完成对新建子程序		iRetval = ManageChildProcess();		if(iRetval != 0)		{			filelog(CIS_SRV_LOG, "Create new process failed");			errlog( "进程[CisServer.bin]创建失败, 程序退出");			continue;		}				MonitorWorkFlag();				sleep(1);		//复位接收到客户端的SOCKET,以便等待其他客户端的连接		comSocket->msocket_id = -1;	}	}/////////////////////////////////////////////////////////////////////////////////      处理信号子进程的函数int ManageChildProcess(){	//如果发现有客户端连接请求,则建立连接并创建新进程处理新连接SOCKET业务	if(0 == comSocket->Service())	{		pid_t chiPid;			//产生子进程操作		chiPid = fork();		if(chiPid < 0)		{		//如果FORK子进程失败那么设置工作标志为通知退出			myglobe->workFlag = FLAG_FORMEXIT;			errlog( "[RecvFromM b.bin] 创建子进程失败");			return (-1);		}        		if(chiPid == 0)		{		//子进程关闭监听套接口			comSocket->Close(comSocket->socket_id);		//让和新客户端建立连接的进程自举,脱离父进程,成为守护进程			ChildProcess();		}		if(chiPid>0)		{		//父进程关闭已经接受处理的套接字,由子进程去处理			comSocket->Close();		}	}	return 0;}/////////////////////////////////////////////////////////////////////////////////子进程的处理函数//设置SOCKET为非阻塞方式///int flag = fcntl(pMsSoket->connfd, F_GETFL, 0);///fcntl(pMsSoket->connfd, F_SETFL, O_NONBLOCK|flag);void ChildProcess(){    //开始子进程的具体处理    char  sResDesc[MAX_MBFE_BUFFER];    char  *RecvBuf = 0;    int   RecvBufLen = 0, SendBufLen = 0;    int   ret;    char  TrNo[100],TransNo[100];    int   RetCode = 0, iRetval = 0;    char  *RetMsg = 0,*Result = 0;    char PassWord[10];    char UserNo[20];    memset( UserNo , 0 , sizeof( UserNo ));    memset( TransNo , 0 , sizeof( TransNo ));	/*    if(FALSE==sBepsPub.GetSysCtlPar(NUM_CONNECT, sysValue, resStr))    {        printf("%s\n", resStr);        delete pMsSoket;        exit(-1);    }    filelog(CIS_SRV_LOG, "sysValue=[%s] sysConfig=[%s]", sysValue, myglobe->chiProcCount);    if(atoi(sysValue)>atoi(myglobe->chiProcCount))    {        pMsSoket->SentHeartMsg("000009NOCONNECT");        pMsSoket->Close();        disConnectToDB();        filelog(CIS_SRV_LOG, "Connect count is max and disconnect client=[%s]",            pMsSoket->clientIp);        exit(-1);    }    //sBepsPub.UpdateNumClient(ADD_CONNECT);        int Xflag = 0;    ret = sBepsPub.CheckSerail(&Xflag);    if( Xflag != 0)    {    	printf("system not permission exit\n");    	exit(0);    }*/    memset( PassWord , 0 , sizeof(PassWord));    strcpy( PassWord , getenv("PASSWORD"));    char DBUserName[10];    memset( DBUserName , 0 , sizeof(DBUserName));    strcpy( DBUserName , getenv("DBUSERNAME"));    StrTrimChar(DBUserName,' ');    if( strlen( DBUserName ) == 0 )    {	strcpy( DBUserName , "sa");    }    printf("DBUserName = [%s]\n", DBUserName);    ret = connectToDB( "SYBASE" , DBUserName, PassWord ,"DIRWAYSDB");    if( ret != 0 )    {        comSocket->Close();        printf("\r\n DataBase connect error!!!");		errlog( "DataBase connect error!!!");        exit(-1);    }	    RecvBuf = ( char *)malloc(MAXBUFF*sizeof(char));    Result = ( char *)malloc(MAXBUFF*sizeof(char));    RetMsg = ( char *)malloc(100*sizeof(char));    if( (NULL == RecvBuf) || (NULL == Result) || (NULL == RetMsg))    {		printf("\r\n malloc error!!!");		filelog(CIS_SRV_LOG, "malloc error!!!\n");		disConnectToDB();		exit(-1);    }    //子进程开始服务    printf("\nPID=[%d] System start service....\n",getpid());	for(;;)	{		memset( RecvBuf, 0, MAXBUFF);		memset( Result,  0, MAXBUFF);		memset( RetMsg,  0, 100);		memset( sResDesc, 0, MAX_MBFE_BUFFER);		//收取信息 		printf("\nPID=[%d] begin Recv....\n",getpid());			iRetval=comSocket->Recv(RecvBuf, RecvBufLen, RetCode, RetMsg); 		if ( iRetval != 0 && iRetval !=2 )		{			//登陆失败,柜员状态不初始化			if( strncmp( TransNo , "10811" , 5 ) != 0)			{				printf("柜员退出,初始化柜员状态!\n");				sBepsPub.InitUserStatus(UserNo);			}else{				printf("柜员登陆失败,不需要初始化柜员状态!\n");			}			comSocket->Close();			//sBepsPub.UpdateNumClient(DEL_CONNECT);			disConnectToDB();			free(RecvBuf);			free(Result);			free(RetMsg);			filelog(CIS_SRV_LOG, "Disconnect from client and exit!\n");			printf("Disconnect from client and exit!\n");			exit(0);		}		//非法消息不处理		if( iRetval == 2)		{			continue;		}					if(strlen(RecvBuf) > 0 )		{			RecvBuf[RecvBufLen] = '\0';			printf("\nRecv = [%d][%s]\n", strlen(RecvBuf),RecvBuf);			filelog(CIS_SRV_LOG, "RecvBuff is:[%d][%s]\n", strlen(RecvBuf), RecvBuf);			char *Begin = NULL,*End = NULL;			memset(UserNo ,0 , sizeof( UserNo ));			Begin = strstr( RecvBuf , ":LoginName:");			End = strstr( Begin + 12 , ":");			memcpy( UserNo , Begin + 11 , End - Begin - 11);			printf("UserNo = [%s]\n", UserNo );			Begin = NULL;			End = NULL;			Begin = strstr( RecvBuf , ":TranNo:");			memcpy( TransNo , Begin + 8 , 5 );			printf("TransNo = [%s]\n", TransNo );			Begin = NULL;			ret = sBepsPub.CisServer( TrNo , RecvBuf, Result, sResDesc );			if( ret <= 0 )			{				errlog("交易处理失败[%s]\n",sResDesc);				printf("交易处理失败[%s]\n",sResDesc);				continue;			}			printf("++RecvBuf:[%s]\n", RecvBuf );			//printf("++Result:[%s]\n", Result );			//printf("++sResDesc:[%s]\n", sResDesc );			SendBufLen = strlen(Result);						//返回处理结果			iRetval = comSocket->Send(Result,sResDesc,SendBufLen, &RetCode, &RetMsg);			if ( iRetval != 0 )			{				//sBepsPub.UpdateNumClient(DEL_CONNECT);				filelog(CIS_SRV_LOG, "Send data failed and exit!\n");				printf("Send data failed and exit!\n");				continue;			}		} else {			printf("非法消息丢弃不处理\n");			continue;		}////////////////////////////////////////////////////*		//每隔一分钟发送一次心跳消息		CurrTime = time(NULL);		if((CurrTime-LastTime) >= 120)		{			if(0 != comSocket->SentHeartMsg("000010SND::HK;  "))			{				MaxHeartMsgFail++;			} else {				MaxHeartMsgFail=0;			}			LastTime = CurrTime;		}		//发送心跳失败的次数超过三次后进程退出		if(MaxHeartMsgFail >= 3)		{			sBepsPub.InitUserStatus(UserNo);			comSocket->Close();			//sBepsPub.UpdateNumClient(DEL_CONNECT);			disConnectToDB();			delete comSocket;			free(RecvBuf);			free(Result);			free(RetMsg);			errlog("发送三次心跳消息失败,系统正常退出");			filelog(CIS_SRV_LOG, "Send HeartMsg max times failed and exit!\n");			printf("Send HeartMsg max times failed and exit!\n");			exit(0);		}*///		ssleep(1*10000L);	}}/////////////////////////////////////////////////////////////////////////////////	处理信号SIGTERM函数void CatchSigTerm(int sig){	myglobe->workFlag = FLAG_FORMEXIT;}    /////////////////////////////////////////////////////////////////////////////////	处理信号SIGCHLD函数void CatchChild(int sig){	pid_t  pid;	int stat;	//通知内核在没有己终止子进程时不要阻塞	while((pid = waitpid(-1, &stat, WNOHANG)) > 0) 	{		//修改该子进程对应的状态		myglobe->mutex->SetChiProInfoEx(pid, csDead);	}} /////////////////////////////////////////////////////////////////////////////////	处理信号SIGINT函数void CatchSigInt(int sig){	KillAllChilPro();	exit (0);}/////////////////////////////////////////////////////////////////////////////////	强行关闭所有进程int KillAllChilPro(){	int I;	pid_t pid;		for(I = 0; I < atoi(myglobe->chiProcCount); I++)	{		pid = myglobe->mutex->GetChiProPid(I);		if(pid > 0)		{			kill(pid, 9);		}	} 	return 0;}/////////////////////////////////////////////////////////////////////////////////	初始化全局数据bool InitGlobeData(){		//设置相关信号处理函数		signal(SIGINT, CatchSigInt);  	signal(SIGTERM, CatchSigTerm);		if(!LoadConfig())	{		errlog( "进程[CisServer]解析配置文件BepsSend.xml出错");		return false;	}			myglobe->workFlag = FLAG_RELOAD;	//初始化互斥量	myglobe->mutex = new CMuTex(atoi(myglobe->chiProcCount));		return true;}/////////////////////////////////////////////////////////////////////////////////	监控系统工作标志int MonitorWorkFlag(){	//处理僵尸进程	signal(SIGCHLD, CatchChild);	//轮询各子进程是否存在,如果不存在则关闭对应还存在的套接字	/*int pid = 0;	for(int i=1; i<atoi(myglobe->chiProcCount); i++)	{		pid = myglobe->mutex->m_ChiInfo[i].m_chiPid;		if(!myglobe->mutex->ChiProIsLive(pid))		{			int socket = myglobe->mutex->m_ChiInfo[i].m_socket;			if(socket != -1)			{				printf("Server is exit and disconect client\n");				comSocket->Close(socket);			}		}	}*/		int result = 0;	switch(myglobe->workFlag)	{		//正常流程		case FLAG_NORMAL:    		{			break;		}		//重载配置			case FLAG_RELOAD:    		{			break;		}		//进程退出		case FLAG_FORMEXIT:    		{			KillAllChilPro();			disConnectToDB();			exit(0);						}		//未定义控制符			default:    		{			break;		}	}	return result;}//	从配置文件中读取配置参数bool LoadConfig(){	bool result = true;	char conpath[50];		memset( conpath, 0x0, sizeof(conpath));	sprintf( conpath,"%s/etc/%s", getenv("WORKDIR"), CONFIGXML);		myglobe->binconfig = new CBinConfig(conpath);	result = myglobe->binconfig->IsReady();	if(result)	{		if(!(result = myglobe->binconfig->GetParameterValueByName("chiProcCount", myglobe->chiProcCount)))		{			printf("从XML中载入参数 [%s] 时出错\n", "chiProcCount");		}		else if(!(result = myglobe->binconfig->GetParameterValueByName("loglevel", myglobe->loglevel)))		{			printf("从XML中载入参数 [%s] 时出错\n", "loglevel");		}		else if(!(result = myglobe->binconfig->GetParameterValueByName("spasswd", myglobe->spasswd)))		{			printf("从XML中载入参数 [%s] 时出错\n", "spasswd");		}	}		printf("配置参数如下所示:\n");	printf("子进程的个数                   [%s]\n", myglobe->chiProcCount);	printf("与MBFE连接的密码               [%s]\n", myglobe->spasswd);	printf("日志层次深度                   [%s]\n", myglobe->loglevel);		return result;}int connectToDB( char *dbname , char *username , char *passwd , char *wkname){	if(!m_clsSybServer.Open(dbname,username ,passwd))	{		printf("连接数据库[%s][%s][%s]失败!\n",dbname,username,passwd);		return -1;	}	if(!m_clsSybServer.SetWrkDb(wkname))	{		printf("切换数据库[%s]失败!\n" , wkname);		return -1;	}	return 0;}int disConnectToDB(){	m_clsSybServer.Close();	return 0;}

⌨️ 快捷键说明

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