5 changed files with 426 additions and 47 deletions
-
61.vscode/settings.json
-
2dep/iflytopcpp
-
2sh/envsetup.sh
-
277src/service/device_io_service.cpp
-
131src/service/device_io_service.hpp
@ -1 +1 @@ |
|||
Subproject commit 2d2ac28f73d5a14aba4501831c1c52468b726a10 |
|||
Subproject commit 574b15ad972bcaae593cfc434f9f60e6d6a13ca8 |
@ -1,4 +1,281 @@ |
|||
#include "device_io_service.hpp"
|
|||
|
|||
#include "iflytopcpp/core/components/string_util.hpp"
|
|||
#include "iflytopcpp/core/components/time_util.hpp"
|
|||
#include "iflytopcpp/core/zexception/zexception.hpp"
|
|||
using namespace iflytop; |
|||
using namespace core; |
|||
using namespace std; |
|||
|
|||
const static int ksubboarddeviceid = 0x01; |
|||
const int kovertime = 33; |
|||
|
|||
#define EXEC_MODBUS(exptr) \
|
|||
int ret = exptr; \ |
|||
if (ret != 0) { \ |
|||
throw zexception( \ |
|||
fmt::format("[{}:{}] do {} fail, ret={},{}", __FUNCTION__, __LINE__, exptr, ret, modbusStatusToStr(ret))); \ |
|||
} |
|||
|
|||
void DeviceIOService::initialize() { |
|||
modbusMaster = shared_ptr<ModbusMaster>(new ModbusMaster()); |
|||
bool suc = modbusMaster->initializeTtyChannel("/dev/ttyUSB0", 115200); |
|||
if (!suc) { |
|||
logger->error("modbusMaster initializeTtyChannel fail"); |
|||
} |
|||
|
|||
thread.reset(new Thread("input_device_state_monitor", [this]() { inputStateMonitorLoop(); })); |
|||
|
|||
idcard_read_thread.reset(new Thread("idcard_read", [this]() { |
|||
ThisThread thisThread; |
|||
while (!thisThread.getExitFlag()) { |
|||
try { |
|||
bool state; |
|||
string info; |
|||
|
|||
idcardread(state, info); |
|||
if (state) { |
|||
logger->info("idcard read info:{}", info); |
|||
onidcard(info); |
|||
} |
|||
|
|||
} catch (zexception& e) { |
|||
static tp_steady lastlogticket; |
|||
if (tu_steady().elapsedTimeS(lastlogticket) > 5) { |
|||
logger->error("idcard read fail:{}", e.what()); |
|||
lastlogticket = tu_steady().now(); |
|||
} |
|||
} |
|||
thisThread.sleepForMs(100); |
|||
} |
|||
})); |
|||
} |
|||
void DeviceIOService::relayControl(uint16_t off, bool value) { |
|||
/**
|
|||
* @brief |
|||
* 0(16Byte) | 继电器0 ->继电器15 掩码 |
|||
* 1(16Byte) | 继电器16->继电器31 掩码 |
|||
* 2(16Byte) | 继电器0 ->继电器15 继电器状态 |
|||
* 3(16Byte) | 继电器16->继电器31 继电器状态 |
|||
*/ |
|||
uint32_t mask = 1 << off; |
|||
uint32_t status = value ? mask : 0; |
|||
|
|||
uint16_t reg[4]; |
|||
MODBUS_SET_REG(reg[0], uint16_t(mask)); |
|||
MODBUS_SET_REG(reg[1], uint16_t(mask >> 16)); |
|||
MODBUS_SET_REG(reg[2], uint16_t(status)); |
|||
MODBUS_SET_REG(reg[3], uint16_t(status >> 16)); |
|||
|
|||
EXEC_MODBUS(modbusMaster->modbus10(ksubboarddeviceid, 0, 4, reg, kovertime)); |
|||
} |
|||
bool DeviceIOService::relayStateGet(uint16_t off) { |
|||
/**
|
|||
* @brief |
|||
* 0(16Byte) | 继电器0 ->继电器15 掩码 |
|||
* 1(16Byte) | 继电器16->继电器31 掩码 |
|||
* 2(16Byte) | 继电器0 ->继电器15 继电器状态 |
|||
* 3(16Byte) | 继电器16->继电器31 继电器状态 |
|||
*/ |
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 2, 2, modbus03rx, kovertime)); |
|||
uint32_t regstate = uint32_t(modbus03rx.getReg(2)) | uint32_t(modbus03rx.getReg(3) << 16); |
|||
return (regstate & (1 << off)) != 0; |
|||
} |
|||
|
|||
uint16_t DeviceIOService::getReg(int index) { |
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, index, 1, modbus03rx, kovertime)); |
|||
return modbus03rx.getReg(index); |
|||
} |
|||
|
|||
/***********************************************************************************************************************
|
|||
* ==================================================路由器电源控制=================================================== * |
|||
***********************************************************************************************************************/ |
|||
bool DeviceIOService::routerGetPowerState() { return relayStateGet(0); } |
|||
void DeviceIOService::routerSetPowerState(bool routepower) { |
|||
logger->debug("routerSetPowerState {}", routepower); |
|||
relayControl(0, true); |
|||
} |
|||
|
|||
/***********************************************************************************************************************
|
|||
* ==================================================触控屏供电控制=================================================== * |
|||
***********************************************************************************************************************/ |
|||
bool DeviceIOService::touchScreenGetPowerState() { return relayStateGet(1); } |
|||
void DeviceIOService::touchScreenSetPowerState(bool touchpower) { |
|||
logger->debug("touchScreenSetPowerState {}", touchpower); |
|||
relayControl(1, touchpower); |
|||
} |
|||
|
|||
/***********************************************************************************************************************
|
|||
* ==================================================USB充电器供电=================================================== * |
|||
***********************************************************************************************************************/ |
|||
bool DeviceIOService::usbChargerGetPowerState() { return relayStateGet(2); } |
|||
void DeviceIOService::usbChargerSetPowerState(bool usbpower) { |
|||
logger->debug("usbChargerSetPowerState {}", usbpower); |
|||
relayControl(2, usbpower); |
|||
} |
|||
|
|||
/***********************************************************************************************************************
|
|||
* ==================================================摄像头供电=================================================== * |
|||
***********************************************************************************************************************/ |
|||
bool DeviceIOService::cameraGetPowerState() { return relayStateGet(3); } |
|||
void DeviceIOService::cameraSetPowerState(bool camerapower) { |
|||
logger->debug("cameraSetPowerState {}", camerapower); |
|||
relayControl(3, camerapower); |
|||
} |
|||
|
|||
/***********************************************************************************************************************
|
|||
* ==================================================照明控制=================================================== * |
|||
***********************************************************************************************************************/ |
|||
bool DeviceIOService::lightGetPowerState() { return relayStateGet(4); } |
|||
void DeviceIOService::lightSetPowerState(bool lightpower) { |
|||
logger->debug("lightSetPowerState {}", lightpower); |
|||
relayControl(4, lightpower); |
|||
} |
|||
|
|||
uint32_t DeviceIOService::getinputState() { |
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 4, 2, modbus03rx, kovertime)); |
|||
uint32_t regstate = uint32_t(modbus03rx.getReg(4)) | uint32_t(modbus03rx.getReg(5) << 16); |
|||
return regstate; |
|||
} |
|||
|
|||
void DeviceIOService::inputStateMonitorLoop() { |
|||
ThisThread thisThread; |
|||
while (!thisThread.getExitFlag()) { |
|||
uint32_t regstate = 0; |
|||
try { |
|||
regstate = getinputState(); |
|||
for (size_t i = 0; i < 32; i++) { |
|||
bool state = (regstate & (1 << i)) != 0; |
|||
bool oldstate = (keystate & (1 << i)) != 0; |
|||
if (state != oldstate) { |
|||
logger->info("on {} state change, state={}", input_device_type2str(input_device_type_t(i)), state); |
|||
onInputStateChange((input_device_type_t)i, state); |
|||
} |
|||
} |
|||
} catch (const std::exception& e) { |
|||
/**
|
|||
* @brief 如果出现异常,则每隔5秒打印一次日志 |
|||
*/ |
|||
static tp_steady lastlogticket; |
|||
if (tu_steady().elapsedTimeS(lastlogticket) > 5) { |
|||
logger->error("inputStateMonitorLoop fail, {}", e.what()); |
|||
lastlogticket = tu_steady().now(); |
|||
} |
|||
} |
|||
thisThread.sleepForMs(50); |
|||
} |
|||
} |
|||
|
|||
uint32_t DeviceIOService::getInterTemperature() { return getReg(16); } |
|||
|
|||
DeviceIOService::env_sensor_state_t DeviceIOService::getEnvSensorState() { |
|||
Modbus03Rx modbus03rx; |
|||
env_sensor_state_t env_sensor_state = {0}; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 48, 11, modbus03rx, kovertime)); |
|||
/**
|
|||
48(16Byte) | 风速 |
|||
49(16Byte) | 风向 |
|||
50(16Byte) | temperature 实际湿度值=temperature/10 ℃ |
|||
51(16Byte) | humidity 实际湿度值=humidity/10 (0->100%) |
|||
52(16Byte) | 噪声 |
|||
53(16Byte) | pm2.5 ug/m³ |
|||
54(16Byte) | pm10 ug/m³ |
|||
55(16Byte) | co2 PPM |
|||
56(16Byte) | 大气压力 PPM |
|||
57(16Byte) | tvoc ppm |
|||
58(16Byte) | hcho mg/m3 |
|||
*/ |
|||
env_sensor_state.wind_speed = modbus03rx.getReg(48); |
|||
env_sensor_state.wind_direction = modbus03rx.getReg(49); |
|||
env_sensor_state.temperature = modbus03rx.getReg(50); |
|||
env_sensor_state.humidity = modbus03rx.getReg(51); |
|||
env_sensor_state.noise = modbus03rx.getReg(52); |
|||
env_sensor_state.pm2_5 = modbus03rx.getReg(53); |
|||
env_sensor_state.pm10 = modbus03rx.getReg(54); |
|||
env_sensor_state.co2 = modbus03rx.getReg(55); |
|||
env_sensor_state.atmospheric_pressure = modbus03rx.getReg(56); |
|||
env_sensor_state.tvoc = modbus03rx.getReg(57); |
|||
env_sensor_state.hcho = modbus03rx.getReg(58); |
|||
logger->debug( |
|||
"getEnvSensorState, " |
|||
"wind_speed={},wind_direction={},temperature={},humidity={},noise={},pm2_5={},pm10={},co2={},atmospheric_" |
|||
"pressure={},tvoc={},hcho={}", |
|||
env_sensor_state.wind_speed, env_sensor_state.wind_direction, env_sensor_state.temperature, |
|||
env_sensor_state.humidity, env_sensor_state.noise, env_sensor_state.pm2_5, env_sensor_state.pm10, |
|||
env_sensor_state.co2, env_sensor_state.atmospheric_pressure, env_sensor_state.tvoc, env_sensor_state.hcho); |
|||
return env_sensor_state; |
|||
} |
|||
|
|||
void DeviceIOService::fanGetState(int id, float& power, uint16_t& error) { |
|||
int startindex = 0; |
|||
if (id == 0) { |
|||
startindex = 128; |
|||
} else if (id == 1) { |
|||
startindex = 136; |
|||
} else { |
|||
power = 0; |
|||
error = 0; |
|||
logger->error("fanGetState fail, id={},id is illegal", id); |
|||
} |
|||
|
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, startindex, 2, modbus03rx, kovertime)); |
|||
power = modbus03rx.getReg(startindex); |
|||
error = modbus03rx.getReg(startindex + 1); |
|||
logger->debug("fanGetState, id={},power={},error={}", id, power, error); |
|||
return; |
|||
} |
|||
void DeviceIOService::fanSetState(int id, float power) { |
|||
logger->debug("fanSetState, id={},power={}", id, power); |
|||
int startindex = 0; |
|||
if (id == 0) { |
|||
startindex = 128; |
|||
} else if (id == 1) { |
|||
startindex = 136; |
|||
} else { |
|||
logger->error("fanGetState fail, id={},id is illegal", id); |
|||
return; |
|||
} |
|||
|
|||
uint16_t reg[1]; |
|||
MODBUS_SET_REG(reg[0], uint16_t(power)); |
|||
EXEC_MODBUS(modbusMaster->modbus10(ksubboarddeviceid, startindex, 1, reg, kovertime)); |
|||
return; |
|||
} |
|||
|
|||
void DeviceIOService::idcardread(bool& state, string& info) { |
|||
/**
|
|||
* 64->127 | 读卡器透传,03时读取消息,10写消息 |
|||
* 64(16Byte) | 是否有新卡信息 |
|||
* 65(16Byte) | 卡的内容 |
|||
* 65(16Byte) | |
|||
* ..(16Byte) | |
|||
* 127(16Byte) | |
|||
*/ |
|||
state = false; |
|||
info = ""; |
|||
int datalen = 0; |
|||
{ |
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 64, 1, modbus03rx, kovertime)); |
|||
datalen = modbus03rx.getReg(64); |
|||
} |
|||
if (datalen == 0) { |
|||
logger->debug("idcardread, state={},info={}", state, info); |
|||
return; |
|||
} |
|||
|
|||
int readreg = datalen / 2 + datalen % 2 != 0 ? 1 : 0; |
|||
|
|||
{ |
|||
Modbus03Rx modbus03rx; |
|||
EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 65, readreg, modbus03rx, kovertime)); |
|||
info = StringUtil().bytesToString(modbus03rx.getRegBegin(), datalen); |
|||
} |
|||
state = true; |
|||
logger->debug("idcardread, state={},info={}", state, info); |
|||
return; |
|||
} |
Write
Preview
Loading…
Cancel
Save
Reference in new issue