// CCOS.Dev.GEN.HaoWei.cpp : 定义 DLL 应用程序的导出函数。 // #include "stdafx.h" #include #include #include "LogicDevice.h" #include "CCOS.Dev.Generator.HaoWei.h" #include "Helper.JSON.hpp" #include #include #include #include using namespace std::placeholders; using namespace CCOS::Dev::Detail::Generator; namespace nsGEN = CCOS::Dev::Detail::Generator; #pragma warning (disable:4244) #pragma warning (disable:4305) #pragma warning (disable:4267) static const int msTimeOut_Lock = 500; #ifdef _WIN64 #ifdef _DEBUG static const auto COM_SCFDllName = "Ccos.Dev.SerialSCFX64D.dll"; #else static const auto COM_SCFDllName = "Ccos.Dev.SerialSCFX64.dll"; #endif #endif #ifdef _WIN64 #ifdef _DEBUG static const auto TCP_SCFDllName = "Ccos.Dev.TcpipSCFX64D.dll"; #else static const auto TCP_SCFDllName = "Ccos.Dev.TcpipSCFX64.dll"; #endif #endif //----------------------------------------------------------------------------- // HaoWeiDevice //----------------------------------------------------------------------------- // 储存的点值 std::vector R10_MA = { 100, 125, 160, 200, 250, 320, 400, 500, 630, 800, 1000, 1250, 1600, 2000, 2500, 3200, 4000, 5000, 6300, 8000, 10000 }; std::vector R10_MS = { 10, 12, 16, 20, 25, 32, 40, 50, 63, 80, 100, 125, 160, 200, 250, 320, 400, 500, 630, 800, 1000, 1250, 1600, 2000, 2500, 3200, 4000, 5000, 6300, 8000, 10000, 12500, 16000, 20000, 25000, 32000, 40000, 50000, 63000, 80000, 100000 }; std::vector R10_MAS = { 10, 12, 16, 20, 25, 32, 40, 50, 63, 80, 100, 125, 160, 200, 250, 320, 400, 500, 630, 800, 1000, 1250, 1600, 2000, 2500, 3200, 4000, 5000, 6300, 8000, 10000, 12500, 16000, 20000, 25000, 32000, 40000, 50000, 63000, 80000, 100000 }; std::vector R20_MA = { 100, 110, 125, 140, 160, 180, 200, 220, 250, 280, 320, 360, 400, 450, 500, 560, 630, 710, 800, 900, 1000, 1100, 1250, 1400, 1600, 1800, 2000, 2200, 2500, 2800, 3200, 3600, 4000, 4500, 5000, 5600, 6300, 7100, 8000, 9000, 10000 }; std::vector R20_MS = { 10, 11, 12, 14, 16, 18, 20, 22, 25, 28, 32, 36, 40, 45, 50, 56, 63, 71, 80, 90, 100, 110, 125, 140, 160, 180, 200, 220, 250, 280, 320, 360, 400, 450, 500, 560, 630, 710, 800, 900, 1000, 1100, 1250, 1400, 1600, 1800, 2000, 2200, 2500, 2800, 3200, 3600, 4000, 4500, 5000, 5600, 6300, 7100, 8000, 9000, 10000, 11000, 12500, 14000, 16000, 18000, 20000, 22000, 25000, 28000, 32000, 36000, 40000, 45000, 50000, 56000, 63000, 71000, 80000, 90000, 100000 }; std::vector R20_MAS = { 10, 11, 12, 14, 16, 18, 20, 22, 25, 28, 32, 36, 40, 45, 50, 56, 63, 71, 80, 90, 100, 110, 125, 140, 160, 180, 200, 220, 250, 280, 320, 360, 400, 450, 500, 560, 630, 710, 800, 900, 1000, 1100, 1250, 1400, 1600, 1800, 2000, 2200, 2500, 2800, 3200, 3600, 4000, 4500, 5000, 5600, 6300, 7100, 8000, 9000, 10000, 11000, 12500, 14000, 16000, 18000, 20000, 22000, 25000, 28000, 32000, 36000, 40000, 45000, 50000, 56000, 63000, 71000, 80000, 90000, 100000 }; atomic nsGEN::HaoWeiDevice::m_iLoopTime = HaoWei_LoopDefTime; std::atomic lastValidResponse; constexpr auto TIMEOUT = std::chrono::seconds(12); // 超时阈值 nsGEN::HaoWeiDevice::HaoWeiDevice(std::shared_ptr center, nsSCF::SCF SCF, string configfile) : super(center, SCF) { assert(EventCenter); string version; if (GetVersion(version, hMyModule)) mLog::FINFO("\n===============log begin : version:{$} ===================\n", version.c_str()); else mLog::FINFO("\n===============log begin : version:0.0.0.0 ===================\n"); m_pHardwareStatusThread = NULL; m_bMasR20 = 0; m_bUseEAcmd = 0; m_bResetActive = false; m_bIsConfigLoaded = false; m_bHasInitializedDevice = false; lastValidResponse = std::chrono::steady_clock::now(); m_DoseUnit.m_KV.reset(new KVMould(0.0, 40.0, 125.0, 1.0)); m_DoseUnit.m_MA.reset(new MAMould(0.0, 10.0, 1000.0, 0.1)); m_DoseUnit.m_MS.reset(new MSMould(0.0, 1.0, 6300.0, 0.01)); m_DoseUnit.m_MAS.reset(new MASMould(0.0, 0.1, 1000.0, 0.01)); m_DoseUnit.m_Techmode.reset(new TECHMODEMould(0, 0, 2, 1)); m_DoseUnit.m_WS.reset(new WORKSTATIONMould(1, 0, 5, 1)); m_DoseUnit.m_Focus.reset(new FOCUSMould(1, 0, 1, 1)); m_DoseUnit.m_AECField.reset(new AECFIELDMould(0, 0, 111, 1)); m_DoseUnit.m_AECFilm.reset(new AECFILMMould(0, 0, 2, 1)); m_DoseUnit.m_AECDensity.reset(new AECDENSITYMould(0, -4, 4, 1)); m_DoseUnit.m_HE.reset(new TUBEHEATMould(0, 0, 100, 1)); m_DoseUnit.m_PostKV.reset(new POSTKVMould(0.0, 40.0, 120.0, 1.0)); m_DoseUnit.m_PostMA.reset(new POSTMAMould(0.0, 10.0, 1000.0, 0.1)); m_DoseUnit.m_PostMS.reset(new POSTMSMould(0.0, 1.0, 10000.0, 0.01)); m_DoseUnit.m_PostMAS.reset(new POSTMASMould(0.0, 0.5, 1000.0, 0.01)); m_DoseUnit.m_GenSynState.reset(new GENSYNSTATEMould(0, AttrKey::GENERATOR_SYNC_ERR, AttrKey::GENERATOR_SYNC_MAX, 1)); m_DoseUnit.m_GenState.reset(new GENSTATEMould(0, AttrKey::GENERATOR_STATUS_SHUTDOWN, AttrKey::GENERATOR_STATUS_MAX, 1)); m_DoseUnit.m_GenTotalExpNumber.reset(new TOTALEXPNUMMould(0, 0, 9999, 1)); m_DoseUnit.m_GenTotalAcqTimes.reset(new TOTALACQTIMESMould(0, 0, 9999, 1)); m_DoseUnit.m_GenTubeCoolWaitTimes.reset(new TUBECOOLTIMEMould(0, 0, 9999, 1)); m_DoseUnit.m_GenTubeOverLoadNumber.reset(new TUBEOVERLOADNUMMould(0, 0, 9999, 1)); m_DoseUnit.m_GenCurrentExpNumber.reset(new CUREXPNUMMould(0, 0, 9999, 1)); m_DoseUnit.m_ExpMode.reset(new EXPMODEMould(AttrKey::EXPMODE_TYPE::Single)); m_DoseUnit.m_FrameRate.reset(new FRAMERATEMould(0, 0, 16, 1)); m_MSGUnit.reset(new nsDetail::MSGUnit(center, nsGEN::GeneratorUnitType)); m_DAP.reset(new DevDAP::DOSEMould(0.0, 0.0, 1000.0, 0.01)); m_DoseUnit.m_FLMode.reset(new FLUModeMould(AttrKey::GENERATOR_FLUMode::GENERATOR_FLMODE_NOTFLU)); m_DoseUnit.m_FLIntTime.reset(new FLUIntTimeMould(0.0, 0.0, 100.0, 0.1)); m_DoseUnit.m_FLAccTime.reset(new FLAccTimeMould(0.0, 0.0, 999.0, 0.1)); m_DoseUnit.m_FLKV.reset(new FLUKVMould(0, 40, 125, 1)); m_DoseUnit.m_FLMS.reset(new FLUMSMould(10.0, 10.0, 999999.0, 0.01)); m_DoseUnit.m_FLMA.reset(new FLUMAMould(0.5, 0.5, 99.0, 0.1)); m_DoseUnit.m_ABSStatus.reset(new FLUABSStatusMould(0, 0, 2, 1)); m_DoseUnit.m_PPS.reset(new PPSMould(0.5, 0.5, 30, 0.1)); m_DoseUnit.m_DoseLevel.reset(new FLUDoseLevelMould(0, 0, 2, 1)); m_DoseUnit.m_Curve.reset(new FLUCurveMould(0, 0, 3, 1)); m_hGenPostEvent = CreateEvent(NULL, TRUE, FALSE, NULL); string strErrConfig = GetProcessDirectory() + R"(\OEMDrivers\Generator\HaoWei\ErrorWarnInfo.json)"; m_DeviceErrorHandler.reset(new DeviceErrorHandler(center, nsGEN::GeneratorUnitType, strErrConfig)); OnCallBack(); Register(); HWSend("ST?"); StartHardwareStatusThread(); } nsGEN::HaoWeiDevice::~HaoWeiDevice() { CloseHandle(m_hGenPostEvent); } std::string nsGEN::HaoWeiDevice::GetGUID() const { mLog::FINFO("\n===============GetGUID : {$} ===================\n", GeneratorUnitType); return GeneratorUnitType; } void nsGEN::HaoWeiDevice::Register() { auto Disp = &Dispatch; superGen::Register(Disp); superGen::RegisterRAD(Disp); superGen::RegisterAEC(Disp); superGen::RegisterExpEnable(Disp); superGen::RegisterGeneratortoSyncStatus(Disp); superGen::RegisterFluoro(Disp); Disp->Get.Push(m_MSGUnit->GetKey().c_str(), [this](std::string& out) { out = m_MSGUnit->JSGet(); return RET_STATUS::RET_SUCCEED; }); auto fun_Clear_DAP = [this](auto a, auto&) { return Clear_DAP(); }; Disp->Action.Push("Clear_DAP", fun_Clear_DAP); auto fun_GetValue_DAP = [this](auto a, auto& b) { float value = 0; RET_STATUS ret = GetValue_DAP(value); b = ToJSON(value); return ret; }; Disp->Action.Push("GetValue_DAP", fun_GetValue_DAP); auto fun_StartMove = [this](auto a,auto& b) { return StartMove(); }; Disp->Action.Push("StartMove", fun_StartMove); auto fun_EndMove = [this](auto a, auto& b) { return EndMove(); }; Disp->Action.Push("EndMove", fun_EndMove); } RET_STATUS nsGEN::HaoWeiDevice::IncKV() { mLog::FINFO("KV value before calling IncKV: {$}\n", m_DoseUnit.m_KV->JSGet().c_str()); /*if (!m_DoseUnit.m_KV->CanInc()) { m_DeviceErrorHandler->ParseAndReport("ECOM_KVMAX"); return RET_STATUS::RET_SUCCEED; }*/ return HWSend("KV+"); } RET_STATUS nsGEN::HaoWeiDevice::DecKV() { mLog::FINFO("KV value before calling DecKV: {$}\n", m_DoseUnit.m_KV->JSGet().c_str()); /*if (!m_DoseUnit.m_KV->CanDec()) { m_DeviceErrorHandler->ParseAndReport("ECOM_KVMIN"); return RET_STATUS::RET_SUCCEED; }*/ return HWSend("KV-"); } RET_STATUS nsGEN::HaoWeiDevice::SetKV(float value) { mLog::FINFO("KV value before calling SetKV: {$}\n", m_DoseUnit.m_KV->JSGet().c_str()); //if (!m_DoseUnit.m_KV->Verify(value)) return RET_STATUS::RET_SUCCEED; char temp[50] = { 0 }; sprintf_s(temp, "KV%03d", (int)value); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::IncMA() { mLog::FINFO("MA value before calling IncMA: {$}\n", m_DoseUnit.m_MA->JSGet().c_str()); //if (!m_DoseUnit.m_MA->CanInc()) return RET_STATUS::RET_SUCCEED; if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is MAS, can't inc MA"); return RET_STATUS::RET_FAILED; } return HWSend("MA+"); } RET_STATUS nsGEN::HaoWeiDevice::DecMA() { mLog::FINFO("MA value before calling DecMA: {$}\n", m_DoseUnit.m_MA->JSGet().c_str()); //if (!m_DoseUnit.m_MA->CanDec()) return RET_STATUS::RET_SUCCEED; if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is MAS, can't dec MA"); return RET_STATUS::RET_FAILED; } return HWSend("MA-"); } RET_STATUS nsGEN::HaoWeiDevice::SetMA(float value) { mLog::FINFO("MA value before calling SetMA: {$}\n", m_DoseUnit.m_MA->JSGet().c_str()); if (!m_DoseUnit.m_MA->Verify(value)) return RET_STATUS::RET_SUCCEED; int index = 0; if (m_bMasR20) { index = FindClosestIndex(R20_MA, static_cast(value)); } else { index = FindClosestIndex(R10_MA, static_cast(value)); } char temp[50] = { 0 }; sprintf_s(temp, "MA%02d", index + 1); // index+1 to match the original requirement return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::IncMS() { mLog::FINFO("MS value before calling IncMS: {$}\n", m_DoseUnit.m_MS->JSGet().c_str()); /*if (!m_DoseUnit.m_MS->CanInc()) { int Level = 1; m_MSGUnit->AddWarnMessage("HaoWei_WARN", Level, "Generator MS Limit"); return RET_STATUS::RET_SUCCEED; }*/ if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is MAS, can't inc MS"); return RET_STATUS::RET_FAILED; } return HWSend("MS+"); } RET_STATUS nsGEN::HaoWeiDevice::DecMS() { mLog::FINFO("MS value before calling DecMS: {$}\n", m_DoseUnit.m_MS->JSGet().c_str()); //if (!m_DoseUnit.m_MS->CanDec()) return RET_STATUS::RET_SUCCEED; if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is MAS, can't dec MS"); return RET_STATUS::RET_FAILED; } return HWSend("MS-"); } RET_STATUS nsGEN::HaoWeiDevice::SetMS(float value) { mLog::FINFO("MS value before calling SetMS: {$}\n", m_DoseUnit.m_MS->JSGet().c_str()); //if (!m_DoseUnit.m_MA->Verify(value)) return RET_STATUS::RET_SUCCEED; int index = 0; if (m_bMasR20) { index = FindClosestIndex(R20_MS, static_cast(value)); } else { index = FindClosestIndex(R10_MS, static_cast(value)); } char temp[50] = { 0 }; sprintf_s(temp, "MS%02d", index + 1); // index+1 to match the original requirement return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::IncMAS() { mLog::FINFO("MAS value before calling IncMAS: {$}\n", m_DoseUnit.m_MAS->JSGet().c_str()); //if (!m_DoseUnit.m_MAS->CanInc()) return RET_STATUS::RET_SUCCEED; if (!m_DoseUnit.m_MS->CanInc()) { int Level = 1; m_MSGUnit->AddWarnMessage("HaoWei_WARN", Level, "Generator MS Limit"); return RET_STATUS::RET_SUCCEED; } if (m_DoseUnit.m_Techmode->Get() != AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is not MAS, can't inc MAS"); return RET_STATUS::RET_FAILED; } return HWSend("MX+"); } RET_STATUS nsGEN::HaoWeiDevice::DecMAS() { mLog::FINFO("MAS value before calling DecMAS: {$}\n", m_DoseUnit.m_MAS->JSGet().c_str()); //if (!m_DoseUnit.m_MAS->CanDec()) return RET_STATUS::RET_SUCCEED; if (m_DoseUnit.m_Techmode->Get() != AttrKey::TECHMODE_V2TYPE::ET_MAS) { mLog::FINFO("\n Techmode is not MAS, can't dec MAS"); return RET_STATUS::RET_FAILED; } return HWSend("MX-"); } RET_STATUS nsGEN::HaoWeiDevice::SetMAS(float value) { mLog::FINFO("MAS value before calling SetMAS: {$}\n", m_DoseUnit.m_MAS->JSGet().c_str()); //if (!m_DoseUnit.m_MAS->Verify(value)) return RET_STATUS::RET_SUCCEED; int index = 0; if (m_bMasR20) { index = FindClosestIndex(R20_MAS, static_cast(value)); } else { index = FindClosestIndex(R10_MAS, static_cast(value)); } char temp[50] = { 0 }; sprintf_s(temp, "MX%02d", index + 1); // index+1 to match the original requirement return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetTechmode(int value) { mLog::FINFO("Techmode value before calling SetTechmode: {$}\n", m_DoseUnit.m_Techmode->JSGet().c_str()); char temp[50] = { 0 }; sprintf_s(temp, "TE%01d", (int)value); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetFocus(int value) { mLog::FINFO("Focus value before calling SetFocus: {$}\n", m_DoseUnit.m_Focus->JSGet().c_str()); char temp[50] = { 0 }; sprintf_s(temp, "FO%01d", (int)value); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetAECDensity(int value) { if (m_DoseUnit.m_Techmode->Get() != AttrKey::TECHMODE_V2TYPE::ET_AEC) return RET_STATUS::RET_FAILED; char temp[50] = { 0 }; sprintf_s(temp, "FN%01d", (int)(value + 8)); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetAECField(int value) { if (m_DoseUnit.m_Techmode->Get() != AttrKey::TECHMODE_V2TYPE::ET_AEC) return RET_STATUS::RET_FAILED; char temp[50] = { 0 }; sprintf_s(temp, "FI%03d", (int)value); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetAECFilm(int value) { if (m_DoseUnit.m_Techmode->Get() != AttrKey::TECHMODE_V2TYPE::ET_AEC) return RET_STATUS::RET_FAILED; char temp[50] = { 0 }; sprintf_s(temp, "FS%03d", (int)value); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetWS(const string value) { int tempws = 0; if (value == "Table") tempws = (int)m_GenConfig["WSTable"]; else if (value == "Wall") tempws = (int)m_GenConfig["WSWall"]; else if (value == "Direct") tempws = (int)m_GenConfig["WSConventional"]; else if (value == "Free") tempws = (int)m_GenConfig["WSFree"]; else if (value == "Tomo") tempws = (int)m_GenConfig["WSTomo"]; char temp[50] = { 0 }; sprintf_s(temp, "WS%01d", tempws); return HWSend(temp); } string nsGEN::HaoWeiDevice::WSUI2Gen(int nUIWS) { string strWS = ""; try { if (nUIWS == AttrKey::GENWS_TYPE::TABLE) //lying: cross mode { strWS = m_GenConfig["WSTable"].encode(); } else if (nUIWS == AttrKey::GENWS_TYPE::WALL) //standing mode { strWS = m_GenConfig["WSWall"].encode(); } else if (nUIWS == AttrKey::GENWS_TYPE::FREE_TABLE) //standing mode { strWS = m_GenConfig["WSFree"].encode(); } else if (nUIWS == AttrKey::GENWS_TYPE::TOMO) //standing mode { strWS = m_GenConfig["WSTOMO"].encode(); } else if (nUIWS == AttrKey::GENWS_TYPE::CONVENTIONAL) //standing mode { strWS = m_GenConfig["WSConventional"].encode(); } } catch (ResDataObjectExption& exp) { mLog::Error("Get configuration failed, {$}\n", exp.what()); } mLog::FINFO("Set WS: {$},Generator workstaion: {$}\n", nUIWS, strWS); if (strWS == "") { strWS = "Table"; } return strWS; } RET_STATUS nsGEN::HaoWeiDevice::SetAPR(const _tAPRArgs& t) { m_t = t; mLog::FINFO("*********************Enter SetAPR*********************"); mLog::FINFO("t.ws={$},t.fKV={$},t.fMA={$},t.fMAS={$},t.nAECDensity={$},t.nAECField={$},t.nAECFilm={$},t.nFocus={$},t.nTechmode={$}", t.nWS,t.fKV, t.fMA, t.fMAS, t.nAECDensity, t.nAECField, t.nAECFilm, t.nFocus, t.nTechmode); //2 SetKV(t.fKV); //3 SetFocus(t.nFocus); //4 if (t.nTechmode == AttrKey::TECHMODE_V2TYPE::ET_AEC)//aec { SetTechmode(t.nTechmode); SetAECField(t.nAECField); SetAECDensity(t.nAECDensity); SetMA(t.fMA); SetMS(t.fMS); } else if (t.nTechmode == AttrKey::TECHMODE_V2TYPE::ET_MAS)//2p { SetTechmode(t.nTechmode); SetMAS(t.fMAS); } else if (t.nTechmode == AttrKey::TECHMODE_V2TYPE::ET_TIME)//3p { SetTechmode(t.nTechmode); SetMA(t.fMA); SetMS(t.fMS); } HWSend("RS?"); mLog::FINFO("*********************Leave SetAPR*********************"); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::QueryHE(int& value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::QueryPostKV(float& value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::QueryPostMA(float& value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::QueryPostMS(float& value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::QueryPostMAS(float& value) { value = m_DoseUnit.m_PostMAS->Get(); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::Clear_DAP() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::GetValue_DAP(float& value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::InitDevice() { HWSend("AC0"); HWSend("SF0"); HWSend("RS?"); HWSend("FO?"); GetSoftwareVersion(); HWSend("GC?"); SetPriorityCoefficient(m_bMasR20); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::StartMove() { mLog::FINFO("Enter startMove"); mLog::FINFO("end startmove"); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::EndMove() { mLog::FINFO("Enter endmove"); mLog::FINFO("end EndMove"); return RET_STATUS::RET_SUCCEED; } int CCOS::Dev::Detail::Generator::HaoWeiDevice::GetGenState() { const int currentState = m_DoseUnit.m_GenState->Get(); if (currentState == 0) { m_DeviceErrorHandler->ParseAndReport("ECOM_CommLost"); } return currentState; } int CCOS::Dev::Detail::Generator::HaoWeiDevice::LoadConfig(string configfile) { mLog::FINFO("=====================LoadConfig========================="); // 检查文件是否存在 std::ifstream file(configfile); if (!file) { // 文件不存在,直接返回空的Connection对象 mLog::FINFO("Config file does not exist: {$}", configfile.c_str()); return -1; } if (m_bIsConfigLoaded) { mLog::FINFO("Configuration already loaded."); return 0; } m_strConfigPath = configfile; ResDataObject temp; temp.loadFile(m_strConfigPath.c_str()); m_GenConfig = temp["CONFIGURATION"]; TransJsonText(m_GenConfig); if (m_GenConfig.GetKeyCount("R20Enable") > 0) { m_bMasR20 = (bool)m_GenConfig["R20Enable"]; } HWSend("ST?"); m_bIsConfigLoaded = true; return 0; } int nsGEN::HaoWeiDevice::SetPriorityCoefficient(int nCoefficient) { char temp[50] = { 0 }; sprintf_s(temp, "GC%01d", nCoefficient); return HWSend(temp); } int CCOS::Dev::Detail::Generator::HaoWeiDevice::GetSoftwareVersion() { mLog::FINFO("Enter GetSoftwareVersion...\n"); return HWSend("GR?"); } int CCOS::Dev::Detail::Generator::HaoWeiDevice::SetPulseSyncMode(int nMode) { char temp[50] = { 0 }; sprintf_s(temp, "FMM%01d", nMode); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SimulateError(std::string Error) { mLog::FINFO("Enter SimulateError...{$} \n", Error.c_str()); std::string type = m_DeviceErrorHandler->ParseAndReport(Error); if (type == "error") { mLog::FINFO("type == error"); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); } return RET_STATUS::RET_SUCCEED; } int nsGEN::HaoWeiDevice::FindClosestIndex(const std::vector& values, int target) { auto it = std::lower_bound(values.begin(), values.end(), target); if (it == values.end()) { return values.size() - 1; } int index = std::distance(values.begin(), it); if (index > 0 && std::abs(values[index - 1] - target) <= std::abs(values[index] - target)) { return index - 1; } return index; } RET_STATUS nsGEN::HaoWeiDevice::SetGenSynState(int value) { mLog::FINFO("Enter SetGenSynState:[{$}]", value); switch (value) { case AttrKey::GENERATOR_RAD_OFF: { }break; case AttrKey::GENERATOR_RAD_PREPARE: { }break; case AttrKey::GENERATOR_RAD_READY: { }break; case AttrKey::GENERATOR_RAD_XRAYON: { }break; case AttrKey::GENERATOR_RAD_XRAYOFF: { }break; case AttrKey::GENERATOR_FLU_OFF: { }break; case AttrKey::GENERATOR_FLU_READY: { }break; case AttrKey::GENERATOR_FLU_XRAYON: { int fluMode = m_DoseUnit.m_FLMode->Get(); mLog::FINFO("SetGenSynState: current FluMode[{$}]", fluMode); switch (fluMode) { case AttrKey::GENERATOR_FLMODE_NOTFLU: break; case AttrKey::GENERATOR_FLMODE_CF: case AttrKey::GENERATOR_FLMODE_HCF: { }break; case AttrKey::GENERATOR_FLMODE_PF: case AttrKey::GENERATOR_FLMODE_HPF: { }break; break; case AttrKey::GENERATOR_FLMODE_MAX: break; default: break; } }break; case AttrKey::GENERATOR_FLU_XRAYOFF: { }break; default: break; } return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetGenState(int value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetExpMode(std::string value) { mLog::FINFO("Enter SetExpMode...{$}",value); m_DoseUnit.m_ExpMode->Update(value); if (!m_DeviceErrorHandler->HasActiveErrors()) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); else { m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR); FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); } return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetFLFMode(std::string value) { mLog::FINFO("Enter SetFLFMode...,FLFMode:{$} \n", value.c_str()); if (value == "CF") { m_DoseUnit.m_FLMode->Update(1); HWSend("FMF0"); } else if (value == "PF") { m_DoseUnit.m_FLMode->Update(2); HWSend("FMF1"); } else if (value == "HLF") { m_DoseUnit.m_FLMode->Update(2); HWSend("FMF1"); } else { mLog::FINFO("other FluMode : {$}", value.c_str()); } return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetAPF(const _tAPFArgs& t) { mLog::FINFO("APF:FLKV={$},FLMA={$},PPS={$},WS={$},FLuType={$},ABSMode={$},DoseLever={$}", t.nFLKV, t.fFLMA, t.nPPS, t.nWS, t.nFluMode, t.nABSMode, t.nDoseLever); SetFluKV(t.nFLKV); SetFluMA(t.fFLMA); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::IncFluKV() { mLog::FINFO("FluKV value before calling IncFluKV: {$}\n", m_DoseUnit.m_FLKV->JSGet().c_str()); //if (!m_DoseUnit.m_FLKV->CanInc()) return RET_STATUS::RET_SUCCEED; return HWSend("FKV+"); } RET_STATUS nsGEN::HaoWeiDevice::DecFluKV() { mLog::FINFO("FluKV value before calling DecFluKV: {$}\n", m_DoseUnit.m_FLKV->JSGet().c_str()); // (!m_DoseUnit.m_FLKV->CanDec()) return RET_STATUS::RET_SUCCEED; return HWSend("FKV-", 4); } RET_STATUS nsGEN::HaoWeiDevice::SetFluKV(float value) { mLog::FINFO("FluKV value before calling SetFluKV: {$}\n", m_DoseUnit.m_FLKV->JSGet().c_str()); //if (!m_DoseUnit.m_FLKV->Verify(value)) return RET_STATUS::RET_SUCCEED; char temp[50] = { 0 }; sprintf_s(temp, "FKV%03d", (int)value); return HWSend(temp, strlen(temp)); } RET_STATUS nsGEN::HaoWeiDevice::IncFluMA() { mLog::FINFO("FluMA value before calling IncFluMA: {$}\n", m_DoseUnit.m_FLMA->JSGet().c_str()); //if (!m_DoseUnit.m_FLMA->CanInc()) return RET_STATUS::RET_SUCCEED; return HWSend("FMA+"); } RET_STATUS nsGEN::HaoWeiDevice::DecFluMA() { mLog::FINFO("FluMA value before calling DecFluMA: {$}\n", m_DoseUnit.m_FLMA->JSGet().c_str()); //if (!m_DoseUnit.m_FLMA->CanDec()) return RET_STATUS::RET_SUCCEED; return HWSend("FMA-"); } RET_STATUS nsGEN::HaoWeiDevice::SetFluMA(float value) { mLog::FINFO("FluMA value before calling SetFluMA: {$}\n", m_DoseUnit.m_FLMA->JSGet().c_str()); if (!m_DoseUnit.m_FLMA->Verify(value)) return RET_STATUS::RET_SUCCEED; char temp[50] = { 0 }; sprintf_s(temp, "FMA%04d", (int)(value * 10)); return HWSend(temp, strlen(temp)); } RET_STATUS nsGEN::HaoWeiDevice::INCPPS() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::DECPPS() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetPPS(float value) { //if (!m_DoseUnit.m_PPS->Verify(value)) return RET_STATUS::RET_SUCCEED; char temp[50] = { 0 }; sprintf_s(temp, "FMN%02d", value); return HWSend(temp, strlen(temp)); } RET_STATUS nsGEN::HaoWeiDevice::SetABSMode(int nMode) { if (!m_DoseUnit.m_ABSStatus->Verify(nMode)) return RET_STATUS::RET_SUCCEED; char temp[50] = { 0 }; mLog::FINFO("SetABSMode[{$}] \n", nMode); sprintf_s(temp, "IBS%1d", (int)nMode); return HWSend(temp, strlen(temp)); } RET_STATUS nsGEN::HaoWeiDevice::SetABSCurve(int curveNum) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::IncABSCurve() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::DecABSCurve() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::GetABSCurve() { return RET_STATUS::RET_SUCCEED; } float nsGEN::HaoWeiDevice::GetFluIntTimer() { return RET_STATUS::RET_SUCCEED; } float nsGEN::HaoWeiDevice::GetFluAccTimer() { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::ResetFluTimer(int ntype) { mLog::FINFO("ReSetFluAccTimer:[{$}] \n", ntype); return HWSend("FTC"); } RET_STATUS nsGEN::HaoWeiDevice::SetFluPre(int value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetFluEXP(int value) { return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetFluMode(std::string value) { mLog::FINFO("Enter SetFLFMode...{$} \n", value.c_str()); if (value == "CF") { m_DoseUnit.m_FLMode->Update(1); return HWSend("FLF1", 4); } else if (value == "PF") { m_DoseUnit.m_FLMode->Update(2); return HWSend("FLF2", 4); } else { mLog::FINFO("other FluMode : {$}", value.c_str()); return RET_STATUS::RET_SUCCEED; } } RET_STATUS nsGEN::HaoWeiDevice::SetFluDoseLever(int value) { return RET_STATUS::RET_SUCCEED; } void CCOS::Dev::Detail::Generator::HaoWeiDevice::UpdateLimits(const std::string& key, float& currentValue, float defaultValue) { if (m_GenConfig.GetKeyCount(key.c_str()) > 0) { currentValue = static_cast(m_GenConfig[key.c_str()]); } else { currentValue = defaultValue; } } void CCOS::Dev::Detail::Generator::HaoWeiDevice::UpdateLimitsInt(const std::string& key, int& currentValue, int defaultValue) { if (m_GenConfig.GetKeyCount(key.c_str()) > 0) { currentValue = static_cast(m_GenConfig[key.c_str()]); } else { currentValue = defaultValue; } } RET_STATUS nsGEN::HaoWeiDevice::SetEXAMMode(std::string value) { //EXAMMODE_TYPE::MANUAL return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::ActiveSyncMode(_tSyncModeArgs value) { mLog::FINFO("value.strSyncMode: {$}, value.strSyncValue: {$}, value.strWS: {$} \n", value.strSyncMode, value.strSyncValue, value.strWS); int nSyncModeValue = atoi(value.strSyncValue.c_str()); char temp[50] = { 0 }; sprintf_s(temp, "WS%01d", nSyncModeValue); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetFrameRate(FLOAT frameRate) { m_DoseUnit.m_FrameRate->Update(frameRate); //this variable should be set when in oncallback. char temp[50]{ 0 }; sprintf_s(temp, "FLS%03d", int(frameRate*10)); return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::SetRPS(int rps) { return RET_STATUS::RET_SUCCEED; //char temp[50]{ 0 }; //sprintf_s(temp, "RPS%03d", rps * 10); //return HWSend(temp); } RET_STATUS nsGEN::HaoWeiDevice::RefreshData() { HWSend("RS?"); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::SetExpEnable() { mLog::FINFO("SetExpEnable in ...\n"); if (!m_DeviceErrorHandler->HasActiveErrors()) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); else { m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR); FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); } return RET_STATUS::RET_SUCCEED; //return HWSend("EXB1"); } RET_STATUS nsGEN::HaoWeiDevice::SetExpDisable() { mLog::FINFO("SetExpDisable in...\n"); if (!m_DeviceErrorHandler->HasActiveErrors()) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); else { m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR); FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); } mLog::FINFO("SetExpDisable... {$}\n", m_DoseUnit.m_GenState->JSGet().c_str()); return RET_STATUS::RET_SUCCEED; } RET_STATUS nsGEN::HaoWeiDevice::Reset() { m_bResetActive = true; mLog::FINFO("RESET in...\n"); return HWSend("CLR0"); m_DeviceErrorHandler->ClearAllErrors(); m_DeviceErrorHandler->ClearAllWarnings(); int level = 0; } RET_STATUS nsGEN::HaoWeiDevice::HWSend(char* strCommand, int nTimeOut) { if (!m_SCF) return RET_STATUS::RET_FAILED; char strSendCommand[100] = { 0 }; int len = strlen(strCommand); int totalLength = len + 3; int tmpSum = 0; for (int i = 0; i < len; i++) { tmpSum += (int)strCommand[i]; } char checkSum = char(tmpSum + 3); //3 is ETX memcpy(strSendCommand, strCommand, len); strSendCommand[len] = 0x03; strSendCommand[len + 1] = checkSum; strSendCommand[len + 2] = 0x00; mLog::FINFO("==OUT==: {$} \n", strSendCommand); int retLength; m_SCF.Lock(msTimeOut_Lock) .SendPacket(strSendCommand, totalLength, nTimeOut, retLength); Sleep(nTimeOut); return RET_STATUS::RET_SUCCEED; } //----------------------------------------------------------------------------- // ProcessCmd //----------------------------------------------------------------------------- void nsGEN::HaoWeiDevice::FireNotify(std::string key, std::string content) { EventCenter->OnNotify(1, key, content); } struct tFrameMapping { static const int MaxLen = 5; // 前缀不能超超过 5 个字符 ! using cbFun = std::function ; char strHead[MaxLen]; int NbOfCharOfHead; cbFun fun; tFrameMapping(char* str, int len, cbFun f) { assert(len < MaxLen); //len最大只能是4 //strHead[0] = 0x02; //STX ----------->note : no package header for (int i = 0; i < len; i++) //给strHead赋值 strHead[i] = str[i]; NbOfCharOfHead = len; fun = f; } }; static std::list arFrame; static bool DecodeFrame(const char* strFrame, int length); void nsGEN::HaoWeiDevice::OnCallBack() { auto HWNotProcess = [](const char* value, int length) -> void { printf("\n This commands didn't need to process!\n"); mLog::FINFO("\n This commands didn't need to process!\n"); }; //==IN==:KV070 MA00320 MS00063 MX00036 sometimes : this long str appear. so must deal with it auto HWKV = [this](const char* value, int length) -> void { assert(value); mLog::FINFO("hwkv={$},len={$}",value, length); int tmpkv = atoi(value); m_DoseUnit.m_KV->Update(tmpkv); FireNotify(AttrKey::KV, m_DoseUnit.m_KV->JSGet()); }; //==IN==:TU0 WS1 FO0 ET0 FI010 FS001 FN 0 HE000 auto HWTU = [this](const char* value, int length) -> void { assert(value); mLog::FINFO("recv TU={$},len={$}", value,length); }; auto HWEC = [this](const char* value, int length) -> void { assert(value); mLog::FINFO("recv EC{$}",value); }; auto HWST = [this](const char* value, int length) -> void { assert(value); int genStatus = atoi(value); // 获取状态码的首位数字,用来判断阶段 int statusPrefix = genStatus / 10; // 根据阶段处理不同的状态 switch (statusPrefix) { case 10: // 初始化阶段 (101, 102, 103) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Initialization Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_INIT)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); break; case 20: // 待机阶段 (200) if (!m_bHasInitializedDevice) { InitDevice(); m_bHasInitializedDevice = true; } mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Standby Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_STANDBY)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); break; case 30: // 拍片准备阶段 (300) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Film Prep Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 40: // 透视准备阶段 (400) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Fluoroscopy Prep Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 50: // 曝光阶段 (500) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Exposure Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 60: // 透视阶段 (600) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Fluoroscopy Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 70: // 点片曝光阶段 (700) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Spot Exposure Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 80: // 故障阶段 (800) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Fault Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); break; case 90: // 灯丝自动校准阶段 (900) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Filament Auto Calibration Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 91: // 透视校准阶段 (910) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Fluoroscopy Calibration Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 92: // 配置阶段 (920) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Configuration Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 93: // 复位阶段 (930) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Reset Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; case 94: // 升级阶段 (940) mLog::FINFO("Get Gen Status:GENSTATE {$} -> (Upgrade Phase)", m_DoseUnit.m_GenState->JSGet().c_str()); break; default: mLog::FINFO("Get Gen Status: [{$}] unknown", genStatus); break; } }; auto HWMAS = [this](const char* value, int length) { assert(value); int index = atoi(value); float fmas = (m_bMasR20) ? R20_MAS[index] : R10_MAS[index]; fmas = fmas / 100.0; mLog::FINFO("Current MAS:{$}", fmas); if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_TIME) { m_DoseUnit.m_MAS->Update(fmas); FireNotify(AttrKey::MAS, to_string(0)); } else { m_DoseUnit.m_MAS->Update(fmas); FireNotify(AttrKey::MAS, m_DoseUnit.m_MAS->JSGet()); } }; auto HWMA = [this](const char* value, int length) { assert(value); int index = atoi(value); float fma = (m_bMasR20) ? R20_MA[index] : R10_MA[index]; fma = fma / 10.0; mLog::FINFO("Current MA:{$}", fma); if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { m_DoseUnit.m_MA->Update(fma); FireNotify(AttrKey::MA, to_string(0)); } else { m_DoseUnit.m_MA->Update(fma); FireNotify(AttrKey::MA, m_DoseUnit.m_MA->JSGet()); } }; auto HWMS = [this](const char* value, int length) { assert(value); int index = atoi(value); float fms = (m_bMasR20) ? R20_MS[index] : R10_MS[index]; fms = fms / 10.0; mLog::FINFO("Current MS:{$}", fms); if (m_DoseUnit.m_Techmode->Get() == AttrKey::TECHMODE_V2TYPE::ET_MAS) { m_DoseUnit.m_MS->Update(fms); FireNotify(AttrKey::MS, to_string(0)); } else { m_DoseUnit.m_MS->Update(fms); FireNotify(AttrKey::MS, m_DoseUnit.m_MS->JSGet()); } }; auto HWFocus = [this](const char* value, int length) { assert(value); int nfous = atoi(value); m_DoseUnit.m_Focus->Update(nfous); { FireNotify(AttrKey::FOCUS, m_DoseUnit.m_Focus->JSGet()); mLog::FINFO("Current focus:{$}, FO={$}", atoi(m_DoseUnit.m_Focus->JSGet().c_str()) ? "large focus" : "small focus", m_DoseUnit.m_Focus->JSGet().c_str()); } }; auto HWTechmode = [this](const char* value, int length) { assert(value); int ntechmode = atoi(value); m_DoseUnit.m_Techmode->Update(ntechmode); FireNotify(AttrKey::TECHMODE, m_DoseUnit.m_Techmode->JSGet()); switch (ntechmode) { case 0: mLog::FINFO("ET={$}", "mA/ms", m_DoseUnit.m_Techmode->JSGet().c_str()); break; case 1: mLog::FINFO("ET={$}", "mAs", m_DoseUnit.m_Techmode->JSGet().c_str()); break; case 2: mLog::FINFO("ET={$}", "AEC", m_DoseUnit.m_Techmode->JSGet().c_str()); break; } }; auto HWAECField = [this](const char* value, int length) { assert(value); int nvalue = atoi(value); if (m_DoseUnit.m_AECField->Update(nvalue)) FireNotify(AttrKey::AECFIELD, m_DoseUnit.m_AECField->JSGet()); }; auto HWAECFilm = [this](const char* value, int length) { assert(value); int nvalue = atoi(value); if (m_DoseUnit.m_AECFilm->Update(nvalue)) FireNotify(AttrKey::AECFILM, m_DoseUnit.m_AECFilm->JSGet()); }; auto HWAECDensity = [this](const char* value, int length) { assert(value); int nvalue = atoi(value); if (m_DoseUnit.m_AECDensity->Update(nvalue)) FireNotify(AttrKey::AECDENSITY, m_DoseUnit.m_AECDensity->JSGet()); }; auto HWWS = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (m_DoseUnit.m_WS->Update(nValue)) { FireNotify(m_DoseUnit.m_WS->GetKey(), m_DoseUnit.m_WS->JSGet()); } }; auto HWPR = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (nValue == 2) { mLog::FINFO("The high voltage generator enters the exposure preparation stage。"); HWSend("PR2"); } else if (nValue == 1) { HWSend("PR1"); m_iLoopTime = HaoWei_LoopExpTime; if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_RAD_PREPARE)) { FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); mLog::FINFO("Generator exposure process status:GENERATOR_RAD_PREPARE"); } } else if (nValue == 0) { HWSend("PR0"); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_RAD_OFF)); { FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); mLog::FINFO("Generator exposure process status:{$};", "GENERATOR_RAD_OFF"); mLog::FINFO("HWPR m_DoseUnit.m_GenSynState->JSGet()={$}", m_DoseUnit.m_GenSynState->JSGet().c_str()); RefreshData(); } if (m_iLoopTime == HaoWei_LoopExpTime) { if ((int)m_GenConfig["loopTime"] >= 100) { m_iLoopTime = (int)m_GenConfig["loopTime"]; } else m_iLoopTime = HaoWei_LoopDefTime; mLog::FINFO("reduction loopTime[{$}]->[{$}]", HaoWei_LoopExpTime, m_iLoopTime.load()); } } }; auto HWXR = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (nValue == 1) { HWSend("XR1"); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_RAD_READY)) { FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); mLog::FINFO("Generator exposure process status:{$};", "GENERATOR_RAD_READY"); } } else if (nValue == 2) { HWSend("XR2"); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_EXP)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_RAD_XRAYON)) { FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); mLog::FINFO("Generator exposure process status:{$};", "GENERATOR_RAD_XRAYON"); } } else if (nValue == 0) { HWSend("XR0"); if(m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_RAD_XRAYOFF)); { FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); mLog::FINFO("Generator exposure process status:{$};", "GENERATOR_RAD_XRAYOFF"); mLog::FINFO("HWXR m_DoseUnit.m_GenSynState->JSGet()={$}", m_DoseUnit.m_GenSynState->JSGet().c_str()); HWSend("AT?"); } } }; auto HWVPDOSE = [this](const char* value, int length)//mas { assert(value); m_DoseUnit.m_PostKV->Update(atof(value)); FireNotify(AttrKey::POSTKV, m_DoseUnit.m_PostKV->JSGet()); mLog::FINFO("Actual exposure parameters KV:{$}", m_DoseUnit.m_PostKV->JSGet().c_str()); }; auto HWAPDOSE = [this](const char* value, int length)//mas { assert(value); m_DoseUnit.m_PostMAS->Update(atof(value) / 10.0); FireNotify(m_DoseUnit.m_PostMAS->GetKey(), m_DoseUnit.m_PostMAS->JSGet()); FireNotify(AttrKey::POSTKV, m_DoseUnit.m_KV->JSGet()); mLog::FINFO("Actual exposure parameters MAS:{$}", m_DoseUnit.m_PostMAS->JSGet().c_str()); }; auto HWATDOSE = [this](const char* value, int length) { assert(value); m_DoseUnit.m_PostMS->Update(atof(value) / 10.0); FireNotify(m_DoseUnit.m_PostMS->GetKey(), m_DoseUnit.m_PostMS->JSGet()); m_DoseUnit.m_PostMA->Update(m_DoseUnit.m_MA->Get()); FireNotify(m_DoseUnit.m_PostMA->GetKey(), m_DoseUnit.m_PostMA->JSGet()); m_DoseUnit.m_PostKV->Update(m_DoseUnit.m_KV->Get()); FireNotify(AttrKey::POSTKV, m_DoseUnit.m_PostKV->JSGet()); m_DoseUnit.m_PostMAS->Update(m_DoseUnit.m_MAS->Get()); FireNotify(m_DoseUnit.m_PostMAS->GetKey(), m_DoseUnit.m_PostMAS->JSGet()); mLog::FINFO("Actual exposure parameters MS:{$}", m_DoseUnit.m_PostMS->JSGet().c_str()); }; auto HWDAPST = [this](const char* value, int length) { assert(value); int dapStatus = atoi(value); if (dapStatus == 1) { m_bDAPEnable = true; m_bAKEnable = false; } else if (dapStatus == 2) { m_bDAPEnable = false; m_bAKEnable = true; } else if (dapStatus == 3) { m_bDAPEnable = true; m_bAKEnable = true; } else { m_bDAPEnable = false; m_bAKEnable = false; } }; auto HWDT = [this](const char* value, int length) { assert(value); int dapStatus = atoi(value); if (dapStatus == 0) { m_bDAPEnable = false; mLog::FINFO("DAP test failed"); } else if (dapStatus == 1) { m_bDAPEnable = true; mLog::FINFO("DAP test passed"); } else if (dapStatus == 2) { m_bDAPEnable = true; mLog::FINFO("DAP test in progress."); } }; auto HWDAP = [this](const char* value, int length) { assert(value); //m_DoseUnit.->Update(atof(value)); //FireNotify(m_DoseUnit.m_PostMS->GetKey(), m_DoseUnit.m_PostMS->JSGet()); //SetEvent(m_hGenPostEvent); m_DAP->Update(atof(value)); //should push to subsystem....... }; auto HWGR = [this](const char* value, int length) { assert(value); // 提取机器型号、功率版本和功能类型 std::string version(value, 3); // 前3个字符为机器型号 char functionalityChar = value[3]; // 第4个字符表示功能类型 // 功能类型的映射 std::string functionality; if (functionalityChar == '0') { functionality = "PR (pet photography)"; } else if (functionalityChar == '1') { functionality = "PF (Pet fluoroscopy)"; } else if (functionalityChar == '2') { functionality = "MR (Human medical photography)"; } else if (functionalityChar == '3') { functionality = "MF (Human medical fluoroscopy)"; } else if (functionalityChar == '4') { functionality = "DR (Single tooth)"; } else if (functionalityChar == '5') { functionality = "DF (CBCT)"; } else if (functionalityChar == '6') { functionality = "IX (industrial circle)"; } else if (functionalityChar == '7') { functionality = "0X (other)"; } else { functionality = "Unknown Functionality:"+ functionalityChar; } // 日志打印输出 mLog::FINFO("Version: {$}, Functionality: {$}", version, functionality.c_str()); }; auto HWGV = [this](const char* value, int length) { assert(value); // 打印原始值 mLog::FINFO("value: {$}", value); int versionNumber = atoi(value); // 拆解 versionNumber 为 4个部分(假设数字按版本号分割:10010 -> V1.0.0.10) int major = versionNumber / 10000; // 取高位,得到主版本号 int minor = (versionNumber / 1000) % 10; // 取次高位,得到次版本号 int patch = (versionNumber / 100) % 10; // 取中位,得到修补版本号 int build = versionNumber % 100; // 取低位,得到构建版本号 // 格式化并打印详细版本信息 mLog::FINFO("Software Version: V{$}.{$}.{$}.{$}", major, minor, patch, build); }; auto HWGU = [this](const char* value, int length) { assert(value); // 打印原始值 mLog::FINFO("value: {$}", value); std::string versionCode(value, 2); // 定义版本类型 std::string versionType; if (versionCode == "00") { versionType = "General Version"; } else if (versionCode == "01") { versionType = "Custom Version"; } else { versionType = "Unknown Version"; // 处理其他情况,可以根据需求扩展 } // 输出详细的版本信息 mLog::FINFO("Software Version: {$}, Type: {$}", value, versionType.c_str()); }; auto HWTR = [this](const char* value, int length) { assert(value); if (value) { mLog::FINFO("Start automatic exposure once, after the end of an automatic reset"); } else { mLog::FINFO("Stop automatic exposure"); } }; auto HWGC = [this](const char* value, int length) { assert(value); if (value) { mLog::FINFO("R20"); } else { mLog::FINFO("R10"); } }; auto HWER = [this](const char* value, int length) { assert(value); std::string errorCode = "HaoWei_ER" + std::string(value); if (m_DeviceErrorHandler->ParseAndReport(errorCode) == "error") { if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_ERROR)) { FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); } } }; auto HWWAR = [this](const char* value, int length) { assert(value); int nWran = atoi(value); if (nWran) { m_DeviceErrorHandler->ParseAndReport("ECOM_FluoroTimerLimitError"); } }; auto HWEHE = [this](const char* value, int length) { assert(value); int nhe = atoi(value); mLog::FINFO("HE{$}%", nhe); if (m_DoseUnit.m_HE->Update(nhe)) FireNotify(m_DoseUnit.m_HE->GetKey(), m_DoseUnit.m_HE->JSGet()); }; //075 FLM100 FLI000 FLT006 FLF2 FLA0 FLS060 FLZ0 FLD0 auto HWFKV = [this](const char* value, int length) { assert(value); m_DoseUnit.m_FLKV->Update(atof(value)); FireNotify(AttrKey::FLUKV, m_DoseUnit.m_FLKV->JSGet()); }; auto HWFMA = [this](const char* value, int length) { assert(value); float tmpflm = atof(value) / 10.0; if (m_DoseUnit.m_FLMA->Update(tmpflm)) FireNotify(AttrKey::FLUMA, m_DoseUnit.m_FLMA->JSGet()); }; auto HWFLS = [this](const char* value, int length) { assert(value); mLog::FINFO("HWFLS={$}", value); float tmppps = atof(value) / 10.0; if (m_DoseUnit.m_PPS->Update(tmppps)) FireNotify(AttrKey::FLUPPS, m_DoseUnit.m_PPS->JSGet()); }; auto HWFLX = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (nValue == 0) { HWSend("FLX0"); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_FLU_XRAYOFF)) { mLog::FINFO("Generator exposure process status{$};", "GENERATOR_FLU_XRAYOFF"); FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); } } else { HWSend("FLX1"); if (m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_EXP)) FireNotify(AttrKey::GENSTATE, m_DoseUnit.m_GenState->JSGet()); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_FLU_XRAYON)) { mLog::FINFO("Generator exposure process status{$};", "GENERATOR_FLU_XRAYON"); FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); } } }; auto HWFLP = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (nValue == 0) { if (m_iLoopTime == HaoWei_LoopExpTime) { if ((int)m_GenConfig["loopTime"] >= 100) { m_iLoopTime = (int)m_GenConfig["loopTime"]; } else m_iLoopTime = HaoWei_LoopDefTime; mLog::FINFO("reduction loopTime[{$}]->[{$}]", HaoWei_LoopExpTime, m_iLoopTime.load()); } HWSend("FLP0"); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_FLU_OFF)) { mLog::FINFO("脚闸抬起,发生器曝光流程状态{$};", "GENERATOR_FLU_OFF"); FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); } RefreshData(); } else { m_iLoopTime = HaoWei_LoopExpTime; HWSend("FLP1"); if (m_DoseUnit.m_GenSynState->Update(AttrKey::GENERATOR_FLU_READY)) { mLog::FINFO("Generator exposure process status{$};", "GENERATOR_FLU_READY"); FireNotify(m_DoseUnit.m_GenSynState->GetKey(), m_DoseUnit.m_GenSynState->JSGet()); } } }; auto HWFLF = [this](const char* value, int length) { assert(value); mLog::FINFO("HWFLF={$};", value); int tmpflf = atoi(value); if (m_DoseUnit.m_FLMode->Update(tmpflf)) FireNotify(AttrKey::FLUMode, m_DoseUnit.m_FLMode->JSGet()); }; auto HWFLA = [this](const char* value, int length) { assert(value); int tmpfla = atoi(value); if (m_DoseUnit.m_ABSStatus->Update(tmpfla)) FireNotify(AttrKey::FLUABSStatus, m_DoseUnit.m_ABSStatus->JSGet()); }; auto HWFLD = [this](const char* value, int length) { assert(value); }; auto HWFLC = [this](const char* value, int length) { assert(value); }; auto HWFLO = [this](const char* value, int length) { assert(value); int nValue = atoi(value); if (m_DoseUnit.m_Curve->Update(nValue)) FireNotify(AttrKey::FLUCurve, m_DoseUnit.m_Curve->JSGet()); }; auto HWFLW = [this](const char* value, int length) { assert(value);; float tmpflms = atof(value) / 100.0; if (m_DoseUnit.m_FLMS->Update(tmpflms)) FireNotify(AttrKey::FLUMS, m_DoseUnit.m_FLMS->JSGet()); }; auto HWFLI = [this](const char* value, int length) { assert(value); float tmpfli = atof(value) / 10.0; if (m_DoseUnit.m_FLIntTime->Update(tmpfli)) FireNotify(AttrKey::FLUIntTime, m_DoseUnit.m_FLIntTime->JSGet()); }; auto HWFLT = [this](const char* value, int length) { assert(value); float tmpflt = atof(value); if (m_DoseUnit.m_FLAccTime->Update(tmpflt)) FireNotify(AttrKey::FLUAccTime, m_DoseUnit.m_FLAccTime->JSGet()); }; // 有部分前缀是包含关系, 长的包含短的, 例如 KVS 包含了 KV. // 因此长的在前面, 短的在后面 // !!! Device 是个短寿命对象, 而 arFrame 是静态变量 !!! // !!! 因此, 在添加到 arFrame 之前, 务必先清零 !!! arFrame.clear(); arFrame.push_back(tFrameMapping("KV", 2, HWKV)); arFrame.push_back(tFrameMapping("TU", 2, HWTU)); arFrame.push_back(tFrameMapping("MX", 2, HWMAS)); arFrame.push_back(tFrameMapping("MA", 2, HWMA)); arFrame.push_back(tFrameMapping("MS", 2, HWMS)); arFrame.push_back(tFrameMapping("TE", 2, HWTechmode)); arFrame.push_back(tFrameMapping("FO", 2, HWFocus)); arFrame.push_back(tFrameMapping("FI", 2, HWAECField)); arFrame.push_back(tFrameMapping("FS", 2, HWAECFilm)); arFrame.push_back(tFrameMapping("FN", 2, HWAECDensity)); arFrame.push_back(tFrameMapping("WS", 2, HWWS)); arFrame.push_back(tFrameMapping("PR", 2, HWPR)); arFrame.push_back(tFrameMapping("XR", 2, HWXR)); arFrame.push_back(tFrameMapping("VP", 2, HWVPDOSE)); arFrame.push_back(tFrameMapping("AP", 2, HWAPDOSE)); arFrame.push_back(tFrameMapping("AT", 2, HWATDOSE)); arFrame.push_back(tFrameMapping("ER", 2, HWER)); arFrame.push_back(tFrameMapping("HE", 2, HWEHE)); arFrame.push_back(tFrameMapping("ST", 2, HWST)); arFrame.push_back(tFrameMapping("EC", 2, HWEC)); arFrame.push_back(tFrameMapping("GR", 2, HWGR)); arFrame.push_back(tFrameMapping("GV", 2, HWGV)); arFrame.push_back(tFrameMapping("GU", 2, HWGU)); arFrame.push_back(tFrameMapping("TR", 2, HWTR)); arFrame.push_back(tFrameMapping("DS", 2, HWDAPST)); //dap status arFrame.push_back(tFrameMapping("DA", 2, HWDAP)); //dap value arFrame.push_back(tFrameMapping("DT", 2, HWDT)); //test dap arFrame.push_back(tFrameMapping("WAR", 3, HWWAR)); arFrame.push_back(tFrameMapping("FKV", 3, HWFKV)); arFrame.push_back(tFrameMapping("FMA", 3, HWFMA)); arFrame.push_back(tFrameMapping("FLS", 3, HWFLS)); arFrame.push_back(tFrameMapping("FLF", 3, HWFLF)); arFrame.push_back(tFrameMapping("FLP", 3, HWFLP)); arFrame.push_back(tFrameMapping("FLX", 3, HWFLX)); arFrame.push_back(tFrameMapping("FLW", 3, HWFLW)); arFrame.push_back(tFrameMapping("FLI", 3, HWFLI)); arFrame.push_back(tFrameMapping("FTS", 3, HWFLT)); arFrame.push_back(tFrameMapping("FLA", 3, HWFLA)); arFrame.push_back(tFrameMapping("FLD", 3, HWFLD)); arFrame.push_back(tFrameMapping("FLC", 3, HWFLD)); arFrame.push_back(tFrameMapping("FLO", 3, HWFLO)); } bool nsGEN::HaoWeiDevice::StartHardwareStatusThread() { mLog::FINFO("enter Start HardwareStatus Thread "); if (m_pHardwareStatusThread == NULL) { DWORD m_HardwareStatusID; m_pHardwareStatusThread = CreateThread(0, 0, HardwareStatusThread, this, 0, &m_HardwareStatusID); if (m_pHardwareStatusThread == NULL) { mLog::Fatal("Start HardwareStatus Thread Failed"); return false; } } return true; } DWORD nsGEN::HaoWeiDevice::HardwareStatusThread(LPVOID pParam) { HaoWeiDevice* pCurGen = (HaoWeiDevice*)pParam; if (pCurGen == NULL) { return false; } mLog::FINFO("loopTime = {$}", pCurGen->m_iLoopTime.load()); int currtTime = pCurGen->m_iLoopTime; mLog::FINFO("HardwareStatusThread start"); while (true) { auto now = std::chrono::steady_clock::now(); auto last = lastValidResponse.load(); if (now - last > TIMEOUT && pCurGen->m_DoseUnit.m_GenState->Get() > 0) { mLog::FINFO("The timeout did not respond"); pCurGen->m_DoseUnit.m_GenState->Update(nsGEN::AttrKey::GENERATOR_STATUS_SHUTDOWN); // 超时未响应则重置状态 } currtTime = pCurGen->m_iLoopTime; Sleep(currtTime); //获取消息 //pCurGen->HWSend("ST?"); } mLog::FINFO("HardwareStatusThread stop"); return true; } //----------------------------------------------------------------------------- // HaoWeiDriver //----------------------------------------------------------------------------- nsGEN::HaoWeiDriver::HaoWeiDriver() { } nsGEN::HaoWeiDriver::~HaoWeiDriver() { } auto nsGEN::HaoWeiDriver::CreateDevice(int index) -> std::unique_ptr { mLog::FINFO("CreateDevice in\n"); m_pDevice = new HaoWeiDevice(EventCenter, m_SCF, m_ConfigFileName); auto dev = std::unique_ptr (new IODevice(m_pDevice)); mLog::FINFO("CreateDevice out\n"); return dev; } void nsGEN::HaoWeiDriver::FireNotify(int code, std::string key, std::string content) { EventCenter->OnNotify(code, key, content); } Log4CPP::Logger* mLog::gLogger = nullptr; void nsGEN::HaoWeiDriver::Prepare() { mLog::FINFO("Enter Prepare."); string strLogPath = GetProcessDirectory() + R"(\OEMDrivers\Generator\Conf\Log4CPP.Config.GEN.xml)"; Log4CPP::GlobalContext::Map::Set(ECOM::Utility::Hash("LogFileName"), "GEN.HaoWei"); auto rc = Log4CPP::LogManager::LoadConfigFile(strLogPath.c_str()); mLog::gLogger = Log4CPP::LogManager::GetLogger("GEN.HaoWei"); m_SCFDllName = GetConnectDLL(m_ConfigFileName); super::Prepare(); } bool DATA_ACTION nsGEN::HaoWeiDriver::Connect() { mLog::FINFO("Enter {$},configlef={$}\n", __FUNCTION__, m_ConfigFileName.c_str()); ResDataObject Connection = GetConnectParam(m_ConfigFileName); mLog::FINFO("connections:{$} \n", Connection.encode()); auto erCode = m_SCF.Connect(Connection.encode(), &nsGEN::HaoWeiDriver::callbackPackageProcess, SCF_PACKET_TRANSFER, 3000); if (erCode != SCF_ERR::SCF_SUCCEED) { mLog::FINFO("SCF connection failed: erCode != SCF_ERR::SCF_SUCCEED\n"); return false; } auto rc = super::Connect(); if (!rc) { mLog::FINFO("super::Connect() failed\n"); return false; } return true; } void nsGEN::HaoWeiDriver::Disconnect() { super::Disconnect(); m_SCF.Disconnect(); } bool nsGEN::HaoWeiDriver::isConnected() const { if (!super::isConnected()) { mLog::FINFO("No valid connection!!!\n"); return false; } //if (m_pDevice == nullptr) //{ // mLog::FINFO("m_pDevice == nullptr\n"); // return false; //} //if (m_pDevice->LoadConfig(m_ConfigFileName) == -1) //{ // return false; //return 0; //} //int genState = m_pDevice->GetGenState(); //mLog::FINFO("m_pDevice->GetGenState() == {$}\n", genState); //return genState > 0; // 只有返回值大于 0 时才返回 true return true; } std::string nsGEN::HaoWeiDriver::DriverProbe() { mLog::FINFO("DriverProbe in \n"); ResDataObject r_config, HardwareInfo; if (r_config.loadFile(m_ConfigFileName.c_str())) { HardwareInfo.add("MajorID", r_config["CONFIGURATION"]["MajorID"]); HardwareInfo.add("MinorID", r_config["CONFIGURATION"]["MinorID"]); HardwareInfo.add("VendorID", r_config["CONFIGURATION"]["VendorID"]); HardwareInfo.add("ProductID", r_config["CONFIGURATION"]["ProductID"]); HardwareInfo.add("SerialID", r_config["CONFIGURATION"]["SerialID"]); } else { HardwareInfo.add("MajorID", "Generator"); HardwareInfo.add("MinorID", "Dr"); HardwareInfo.add("VendorID", "HaoWei"); HardwareInfo.add("ProductID", "HF"); HardwareInfo.add("SerialID", "Drv"); } string ret = HardwareInfo.encode(); mLog::FINFO("DriverProbe out \n"); return ret; } std::string nsGEN::HaoWeiDriver::GetResource() { ResDataObject temp; if (!temp.loadFile(m_ConfigFileName.c_str())) return std::string(); auto r_config = temp["CONFIGURATION"]; for (auto& Item : m_ConfigInfo) { string key = Item.GetKey(); if (key == ConfKey::CcosGeneratorType) { Item.SetCurrentValue(((string)r_config["VendorID"]).c_str()); } else if (key == ConfKey::CcosGeneratorModel) { Item.SetCurrentValue(((string)r_config["ProductID"]).c_str()); } else if (key == ConfKey::CcosWSTable || key == ConfKey::CcosWSWall || key == ConfKey::CcosWSFree || key == ConfKey::CcosWSTomo || key == ConfKey::CcosWSConventional) { Item.SetCurrentValue(((string)r_config[key.c_str()]).c_str()); } else if (key == ConfKey::CcosSynTable || key == ConfKey::CcosSynWall || key == ConfKey::CcosSynFree || key == ConfKey::CcosSynTomo || key == ConfKey::CcosSynConventional) { Item.SetCurrentValue(((string)r_config[key.c_str()]).c_str()); } else if (key == ConfKey::CcosSCFType) { Item.SetCurrentValue(((string)r_config["connections"][0]["type"]).c_str()); } else if (key == ConfKey::CcosSCFPort || key == ConfKey::CcosSCFBaudrate || key == ConfKey::CcosSCFBytesize || key == ConfKey::CcosSCFParity || key == ConfKey::CcosSCFStopbits || key == ConfKey::CcosSCFIP) { if (r_config["connections"][0].GetFirstOf(key.c_str()) >= 0) { Item.SetCurrentValue(((string)r_config["connections"][0][key.c_str()]).c_str()); } } } ResDataObject resAttr, resDescription; for (auto Item : m_ConfigInfo) { resAttr.add(Item.GetKey(), Item.GetCurrentValue()); resDescription.add(Item.GetKey(), Item.GetDescription()); } ResDataObject resDeviceResource; resDeviceResource.add(ConfKey::CcosGeneratorAttribute, resAttr); resDeviceResource.add(ConfKey::CcosGeneratorDescription, resDescription); string res = resDeviceResource.encode(); //printf("resDeviceResource :%s \n", resDeviceResource.encode()); //mLog::FINFO("resDeviceResource :{$} \n", resDeviceResource.encode()); ResDataObject DescriptionTempEx; DescriptionTempEx.add(ConfKey::CcosGeneratorConfig, resDeviceResource); m_DeviceConfig.clear(); m_DeviceConfig = DescriptionTempEx; return res; } bool nsGEN::HaoWeiDriver::GetDeviceConfig(std::string& Cfg) { //Cfg = m_DeviceConfigSend.encode(); Cfg = m_DeviceConfig.encode(); //printf("GetDeviceConfig over"); printf("GetDeviceConfig over , %s", Cfg.c_str()); return true; } bool nsGEN::HaoWeiDriver::SetDeviceConfig(std::string Cfg) { mLog::FINFO("--Func-- SetDeviceConfig {$}\n", Cfg.c_str()); return true; } bool nsGEN::HaoWeiDriver::SaveConfigFile(bool bSendNotify) { m_ConfigAll["CONFIGURATION"] = m_Configurations; bool bRt = m_ConfigAll.SaveFile(m_ConfigFileName.c_str()); mLog::FINFO("SaveConfigFile over {$}", bRt); return true; } std::string nsGEN::HaoWeiDriver::DeviceProbe() { mLog::FINFO("std::string nsGEN::PSGRFDriver::DeviceProbe() in\n"); ResDataObject r_config, HardwareInfo; if (r_config.loadFile(m_ConfigFileName.c_str())) { HardwareInfo.add("MajorID", r_config["CONFIGURATION"]["MajorID"]); HardwareInfo.add("MinorID", r_config["CONFIGURATION"]["MinorID"]); HardwareInfo.add("VendorID", r_config["CONFIGURATION"]["VendorID"]); HardwareInfo.add("ProductID", r_config["CONFIGURATION"]["ProductID"]); HardwareInfo.add("SerialID", r_config["CONFIGURATION"]["SerialID"]); } else { HardwareInfo.add("MajorID", "Generator"); HardwareInfo.add("MinorID", "Dr"); HardwareInfo.add("VendorID", "HaoWei"); HardwareInfo.add("ProductID", "HF"); HardwareInfo.add("SerialID", "1234"); } string ret = HardwareInfo.encode(); mLog::FINFO("std::string nsGEN::PSGRFDriver::DeviceProbe() out\n"); return ret; } void nsGEN::HaoWeiDriver::Dequeue(const char* Packet, DWORD Length) { DecodeFrame(Packet, Length); } /* ==IN==:KV070 MA00320 MS00063 MX00036 ==IN==:TU0 WS1 FO0 ET0 FI010 FS001 FN 0 HE000 how to split the str like up. //command+03+sum */ PACKET_RET nsGEN::HaoWeiDriver::callbackPackageProcess(const char* RecData, DWORD nLength, DWORD& PacketLength) { //mLog::FINFO("==IN==11:[{:02X$}]\n", RecData); if (nLength < 1) // 最小有效包为0x03 + checksum + 0x00(3字节) { return PACKET_USELESS; } for (DWORD i = 0; i < nLength; ++i) // 遍历所有字节 { if (RecData[i] == 0x00) { if (i < 2) { // 至少需要0x03、校验和和结束符 return PACKET_USELESS; } size_t markerPos = i - 2; if (RecData[markerPos] != 0x03) { // 检查0x03标识符 // 不是有效的起始符,继续查找下一个结束符 continue; } //BYTE calcSum = 0; //for (size_t j = 0; j <= markerPos; ++j) { // calcSum += RecData[j]; //} //BYTE recvSum = RecData[i - 1]; //if (calcSum != recvSum) { // // 校验失败,继续查找后续可能的包 // continue; //} PacketLength = static_cast(i - 2); //应该+2.才会把最后的checmsum也包含进来。FO1+03+sum. char strtemp[100] = { 0 }; memcpy(strtemp, RecData, i); strtemp[i + 1] = 0; //mLog::FINFO("==IN==:{:02x$}\n", strtemp); return PACKET_ISPACKET; } } return PACKET_NOPACKET; } //----------------------------------------------------------------------------- // DecodeFrame //----------------------------------------------------------------------------- static bool DecodeFrame(const char* strFrame, int length) { mLog::FINFO("==IN==:{:02x$}\n", strFrame); auto pr = [strFrame, length](const tFrameMapping& Item) { for (int i = 0; i < Item.NbOfCharOfHead; i++) { if (strFrame[i] != Item.strHead[i]) { return false; } } return true; }; auto found = std::find_if(arFrame.begin(), arFrame.end(), pr); if (found == arFrame.end()) { return false; } lastValidResponse.store(std::chrono::steady_clock::now()); const auto& Item = *found; auto pc = strFrame; pc += Item.NbOfCharOfHead; Item.fun(pc, length - Item.NbOfCharOfHead); return true; } //----------------------------------------------------------------------------- // GetIODriver & CreateIODriver //----------------------------------------------------------------------------- static nsGEN::HaoWeiDriver gIODriver; extern "C" CCOS::Dev::IODriver * __cdecl GetIODriver() // 返回静态对象的引用, 调用者不能删除 ! { return &gIODriver; } extern "C" CCOS::Dev::IODriver * __cdecl CreateIODriver() // 返回新对象, 调用者必须自行删除此对象 ! { return new nsGEN::HaoWeiDriver(); }