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

📄 workthread.cpp

📁 短信群发系统
💻 CPP
字号:
// WorkThread.cpp: implementation of the WorkThread class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "notesendsystem.h"
#include "WorkThread.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

WorkThread::WorkThread(CMainFrame * pMainFrm)
{
	m_sendIn	= 0;			
	m_sendOut	= 0;					
	m_recvIn	= 0;			
	m_recvOut	= 0;
	m_orderId	= 0;
	m_pMainFrame = pMainFrm;

	m_hKillThreadEvent   = CreateEvent(NULL, TRUE, FALSE, NULL);
	m_hThreadKilledEvent = CreateEvent(NULL, TRUE, FALSE, NULL);

	InitializeCriticalSection(&m_csSend);
	InitializeCriticalSection(&m_csRecv);

	// 启动工作线程
//	AfxBeginThread(wordThread, this, THREAD_PRIORITY_NORMAL);
}

WorkThread::~WorkThread()
{
	SetEvent(m_hKillThreadEvent);			
	WaitForSingleObject(m_hThreadKilledEvent, INFINITE);	

 	DeleteCriticalSection(&m_csSend);
 	DeleteCriticalSection(&m_csRecv);
	
	CloseHandle(m_hKillThreadEvent);
	CloseHandle(m_hThreadKilledEvent);
}

void WorkThread::GetOrderId(int &order_id)
{
	m_orderId = order_id;
}
// 把消息放入发送队列
void WorkThread::PutToSendQueue(SM_PARAM* pParam)
{
	EnterCriticalSection(&m_csSend);

	memcpy(&m_SendQueue[m_sendIn], pParam, sizeof(SM_PARAM));
	m_sendIn++;
	if (m_sendIn == 100)
	{
		TRACE("发送队列已满\n");
		m_sendIn = 0;
	}
	LeaveCriticalSection(&m_csSend);
}		
// 从发送队列读取消息
BOOL WorkThread::GetFromSendQueue(SM_PARAM* pParam)
{
	EnterCriticalSection(&m_csSend);
	if (m_sendOut == m_sendIn)
	{
		LeaveCriticalSection(&m_csSend);
		return 0;
	}
	memcpy(pParam, &m_SendQueue[m_sendOut], sizeof(SM_PARAM));
	m_sendOut++;
	if (m_sendOut == 100)
	{	
		TRACE("发送队列已满\n");
		m_sendOut= 0;
	}
	LeaveCriticalSection(&m_csSend);
	return 1;	
}	

// 把读取来的消息放入接收队列
void WorkThread::PutToRecvQueue(SM_PARAM* pParam, int count)
{
	EnterCriticalSection(&m_csRecv);
	memcpy(&m_RecvQueue[m_recvIn], pParam, sizeof(SM_PARAM));		
	m_recvIn++;
	if (m_recvIn == 100)  
	{
		m_recvIn = 0;		
	}
	LeaveCriticalSection(&m_csRecv);
}
// 从接收队列中读取一条短消息
BOOL WorkThread::GetFromRecvQueue(SM_PARAM* pParam)
{
	EnterCriticalSection(&m_csRecv);

	if (m_recvIn == m_recvOut)
	{
		LeaveCriticalSection(&m_csRecv);		//
		return 0;				//表示当前队列里面没消息
	}
	memcpy(pParam, &m_RecvQueue[m_recvOut], sizeof(SM_PARAM));
	m_recvOut++;
	if (m_recvOut == 100)
	{
		TRACE("接收队列已满");
		m_recvOut = 0;
	}
	LeaveCriticalSection(&m_csRecv);
	return 1;
}

UINT WorkThread::wordThread(LPVOID pParam)
{
	WorkThread * pWork=(WorkThread *)pParam;

	SM_BUFF		buff;				// 接收临时缓冲区
	SM_PARAM	param[256];			// 接收短消息缓冲区
	int			DelNo;				// 当前删除短信的编号 
	int			SendState;			// 发送消息状态
	CTime		OldTime, NowTime;	// 时间
	enum {
		beginwait,				// 开始等待,看是否有消息
		continueWait,			// 继续等待		
		
		sendMsgCmd,				// 发送消息	,开始发送
		sendResponse,			// 发送

		readMessage,			// 发送命令,要开始读取接收队列

		delMsgCmd,				// 发送命令, 删除消息
		delResponse,			// 删除完成,读取应答
		reDel,					// 删除不成功,重新删除
		exitThread,				// 退出线程

	} nState;	

	nState = beginwait;
	while (nState != exitThread)
	{
		switch(nState)
		{
			case beginwait:						// 开始等待
				OldTime = CTime::GetCurrentTime();
				nState = continueWait;			// 继续等待状态
				break;

			case continueWait:
				Sleep(300);						// 休眠300毫秒
				NowTime = CTime::GetCurrentTime();
				if (pWork->GetFromSendQueue(&param[0]))		
				{
					nState = sendMsgCmd;			// 有数据,进入发送状态
				}
				else if (NowTime - OldTime > 5)		
				{
					nState = readMessage;			// 过了5秒, 发送读取命令
				}
				break;

			case sendMsgCmd:				// 发送消息
				gsmSendMessage(&param[0], pWork->m_pMainFrame);	// 只发送第一条信息																
				memset(&buff, 0, sizeof(buff));
				OldTime = CTime::GetCurrentTime();
				nState  = sendResponse;
				break;

			case sendResponse:
				Sleep(300);
				NowTime = CTime::GetCurrentTime();
				switch (gsmGetResponse(&buff, pWork->m_pMainFrame))
				{
					case GSM_OK: 
						// 写入数据库
						SendState = 1;
						pWork->SaveSendMsg(&param[0], SendState);
						//在界面上显示出来  发送状态成功
						pWork->m_pMainFrame->ShowSendMsg(param[0], SendState);
						Sleep(300);
						nState = beginwait;
						break;
					case GSM_ERR:
						SendState = 0;
						pWork->SaveSendMsg(&param[0], SendState);
						//在界面上显示出来  发送状态失败
						pWork->m_pMainFrame->ShowSendMsg(param[0], SendState);
						Sleep(300);
						nState = beginwait;
						break;
					default:
						if (NowTime - OldTime >= 10)
						{
							nState = beginwait;
						}
				}
				break;

			case readMessage:		// 发送命令,要开始读取接收队列
				SM_PARAM		buffer;
				memset(&buff, 0, sizeof(buff));
				//返回0表示没有数据
				if (!DetectReadMsg(buffer, pWork->m_pMainFrame))
				{
					nState = beginwait;
				}
				//有数据, 放入接收队列
				else
				{
					pWork->PutToRecvQueue(&buffer, 1);
					DelNo = buffer.index;
					nState = delMsgCmd;
				}
				break;

			case delMsgCmd:				// 发送命令, 删除消息
				gsmDeleteMessage(DelNo, pWork->m_pMainFrame);
				memset(&buff, 0, sizeof(buff));
				OldTime = CTime::GetCurrentTime();
				nState = delResponse;
			case delResponse:					// 读取删除应答
				Sleep(100);
				NowTime = CTime::GetCurrentTime();
				switch (gsmGetResponse(&buff, pWork->m_pMainFrame))		// 回应信息
				{
				case GSM_OK: 
					nState = beginwait;
					break;
				case GSM_ERR:
					nState = reDel;				//错误的时重新删除
					break;
				default:
					if (NowTime - OldTime >= 5)		//判断是否超时
					{
						nState = beginwait;
					}
				}
				break;
			case reDel:					// 删除不成功,重新删除
				Sleep(400);
				nState = delMsgCmd;
				break;
		}		
		DWORD dwEvent = WaitForSingleObject(pWork->m_hKillThreadEvent, 20);
		if (dwEvent == WAIT_OBJECT_0)  nState = exitThread;
	}
	SetEvent(pWork->m_hThreadKilledEvent);
	return 1;
}

//保存发送数据到数据库
void WorkThread::SaveSendMsg(SM_PARAM * param, int &SendState)
{	
	CNoteSendSystemApp *pApp = (CNoteSendSystemApp *)AfxGetApp();
	COleDateTime time;
	CString		 timestr;
	CString		 strContent;
	CString		 strNo;

	time = COleDateTime::GetCurrentTime();
	timestr = time.Format("%Y-%m-%d %H:%M:%S");	
	strContent = param->TP_UD;
	strNo	   = param->TPA;
	if(strNo.Left(2) == "86")  strNo = strNo.Mid(2);
	if (!pApp->m_pConnection.SaveSendMsg(m_orderId, timestr, SendState,strContent, strNo))
	{
		CString		buf;
		buf.Format("保存到数据库失败:号码[%s]", strNo);
		AfxMessageBox(buf);
	}
}


void WorkThread::init(CWnd *pWnd)
{
	// 启动工作线程
	m_pMainFrame = (CMainFrame*)pWnd;
	AfxBeginThread(wordThread, this, THREAD_PRIORITY_NORMAL);
}

⌨️ 快捷键说明

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