📄 ysdataprocess.cpp
字号:
if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); if(rowcount<=0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } g_PublicClass.m_SrvPid=db.GetFieldValue(result,0,0).toInt(); g_PublicClass.m_MsgQueueID[0]=db.GetFieldValue(result,0,1).toInt(); g_PublicClass.m_MsgQueueID[1]=db.GetFieldValue(result,0,2).toInt(); g_PublicClass.m_MsgQueueID[2]=db.GetFieldValue(result,0,3).toInt(); g_PublicClass.m_MsgQueueID[3]=db.GetFieldValue(result,0,4).toInt(); db.ClearResult(result); if(bNew){db.DisConnectDataBase(hdbc);} if(g_PublicClass.m_SrvPid<=0||g_PublicClass.m_MsgQueueID[0]<=0) return 0; return 1;}///////////////////////////写系统日志////////////////////////////////////////bool BCDataProcess::WriteSysLog(long &hdbc,int EventClass,QString Event,int ESource,int LClass,int Result){ QString RecordIndex=g_PublicClass.GetNewRecordIndex("");int StationNo=g_PublicClass.m_StationNo; QString ModuleName=g_PublicClass.m_ModuleName; QString EDateTime=getTimeStr(); QString CDateTime=EDateTime; QString SqlStr=""; SqlStr.sprintf("Insert Into SYSLOG(RECORDINDEX,STRECORDINDEX,StationNo,ModuleName,EDateTime,EventClass,ESource,\ LClass,Event,RESULT,CURRENTDATE,NOTE) \ Values('%s','%s',%d,'%s','%s',%d,%d, %d,'%s',%d,'%s','%s');", RecordIndex.data(),"",StationNo,ModuleName.data(),EDateTime.data(),EventClass,ESource, LClass,Event.data(),Result,CDateTime.data(),""); //写入数据库 CDataBase db;bool bNew=0; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; db.SqlExec(hdbc,SqlStr); if(bNew) db.DisConnectDataBase(hdbc); if(g_PublicClass.m_OutToConsole>1) { NoticOperModule(hdbc,"SysLog",RecordIndex,DATA_SYSLOG); } if(g_PublicClass.m_OutToConsole==1||g_PublicClass.m_OutToConsole==3) { CLMutexLocker lock(&g_PublicClass.m_OutLock,true); QString s1=""; if(EventClass==0) s1="信息";else if(EventClass==1) s1="警告"; else s1="错误"; QString msg;msg="["+ModuleName+"-"+EDateTime+" '"+s1+"']"+" "+Event; printf("%s\n",msg.data()); } return true;}/////////////////////////修改模块运行时间/////////////////////////////////bool BCDataProcess::UpdateSignalTestTime(long &hdbc,int pid){ CDataBase db;int ret=0;QString serr="";bool bNew=0; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; QString SqlStr=""; QString StartTime=getTimeStr(); SqlStr.sprintf("Update MODULESTARTINFO set TESTSINALTIME='%s',SignalCount=0 Where PID=%d;",StartTime.data(),pid); ret=db.SqlExec(hdbc,SqlStr); if(bNew) db.DisConnectDataBase(hdbc); if(ret<0) return 0; return 1;}////////////////////////////////////后台服务使用的发送测试信号////////////////////////bool BCDataProcess::SendTestSignal(long &hdbc){ CDataBase db;bool bNew=0;int ret=0;long result=0;QString SqlStr="";CMessageQueue cm; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf(" Select Pid,SignalCount,RESTARTCOUNT,MODULENAME,RETRYFLAG,MODULEPATH \ from MODULESTARTINFO where STATE=1;"); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); for(int i=0;i<rowcount;i++) { int Pid=db.GetFieldValue(result,i,0).toInt(); int SignalCount=db.GetFieldValue(result,i,1).toInt(); int ReStartCount=db.GetFieldValue(result,i,2).toInt(); int isRetry=db.GetFieldValue(result,i,4).toInt(); QString ModuleName=db.GetFieldValue(result,i,3); QString ModulePath=db.GetFieldValue(result,i,5); SignalCount++; if(SignalCount>=10) //杀掉进程,删除数据库记录 { kill(Pid,SIGKILL);int kill;waitpid(Pid,&kill,0); //2.杀死该进程 //1.清除隶属队列中的有关该进程的消息 for(int j=0;j<MESSAGEQUEUES;j++) { cm.ClearMessage(g_PublicClass.m_MsgQueueID[j],Pid); } if(isRetry==1) //3.判定重试次数 { if(ReStartCount>=3) //如果重启三次,则不再重启 { SqlStr.sprintf("delete from modulestartinfo where pid=%d;",Pid);db.SqlExec(hdbc,SqlStr);sleep(1);continue; } else { ReStartCount++; SqlStr.sprintf("update modulestartinfo set RESTARTCOUNT=%d,State=0,SignalCount=0 where pid=%d;",ReStartCount,Pid); db.SqlExec(hdbc,SqlStr);SignalCount=0; //删除该模块的下级设备 SqlStr.sprintf("delete from DEVICESTARTINFO where MODULENAME='%s';",ModuleName.data()); db.SqlExec(hdbc,SqlStr); g_PublicClass.StartSomeDevModule(ModulePath,ModuleName); sleep(1); continue; } } else //不需要重启模块 { SqlStr.sprintf("delete from modulestartinfo where pid=%d;",Pid); db.SqlExec(hdbc,SqlStr); sleep(1); continue; } } SqlStr.sprintf("update modulestartinfo set signalcount=%d where pid=%d;",SignalCount,Pid);db.SqlExec(hdbc,SqlStr); g_PublicClass.m_Signal.SendSignal((pid_t)Pid,38,1,NULL,0); //发送信号38进行测试 sleep(1); } db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return 1;}//////////////////////////当系统启动时得到可以运行的所有模块并且启动//////////////////////////此函数由主模块调用void BCDataProcess::StartAllModule(long &hdbc){ CDataBase db;int ret=0;long result=0;bool bNew=0;QString SqlStr="";QString s1; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return; SqlStr.sprintf("Select distinct modulname from DeviceRela where UsedIp=1;"); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return; } int rowcount=db.GetRecordCount(result); for(int i=0;i<rowcount;i++) { s1=db.GetFieldValue(result,i,0);s1=s1.stripWhiteSpace(); if(s1=="") continue; if(!_isFileExists(g_PublicClass.GetWorkPath()+"/Module/"+s1)) continue; StartSomeDevModule(hdbc,s1); } db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);}//////////////////////////启动指定的一个模块//////////////////////////此函数由主模块调用bool BCDataProcess::StartSomeDevModule(long &hdbc,QString ModuleName){ pid_t child;QString Name=ModuleName;QString serr="";QString sParam;int f=0; ModuleName=g_PublicClass.GetWorkPath()+"/Module/"+ModuleName; sParam.sprintf("-module=%s",ModuleName.data()); if(!_isFileExists(ModuleName)) { serr.sprintf("模块:%s不存在!",ModuleName.data());WriteSysLog(hdbc,0,serr);return false; } serr.sprintf("启动模块:%s!",ModuleName.data());WriteSysLog(hdbc,0,serr); if((child=fork())==-1) {return false; } else if(child==0) { f=execl(ModuleName.data(),sParam.data(),"-n","-r","-d","-p",NULL); //带参数启动-r=需要重启;-d=注册模块 } else {return true;} if(f==-1) {return false;} return true;}/////////////////////////////注册模块//////////////////////////////////////////////////带入本身模块的类型bool BCDataProcess::InsertToModuleInfo(long &hdbc,QString ClassFlag,int isRetry){ QString SqlStr="",tmpStr;CDataBase db;int ret=0;bool bNew=0; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; //检查该模块名是否已经存在 QString where="";where.sprintf("MODULENAME='%s'",g_PublicClass.m_ModuleName.data()); int row=IsRecordExist(hdbc,"ModuleStartInfo",where); if(row==0) { tmpStr.sprintf("Insert into ModuleStartInfo(RECORDINDEX,STATIONNO,MODULENAME,STATE,PID,STARTUPTIME,RUNTIME,\ MODULETIME,VER,NOTE,SENDQUEUEID,RECVQUEUEID,OTHER,CLASSFLAG,\ RETRYFLAG,ModulePath) \ Values('%s',%d,'%s',%d,%d,'%s','%s', '%s','%s','%s',%d,%d,'%s','%s' ,%d,'%s');", g_PublicClass.GetNewRecordIndex("").data(),g_PublicClass.m_StationNo, g_PublicClass.m_ModuleName.data(),1,g_PublicClass.m_SelfPid,"","","","","", g_PublicClass.m_MsgQueueID[0],g_PublicClass.m_MsgQueueID[1],"",ClassFlag.data(), isRetry,g_PublicClass.m_ModulePath.data()); } else { //删除模块的下级设备,更新模块信息 tmpStr.sprintf("delete from devicestartinfo where ModuleName='%s';\ Update ModuleStartInfo set STATE=%d,PID=%d,ClassFlag='%s',RETRYFLAG=%d,ModulePath='%s' \ where MODULENAME='%s'", g_PublicClass.m_ModuleName.data(),1,g_PublicClass.m_SelfPid,ClassFlag.data(),isRetry,g_PublicClass.m_ModulePath.data(), g_PublicClass.m_ModuleName.data()); } SqlStr+=tmpStr; ret=db.SqlExec(hdbc,SqlStr); if(bNew) db.DisConnectDataBase(hdbc); if(ret<0) return 0; return 1;}////////////////////////////////注册一个下级设备信息/////////////////////////////////////bool BCDataProcess::InsertToDeviceInfo(long &hdbc,QString ModuleName,int StationNo,int MachineNo, int ThreadId,int CommState,QString ClassFlag,QString RecordIndex,QString ParentIndex){ //从模块名得到模块的记录号及进程号 QString SqlStr=""; CDataBase db;int ret=0;bool bNew=0; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; QString Where;Where.sprintf(" ModuleName='%s' ",ModuleName.data()); QString mRecordIndex=NormalQuery(hdbc,"ModuleStartInfo",Where,"RecordIndex"); int mPid=NormalQuery(hdbc,"ModuleStartInfo",Where,"Pid").toInt(); Where.sprintf(" Code=%d ",MachineNo); QString MachineName=NormalQuery(hdbc,"DeviceInfo",Where,"Name"); SqlStr.sprintf("delete from DeviceStartInfo where MODULENAME='%s' and STATIONNO=%d and MACHINENO=%d; \ Insert into DeviceStartInfo(PRECORDINDEX,RECORDINDEX,MODULENAME,STATIONNO,MACHINENO,\ MACHINENAME,PID,THREADID,COMMSTATE,CLASSFLAG,DEVRECORDINDEX,DEVPARENTINDEX)\ Values('%s','%s','%s',%d,%d, '%s',%d,%d,%d,'%s','%s','%s');", ModuleName.data(),StationNo,MachineNo, mRecordIndex.data(),g_PublicClass.GetNewRecordIndex(QString("%1").arg(MachineNo)).data(),ModuleName.data(),StationNo, MachineNo,MachineName.data(),mPid,ThreadId,CommState,ClassFlag.data(),RecordIndex.data(),ParentIndex.data()); ret=db.SqlExec(hdbc,SqlStr); if(bNew) db.DisConnectDataBase(hdbc); if(ret<0) return 0; return 1;}////////////////////杀死已经注册的所有进程////////////////////////////////////bool BCDataProcess :: KillAllRegProcess(long &hdbc){ QString SqlStr="";int ret=0;long result=0;CDataBase db;bool bNew=0;CMessageQueue cm; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf(" Select Pid from MODULESTARTINFO where STATE=1;"); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); for(int i=0;i<rowcount;i++) { int Pid=db.GetFieldValue(result,i,0).toInt();kill(Pid,SIGKILL);int kill;waitpid(Pid,&kill,0); for(int i=0;i<MESSAGEQUEUES;i++) { cm.ClearMessage(g_PublicClass.m_MsgQueueID[i],Pid); } SqlStr.sprintf("delete from modulestartinfo where pid=%d;",Pid);db.SqlExec(hdbc,SqlStr);usleep(100); } db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return 1;}/////////////////////////////////当后台监视模块退出时/////////////////////////////////////////////bool BCDataProcess::WhenSrvModuleExit(long &hdbc,int Pid){ CDataBase db;int ret=0;QString SqlStr="";bool bNew=0;CMessageQueue cm; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; KillAllRegProcess(hdbc); for(int i=0;i<MESSAGEQUEUES;i++) { cm.ClearMessage(g_PublicClass.m_MsgQueueID[i],Pid); cm.Remove_MessageQueue(g_PublicClass.m_MsgQueueID[i]); } SqlStr.sprintf("delete from publicinfo;");ret=db.SqlExec(hdbc,SqlStr);usleep(100); if(bNew) db.DisConnectDataBase(hdbc); kill(Pid,SIGKILL);int kill;waitpid(Pid,&kill,0); return 1;}/////////////////////////////////当子模块退出时/////////////////////////////////////////////bool BCDataProcess::WhenModuleExit(long &hdbc , int Pid) //Liang 2206/6/28{// global_cleanup.exit() ; //Liang 2006/7/19 bool bNew = false ; bool bc = isConnectDatabase(hdbc , bNew) ; if (!bc) { return false ; }//if QString SqlStr ; SqlStr.sprintf("select MACHINENO from DEVICESTARTINFO where COMMSTATE=1 and pid=%d and (CLASSFLAG='00' or CLASSFLAG='02') ;" , Pid) ; long result = 0 ; CDataBase db ; db.SqlSelect(hdbc , SqlStr , result) ; int count = db.GetRecordCount(result) ; for (int i = 0 ; i < count ; ++i) { SendCommStateToMain(db.GetFieldValue(result , i , 0).toInt() , false) ; }//for db.ClearResult(result) ; sleep(2) ; //通知上行模块 SqlStr.sprintf("update modulestartinfo set state=0 where pid=%d ; delete from devicestartinfo where pid=%d ;" , Pid , Pid) ; db.SqlExec(hdbc,SqlStr) ; if(bNew) { db.DisConnectDataBase(hdbc) ; }//if CMessageQueue cm ; for (int i = 0 ; i < MESSAGEQUEUES ; i++) { cm.ClearMessage(g_PublicClass.m_MsgQueueID[i] , Pid) ; }//for //杀死本进程,在信号处理部分 return true ;}/////////////////////////////////////每个模块发送接点时都会用到:检查目标模块运行状况//////////////////检查进程号为Pid的模块是否在运行bool BCDataProcess::CheckModuleRunning(long &hdbc,int Pid){ CDataBase db;bool bNew=0;int ret=0;long result=0;QString SqlStr=""; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf(" Select Pid,SignalCount,RESTARTCOUNT,MODULENAME from MODULESTARTINFO \ where STATE=1 and Pid=%d;",Pid); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return (rowcount>0);}/////////////////////////////////////每个模块发送接点时都会用到:检查目标模块运行状况//////////////////检查模块名ModuleName是否在运行bool BCDataProcess::CheckModuleRunning(long &hdbc,QString ModuleName){ CDataBase db;int ret=0;long result=0;bool bNew=0;QString SqlStr=""; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf(" Select Pid,SignalCount,RESTARTCOUNT,MODULENAME from MODULESTARTINFO where STATE=1 and ModuleName='%s';",ModuleName.data()); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return (rowcount>0);}////////////////////////////////////从设备号得到模块的进程号及设备通讯线程号////////////////////////////表:DeviceStartInfobool BCDataProcess::GetModulePidByMachineNo(long &hdbc,int MachineNo,int &pid,int &threadid){ CDataBase db;int ret=0;QString SqlStr="";long result=0;bool bNew=0;pid=-1;threadid=-1; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf("Select Pid,ThreadId from DeviceStartinfo where MachineNo=%d;",MachineNo); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc);return 0; } int rowcount=db.GetRecordCount(result); for(int i=0;i<rowcount;i++) { pid=db.GetFieldValue(result,i,0).toInt();threadid=db.GetFieldValue(result,i,1).toInt();break; } db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return (pid>0&&threadid!=0);}//////////////////////////////////得到操作模块或主模块的进程号//////////////////////////对于重复类型,如保护,不能使用int BCDataProcess::GetModulePid(long &hdbc,QString ClassFlag){ CDataBase db;int ret=0;QString SqlStr="";long result=0;int pid=-1;bool bNew=0; bool bc=isConnectDatabase(hdbc,bNew);if(!bc) return 0; SqlStr.sprintf("Select Pid from ModuleStartInfo where CLASSFLAG='%s';",ClassFlag.data()); ret=db.SqlSelect(hdbc,SqlStr,result); if(ret<0) { db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return -1; } int rowcount=db.GetRecordCount(result); for(int i=0;i<rowcount;i++) { pid=db.GetFieldValue(result,i,0).toInt();break; } db.ClearResult(result);if(bNew) db.DisConnectDataBase(hdbc); return pid;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -