📄 finalrole.cpp
字号:
#include "FinalRole.h"
FinalRole::FinalRole(DEBUGFUNCTION debugFunction):
mhStdinRd(NULL),
mhStdinWr(NULL),
mhStdoutWr(NULL),
mhStdoutRd(NULL),
mhProcess(NULL),
mhThread(NULL),
mhThreadProc(NULL),
mState(ROLE_STATE_NULL),
mAction(INVALID_ACTION),
mDebugFunction(debugFunction)
{
}
FinalRole::~FinalRole(void)
{
release();
}
int FinalRole::init(wchar_t *fileName)
{
if(mState != ROLE_STATE_NULL)
return -1;
// create pipes
SECURITY_ATTRIBUTES saAttr;
saAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
saAttr.bInheritHandle = TRUE;
saAttr.lpSecurityDescriptor = NULL;
if(!CreatePipe(&mhStdinRd, &mhStdinWr, &saAttr, 0))
{
MessageBox(NULL, L"初始化子进程标准输入失败!", L"程序异常", MB_OK | MB_ICONERROR);
PostQuitMessage(0);
}
SetHandleInformation(mhStdinWr, HANDLE_FLAG_INHERIT, 0);
saAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
saAttr.bInheritHandle = TRUE;
saAttr.lpSecurityDescriptor = NULL;
if(!CreatePipe(&mhStdoutRd, &mhStdoutWr, &saAttr, 0))
{
MessageBox(NULL, L"初始化子进程标准输出失败!", L"程序异常", MB_OK | MB_ICONERROR);
PostQuitMessage(0);
}
SetHandleInformation(mhStdoutRd, HANDLE_FLAG_INHERIT, 0);
// create process
STARTUPINFO si;
PROCESS_INFORMATION pi;
ZeroMemory(&si, sizeof(si));
si.cb = sizeof(STARTUPINFO);
si.hStdInput = mhStdinRd;
si.hStdOutput = mhStdoutWr;
si.hStdError = mhStdoutWr;
si.dwFlags = STARTF_USESTDHANDLES;
ZeroMemory(&pi, sizeof(pi));
if(CreateProcess(
NULL,
(LPWSTR)fileName,
NULL,
NULL,
TRUE,
NORMAL_PRIORITY_CLASS | CREATE_NO_WINDOW,
NULL,
NULL,
&si,
&pi) == 0)
{
MessageBox(NULL, L"创建子进程失败!请检查文件是否存在!", L"警告", MB_OK | MB_ICONWARNING);
release();
return -1;
}
else
{
mhProcess = pi.hProcess;
mhThread = pi.hThread;
}
// create server thread
mhThreadProc = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)FinalRole::ThreadProc, (LPVOID)this, 0, NULL);
if(mhThreadProc == NULL)
{
MessageBox(NULL, L"创建伺服线程失败!", L"程序异常", MB_OK | MB_ICONERROR);
PostQuitMessage(0);
}
mState = ROLE_STATE_READY;
return 0;
}
int FinalRole::pause(void)
{
if(mState != ROLE_STATE_RUNNING)
return -1;
DWORD retval = SuspendThread(mhThread);
if(retval == (DWORD)(-1))
{
MessageBox(NULL, L"挂起子程序失败!", L"程序异常", MB_OK | MB_ICONERROR);
return -1;
}
if(retval > 1)
{
MessageBox(NULL, L"重复挂起子程序!", L"警告", MB_OK | MB_ICONWARNING);
ResumeThread(mhThread);
return -1;
}
return 0;
}
int FinalRole::resume(void)
{
if(mState != ROLE_STATE_RUNNING)
return -1;
DWORD retval = ResumeThread(mhThread);
if(retval == (DWORD)(-1))
{
MessageBox(NULL, L"恢复子程序失败!", L"程序异常", MB_OK | MB_ICONERROR);
return -1;
}
if(retval > 1)
{
MessageBox(NULL, L"重复挂起子程序!", L"警告", MB_OK | MB_ICONWARNING);
while(retval > 1)
retval = ResumeThread(mhThread);
}
return 0;
}
void FinalRole::unInit(void)
{
mState = ROLE_STATE_NULL;
release();
}
int FinalRole::start(void)
{
if(mState != ROLE_STATE_READY)
return -1;
char startSignal = 'S';
DWORD count;
if((!WriteFile(mhStdinWr, &startSignal, sizeof(startSignal), &count, NULL)) ||
(count != sizeof(startSignal)))
{
// 猜测选手程序有问题
mState = ROLE_STATE_BAD;
release();
MessageBox(NULL, L"发送 startSignal 失败!", L"程序异常", MB_OK | MB_ICONERROR);
return -1;
}
mState = ROLE_STATE_RUNNING;
mRoundOut = 0;
return 0;
}
int FinalRole::getAction(unsigned char &action)
{
if(mState != ROLE_STATE_RUNNING)
return -1;
// 检查选手是否已经返回决策
if(mAction == INVALID_ACTION)
{
action = NONE;
mRoundOut++;
if(mRoundOut > ROUND_OUT)
{
mState = ROLE_STATE_BAD;
release();
}
return -1;
}
action = mAction;
return 0;
}
int FinalRole::feedback(bool isQueenHere,
unsigned char x0, unsigned char y0, unsigned char direction0,
unsigned char x1, unsigned char y1, unsigned char direction1)
{
if(mState != ROLE_STATE_RUNNING)
return -1;
if(mAction == INVALID_ACTION)
return -1;
DWORD count;
RETURNPACKAGE returnPackage;
returnPackage.isQueenHere = isQueenHere;
returnPackage.x0 = x0;
returnPackage.y0 = y0;
returnPackage.direction0 = direction0;
returnPackage.x1 = x1;
returnPackage.y1 = y1;
returnPackage.direction1 = direction1;
if((!WriteFile(mhStdinWr, &returnPackage, sizeof(returnPackage), &count, NULL)) ||
(count != sizeof(returnPackage)))
{
// 猜测选手程序有问题
mState = ROLE_STATE_BAD;
release();
MessageBox(NULL, L"发送反馈信息失败!", L"程序异常", MB_OK | MB_ICONERROR);
return -1;
}
mAction = INVALID_ACTION; // 允许接纳下一个 action
return 0;
}
int FinalRole::setState(bool isCompleted)
{
if((mState != ROLE_STATE_RUNNING) && (mState != ROLE_STATE_FINISHED))
return -1;
if(isCompleted)
mState = ROLE_STATE_COMPLETED;
else
mState = ROLE_STATE_FAILED;
release();
return 0;
}
unsigned char FinalRole::getState(void)
{
return mState;
}
void FinalRole::release(void)
{
if(mhThreadProc != NULL)
{
TerminateThread(mhThreadProc, 0);
CloseHandle(mhThreadProc);
mhThreadProc = NULL;
}
if(mhProcess != NULL)
{
TerminateThread(mhThread, 0);
TerminateProcess(mhProcess, 0);
CloseHandle(mhProcess);
CloseHandle(mhThread);
mhProcess = NULL;
mhThread = NULL;
}
if(mhStdinRd != NULL)
{
CloseHandle(mhStdinRd);
mhStdinRd = NULL;
}
if(mhStdinWr != NULL)
{
CloseHandle(mhStdinWr);
mhStdinWr = NULL;
}
if(mhStdoutWr != NULL)
{
CloseHandle(mhStdoutWr);
mhStdoutWr = NULL;
}
if(mhStdoutRd != NULL)
{
CloseHandle(mhStdoutRd);
mhStdoutRd = NULL;
}
}
DWORD WINAPI FinalRole::ThreadProc(LPVOID lParam)
{
FinalRole *pRole = (FinalRole*)lParam;
DWORD count;
char id;
unsigned char action;
char message[MAXDEBUGMESSAGESIZE];
bool flag = true;
while(flag)
{
if(!ReadFile(pRole->mhStdoutRd, &id, sizeof(id), &count, NULL) ||
(count != sizeof(id)))
{
// 猜测选手程序有问题
pRole->mState = ROLE_STATE_BAD;
pRole->release();
MessageBox(NULL, L"主进程接收数据 id 失败!", L"程序异常", MB_OK | MB_ICONERROR);
break;
}
switch(id)
{
case 'A':
if(!ReadFile(pRole->mhStdoutRd, &action, sizeof(action), &count, NULL) ||
(count != sizeof(action)))
{
// 猜测选手程序有问题
pRole->mState = ROLE_STATE_BAD;
pRole->release();
flag = false;
MessageBox(NULL, L"主进程接收决策数据失败!", L"程序异常", MB_OK | MB_ICONERROR);
}
else
{
if(pRole->mAction != INVALID_ACTION)
{
// 猜测选手程序有问题
pRole->mState = ROLE_STATE_BAD;
pRole->release();
flag = false;
MessageBox(NULL, L"重复置入决策数据!", L"程序异常", MB_OK | MB_ICONERROR);
}
else
{
if(action == INVALID_ACTION)
action = NONE;
pRole->mAction = action;
}
}
break;
case 'D':
if(!ReadFile(pRole->mhStdoutRd, message, sizeof(message), &count, NULL) ||
(count != sizeof(message)))
{
// 猜测选手程序有问题
pRole->mState = ROLE_STATE_BAD;
pRole->release();
flag = false;
MessageBox(NULL, L"主进程接收调试信息失败!", L"程序异常", MB_OK | MB_ICONERROR);
break;
}
else if(pRole->mDebugFunction != NULL)
{
message[MAXDEBUGMESSAGESIZE - 1] = 0;
pRole->mDebugFunction(message);
}
break;
case 'F':
pRole->mState = ROLE_STATE_FINISHED;
pRole->release();
flag = false;
break;
default:
// 猜测选手程序有问题
pRole->mState = ROLE_STATE_BAD;
pRole->release();
flag = false;
MessageBox(NULL, L"主进程接收到错误的数据 id !", L"程序异常", MB_OK | MB_ICONERROR);
}
}
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -