123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421 |
- #pragma once
- #include "SpBase.h"
- #include "SpFSM.h"
- #include "SpSecureClient.h"
- #include "download.h"
- #include <list>
- #include "Download_msg_g.h"
- using namespace Download;
- #pragma pack(1)
- // [StructName("LISTREQ")]
- struct ListReq
- {
- char TerminalNo[16];
- };
- //[StructName("LISTANS")]
- struct ListAns
- {
- int ResultCode;
- char ListXmlContent[0]; // no more than 32k
- };
- //新国密文件列表接口20200210 lwt
- // [StructName("LISTNREQ")]
- struct ListNReq
- {
- char TerminalNo[16];
- };
- //[StructName("LISTNANS")]
- struct ListNAns
- {
- int ResultCode;
- char ListXmlContent[0]; // no more than 50k
- };
- //[StructName("FILEREQ")]
- struct FileReq
- {
- //char FileName[64];
- char FileName[256];
- int BlockNo;
- };
- //[StructName("FILEANS")]
- struct FileAns
- {
- int ResultCode;
- //char FileName[64];
- char FileName[256];
- int BlockNo;
- char FileContent[0]; // no more than 32k
- };
- #pragma pack()
- enum DownloadCtlCode
- {
- Finish = 0, //完成
- Begin = 1, //开始下载
- Continua = 2, //文件已经存在,断点续传,按返回块开始传
- ErrorBlock = 3, //上块错误,重新传
- ReturnList = 4, //返回列表
- };
- #define USER_EVT_JMP_DISABLE EVT_USER+1
- #define USER_EVT_JMP_ENABLE EVT_USER+2
- #define USER_EVT_JMP_GETFILEINFO EVT_USER+3
- #define USER_EVT_FILEINO_ANS EVT_USER+4
- #define USER_EVT_FILE_ANS EVT_USER+5
- #define USER_EVT_DISCONNECT EVT_USER+6
- #define USER_EVT_JMP_SYNC EVT_USER+7
- #define USER_EVT_SYNC_FINISHED EVT_USER+8
- #define USER_EVT_NOTASK EVT_USER+9
- #define XML_US_ASCII_PREFIX "<?xml version=\"1.0\" encoding=\"utf-8\" ?>\r\n"
- struct ListAnsEvent : public FSMEvent
- {
- ListAnsEvent(BYTE *pBuf, int nLen) : FSMEvent(USER_EVT_FILEINO_ANS) {
- int size = nLen;
- int nprefix = strlen(XML_US_ASCII_PREFIX);
- int offset = 0;
- if (memcmp(pBuf + sizeof(ListAns), "<?", 2) != 0) {
- size += nprefix;
- }
- LPBYTE pData = new BYTE[size+1];
- if (size != nLen) {
- memcpy(pData, pBuf, sizeof(ListAns));
- offset = sizeof(ListAns);
- memcpy(pData+offset, XML_US_ASCII_PREFIX, nprefix);
- offset += nprefix;
- memcpy(pData+offset, pBuf+sizeof(ListAns), nLen-sizeof(ListAns));
- offset += nLen-sizeof(ListAns);
- pData[offset] = 0;
- m_xml_length = nLen - sizeof(ListAns) + nprefix;
- } else {
- memcpy(pData, pBuf, nLen);
- pData[nLen] = 0;
- m_xml_length = nLen - sizeof(ListAns);
- }
- m_reply = (ListAns*)pData;
- }
- virtual ~ListAnsEvent() { delete (LPBYTE)m_reply; }
- ListAns *m_reply;
- int m_xml_length;
- };
- //新国密文件列表回应报文
- struct ListNAnsEvent : public FSMEvent
- {
- ListNAnsEvent(BYTE *pBuf, int nLen) : FSMEvent(USER_EVT_FILEINO_ANS) {
- int size = nLen;
- int nprefix = strlen(XML_US_ASCII_PREFIX);
- int offset = 0;
- if (memcmp(pBuf + sizeof(ListAns), "<?", 2) != 0) {
- size += nprefix;
- }
- LPBYTE pData = new BYTE[size+1];
- if (size != nLen) {
- memcpy(pData, pBuf, sizeof(ListAns));
- offset = sizeof(ListAns);
- memcpy(pData+offset, XML_US_ASCII_PREFIX, nprefix);
- offset += nprefix;
- memcpy(pData+offset, pBuf+sizeof(ListAns), nLen-sizeof(ListAns));
- offset += nLen-sizeof(ListAns);
- pData[offset] = 0;
- m_xml_length = nLen - sizeof(ListAns) + nprefix;
- } else {
- memcpy(pData, pBuf, nLen);
- pData[nLen] = 0;
- m_xml_length = nLen - sizeof(ListAns);
- }
- m_reply = (ListAns*)pData;
- }
- virtual ~ListNAnsEvent() { delete (LPBYTE)m_reply; }
- ListAns *m_reply;
- int m_xml_length;
- };
- struct FileAnsEvent : public FSMEvent
- {
- FileAnsEvent(BYTE *pBuf, int nLen) : FSMEvent(USER_EVT_FILE_ANS) {
- LPBYTE pData = new BYTE[nLen+1];
- memcpy(pData, pBuf, nLen);
- m_reply = (FileAns*)pData;
- pData[nLen] = 0;
- m_content_length = nLen - sizeof(FileAns);
- }
- virtual ~FileAnsEvent() { delete (LPBYTE)m_reply; }
- FileAns *m_reply;
- int m_content_length;
- };
- struct DownloadFileTask
- {
- CSimpleStringA FileName;
- DWORD ExpireTime;
- };
- class DownloadConnection;
- class DownloadFSM : public FSMImpl<DownloadFSM>, public IFSMStateHooker, public ISysVarListener
- {
- public:
- DownloadFSM();
- virtual ~DownloadFSM();
- virtual void OnStateTrans(int iSrcState, int iDstState);
- virtual void OnSysVarEvent(const char *pszKey, const char *pszValue,const char *pszOldValue,const char *pszEntityName);
- virtual ErrorCodeEnum OnInit();
- virtual ErrorCodeEnum OnExit();
- enum {s0,s1,s2,s3,s4,s5};
- enum {SYNC_STATE = s5};
- BEGIN_FSM_STATE(DownloadFSM)
- FSM_STATE_ENTRY(s0,"Disable",s0_on_entry,s0_on_exit,s0_on_event)//判断可视柜台是否离线状态,否则等待10s再进行判断,成功则跳出不可用状态
- FSM_STATE_ENTRY(s1,"Enable",s1_on_entry,s1_on_exit,s1_on_event)//10秒内无连线状态则进入s2
- FSM_STATE_ENTRY(s2, "Active",s2_on_entry,s2_on_exit,s2_on_event)//连接中台服务,不成功则等待30s后再连接
- FSM_STATE_ENTRY(s3, "getFileInfo",s3_on_entry,s3_on_exit,s3_on_event)
- FSM_STATE_ENTRY(s4, "DownloadFile", s4_on_entry, s4_on_exit, s4_on_event)
- FSM_STATE_ENTRY(s5, "Synchronized", s5_on_entry, s5_on_exit, s5_on_event)
- END_FSM_STATE()
- BEGIN_FSM_RULE(DownloadFSM,s0)
- FSM_RULE_ENTRY_ANY(s0, s2, USER_EVT_JMP_ENABLE)
- //FSM_RULE_ENTRY_ANY(s0, s5, USER_EVT_JMP_SYNC)
- FSM_RULE_ENTRY_ANY(s1, s0, USER_EVT_JMP_DISABLE)
- FSM_RULE_ENTRY_ANY(s1, s2, EVT_TIMER)
- FSM_RULE_ENTRY_ANY(s2, s0, USER_EVT_JMP_DISABLE)
- FSM_RULE_ENTRY_ANY(s2, s1, USER_EVT_NOTASK)//无任务时跳回s1
- FSM_RULE_ENTRY_ANY(s2, s3, USER_EVT_JMP_GETFILEINFO)
- FSM_RULE_ENTRY(s3, s1, USER_EVT_FILEINO_ANS, 0)//获取信息列表失败,则跳回s1
- FSM_RULE_ENTRY(s3, s4, USER_EVT_FILEINO_ANS, 1)//需要下载
- FSM_RULE_ENTRY(s3, s5, USER_EVT_FILEINO_ANS, 2)//无信息列表,经过滤后无新任务需要下载,则跳到s5,等待一段时间下载
- FSM_RULE_ENTRY_ANY(s3, s1, USER_EVT_DISCONNECT)//通讯失败时跳回s1
- FSM_RULE_ENTRY_ANY(s3, s1, USER_EVT_NOTASK)//任务列表无任务时跳回s1
- FSM_RULE_ENTRY_ANY(s3, s0, USER_EVT_JMP_DISABLE)
- FSM_RULE_ENTRY_ANY(s4, s1, USER_EVT_DISCONNECT)//通讯失败时跳回s1
- FSM_RULE_ENTRY_ANY(s4, s0, USER_EVT_JMP_DISABLE)
- FSM_RULE_ENTRY_ANY(s4, s5, USER_EVT_JMP_SYNC)
- FSM_RULE_ENTRY_ANY(s5, s0, USER_EVT_SYNC_FINISHED)
- END_FSM_RULE()
- void s1_on_entry();
- void s1_on_exit();
- unsigned int s1_on_event(FSMEvent* event);
- void s0_on_entry();
- void s0_on_exit();
- unsigned int s0_on_event(FSMEvent* event);
- void s2_on_entry();
- void s2_on_exit();
- unsigned int s2_on_event(FSMEvent* event);
- void s3_on_entry();
- void s3_on_exit();
- unsigned int s3_on_event(FSMEvent* event);
- void s4_on_entry();
- void s4_on_exit();
- unsigned int s4_on_event(FSMEvent* event);
- void s5_on_entry();
- void s5_on_exit();
- unsigned int s5_on_event(FSMEvent* event);
- ErrorCodeEnum LoadDownloadFileList();//加载运行时文件任务
- bool checkFileStr(CSimpleStringA strFile,int count);//检查运行时文件是否正确
- ErrorCodeEnum SaveDownloadFileList();//保存运行时文件任务
- ErrorCodeEnum addDownLoadFileWork(CSimpleStringA fileName,DWORD expireTime);//添加下载任务
- ErrorCodeEnum deleteDownLoadFileWork(CSimpleStringA fileName);//取消下载任务
- ErrorCodeEnum deleteCurrentDownloadFile(CSimpleStringA fileName);//取消正在下载的任务
- ErrorCodeEnum checkWorkExpireTime();//过滤检查下载任务时效性
- ErrorCodeEnum returnDownloadFileResult(const char* filename,ErrorCodeEnum error,CSimpleStringA errorMsg);//广播下载文件结果
- ErrorCodeEnum returnDownloadProgress(download_file_t* file,download_storage_t * currentStorage);
- bool isDownloadTask(const char * filename);
- private:
- ErrorCodeEnum LoadServerConfig();
- void nextTask();
-
- private:
- DownloadConnection *m_pConnection;//中台连接
- download_storage_t *m_current; //正在下载的文件
- array_header_t *m_arr_downlist; //这次连接需要下载的文件列表
- char *m_last_filelist; // 缓存上次返回列表(废除)
- char m_base_path[MAX_PATH];
- CSimpleStringA m_server1;
- int m_server1_port;
- CSimpleStringA m_server2;
- int m_server2_port;
- std::list<DownloadFileTask*> *m_DFlist;//下载任务列表:多线程会改变里面的值
- CRITICAL_SECTION m_cs;//临界区变量
- std::list<download_file_t*> *m_currentFileTask;//当前正在下载的文件列表:只有单线程能改变里面的值
- bool isStartUp;
- public:
- CSimpleStringA m_currentFileName;//正在下载的文件名
- };
- class DownloadConnection : public SpSecureClient
- {
- public:
- DownloadConnection(CEntityBase *pEntity, DownloadFSM *pFSM) : SpSecureClient(pEntity), m_pFSM(pFSM) {}
- void SendListReq()
- {
- ListReq req = {0};
- CSystemStaticInfo si;
- {
- m_pEntity->GetFunction()->GetSystemStaticInfo(si);
- }
- strcpy(&req.TerminalNo[0], si.strTerminalID);
- CSmartPointer<IPackage> pkt = CreateNewPackage("LISTREQ");
- pkt->AddStruct("LISTREQ", false, false, (LPBYTE)&req, sizeof(ListReq));
- SendPackage(pkt);
- }
- void SendListNReq()
- {
- ListNReq req = {0};
- CSystemStaticInfo si;
- {
- m_pEntity->GetFunction()->GetSystemStaticInfo(si);
- }
- strcpy(&req.TerminalNo[0], si.strTerminalID);
- CSmartPointer<IPackage> pkt = CreateNewPackage("LISTNREQ");
- pkt->AddStruct("LISTNREQ", false, false, (LPBYTE)&req, sizeof(ListNReq));
- SendPackage(pkt);
- }
- void SendFileReq(const char *file, int block_id)
- {
- FileReq req = {0};
- req.BlockNo = block_id;
- strcpy(req.FileName, file);
- //CSmartPointer<IPackage> pkt = CreateNewPackage("FILEREQ");
- //pkt->AddStruct("FILEREQ", false, false, (LPBYTE)&req, sizeof(FileReq));
- CSmartPointer<IPackage> pkt = CreateNewPackage("LFILEREQ");
- pkt->AddStruct("LFILEREQ", false, false, (LPBYTE)&req, sizeof(FileReq));
- SendPackage(pkt);
- }
- protected:
- virtual ~DownloadConnection() {}
- virtual void OnDisconnect()
- {
- m_pFSM->PostEventFIFO(new FSMEvent(USER_EVT_DISCONNECT));
- }
- virtual void OnPkgAnswer(const CSmartPointer<IPackage> &pRecvPkg)
- {
- //以前有问题,增加errmsg错误判断,
- DWORD dwSysCode, dwUserCode;
- string strErrMsg;
- ErrorCodeEnum rc = Error_Succeed;
- if (pRecvPkg->GetErrMsg(dwSysCode, dwUserCode, strErrMsg)){
- // 错误处理
- rc = (ErrorCodeEnum)dwSysCode;
- LogError(Severity_Middle, (ErrorCodeEnum)dwSysCode, dwUserCode, strErrMsg.c_str());
- string serviceCode = pRecvPkg->GetServiceCode();
- Dbg("receive %s ans packet is error,errormsg is %s", serviceCode.c_str(),strErrMsg.c_str());
- OnDisconnect();
- }else{
- // 正常处理
- string serviceCode = pRecvPkg->GetServiceCode();
- if (serviceCode == "LISTREQ") {
- int nLen = pRecvPkg->GetStructLen("LISTANS");
- if (nLen > 0) {
- BYTE *pBuf = new BYTE[nLen];
- memset(pBuf, 0, nLen);
- int nArrayNum = 0;
- if (pRecvPkg->GetStructData("LISTANS", pBuf, &nLen, &nArrayNum)) {
- FSMEvent *evt = new ListAnsEvent(pBuf, nLen);
- m_pFSM->PostEventFIFO(evt);
- } else {
- Dbg("create invalid fileInfo_Ans packet!");
- OnDisconnect();
- }
- delete[] pBuf;
- }
- } else if (serviceCode == "LISTNREQ") {//新国密列表文件
- int nLen = pRecvPkg->GetStructLen("LISTNANS");
- if (nLen > 0) {
- BYTE *pBuf = new BYTE[nLen];
- memset(pBuf, 0, nLen);
- int nArrayNum = 0;
- if (pRecvPkg->GetStructData("LISTNANS", pBuf, &nLen, &nArrayNum)) {
- FSMEvent *evt = new ListNAnsEvent(pBuf, nLen);
- m_pFSM->PostEventFIFO(evt);
- } else {
- Dbg("create invalid fileNewInfo_Ans packet!");
- OnDisconnect();
- }
- delete[] pBuf;
- }
- } else if (serviceCode == "LFILEREQ") {
- int nLen = pRecvPkg->GetStructLen("LFILEANS");
- if (nLen > 0) {
- BYTE *pBuf = new BYTE[nLen];
- memset(pBuf, 0, nLen);
- int nArrayNum = 0;
- if (pRecvPkg->GetStructData("LFILEANS", pBuf, &nLen, &nArrayNum)) {
- FSMEvent *evt = new FileAnsEvent(pBuf, nLen);
- m_pFSM->PostEventFIFO(evt);
- } else {
- Dbg("create invalid file_Ans packet!");
- OnDisconnect();
- }
- delete[] pBuf;
- }
- } else {
- Dbg("unknown service code!");
- OnDisconnect();
- }
- }
-
- }
- private:
- DownloadFSM *m_pFSM;
- };
|