You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

297 lines
12 KiB

3 years ago
3 years ago
  1. #include "device_io_service.hpp"
  2. #include "iflytopcpp/core/components/string_util.hpp"
  3. #include "iflytopcpp/core/components/time_util.hpp"
  4. #include "iflytopcpp/core/zexception/zexception.hpp"
  5. using namespace iflytop;
  6. using namespace core;
  7. using namespace std;
  8. const static int ksubboarddeviceid = 0x01;
  9. const int kovertime = 33;
  10. #define EXEC_MODBUS(exptr) \
  11. int ret = exptr; \
  12. if (ret != 0) { \
  13. throw zexception( \
  14. fmt::format("[{}:{}] do {} fail, ret={},{}", __FUNCTION__, __LINE__, exptr, ret, modbusStatusToStr(ret))); \
  15. }
  16. void DeviceIOService::initialize() {
  17. modbusMaster = shared_ptr<ModbusMaster>(new ModbusMaster());
  18. bool suc = modbusMaster->initializeTtyChannel("/dev/ttyUSB0", 115200);
  19. if (!suc) {
  20. logger->error("modbusMaster initializeTtyChannel fail");
  21. }
  22. thread.reset(new Thread("input_device_state_monitor", [this]() { inputStateMonitorLoop(); }));
  23. idcard_read_thread.reset(new Thread("idcard_read", [this]() {
  24. ThisThread thisThread;
  25. while (!thisThread.getExitFlag()) {
  26. try {
  27. bool state;
  28. string info;
  29. idcardread(state, info);
  30. if (state) {
  31. logger->info("idcard read info:{}", info);
  32. onidcard(info);
  33. }
  34. } catch (zexception& e) {
  35. static tp_steady lastlogticket;
  36. if (tu_steady().elapsedTimeS(lastlogticket) > 5) {
  37. logger->error("idcard read fail:{}", e.what());
  38. lastlogticket = tu_steady().now();
  39. }
  40. }
  41. thisThread.sleepForMs(100);
  42. }
  43. }));
  44. }
  45. void DeviceIOService::relayControl(relay_device_type_t type, bool value) {
  46. /**
  47. * @brief
  48. * 0(16Byte) | 0 ->15
  49. * 1(16Byte) | 16->31
  50. * 2(16Byte) | 0 ->15
  51. * 3(16Byte) | 16->31
  52. */
  53. uint32_t off = (uint32_t)type;
  54. uint32_t mask = 1 << off;
  55. uint32_t status = value ? mask : 0;
  56. uint16_t reg[4];
  57. MODBUS_SET_REG(reg[0], uint16_t(mask));
  58. MODBUS_SET_REG(reg[1], uint16_t(mask >> 16));
  59. MODBUS_SET_REG(reg[2], uint16_t(status));
  60. MODBUS_SET_REG(reg[3], uint16_t(status >> 16));
  61. EXEC_MODBUS(modbusMaster->modbus10(ksubboarddeviceid, 0, 4, reg, kovertime));
  62. }
  63. DeviceIOService::RelayDeviceState DeviceIOService::relayStateGet() {
  64. /**
  65. * @brief
  66. * 0(16Byte) | 0 ->15
  67. * 1(16Byte) | 16->31
  68. * 2(16Byte) | 0 ->15
  69. * 3(16Byte) | 16->31
  70. */
  71. DeviceIOService::RelayDeviceState state = {};
  72. Modbus03Rx modbus03rx;
  73. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 2, 2, modbus03rx, kovertime));
  74. uint32_t regstate = uint32_t(modbus03rx.getReg(2)) | uint32_t(modbus03rx.getReg(3) << 16);
  75. state.state = regstate;
  76. return state;
  77. }
  78. uint16_t DeviceIOService::getReg(int index) {
  79. Modbus03Rx modbus03rx;
  80. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, index, 1, modbus03rx, kovertime));
  81. return modbus03rx.getReg(index);
  82. }
  83. #if 0
  84. /***********************************************************************************************************************
  85. * ===================================================================================================== *
  86. ***********************************************************************************************************************/
  87. bool DeviceIOService::routerGetPowerState() { return relayStateGet(0); }
  88. void DeviceIOService::routerSetPowerState(bool routepower) {
  89. logger->debug("routerSetPowerState {}", routepower);
  90. relayControl(0, true);
  91. }
  92. /***********************************************************************************************************************
  93. * ===================================================================================================== *
  94. ***********************************************************************************************************************/
  95. bool DeviceIOService::touchScreenGetPowerState() { return relayStateGet(1); }
  96. void DeviceIOService::touchScreenSetPowerState(bool touchpower) {
  97. logger->debug("touchScreenSetPowerState {}", touchpower);
  98. relayControl(1, touchpower);
  99. }
  100. /***********************************************************************************************************************
  101. * ==================================================USB充电器供电=================================================== *
  102. ***********************************************************************************************************************/
  103. bool DeviceIOService::usbChargerGetPowerState() { return relayStateGet(2); }
  104. void DeviceIOService::usbChargerSetPowerState(bool usbpower) {
  105. logger->debug("usbChargerSetPowerState {}", usbpower);
  106. relayControl(2, usbpower);
  107. }
  108. /***********************************************************************************************************************
  109. * ===================================================================================================== *
  110. ***********************************************************************************************************************/
  111. bool DeviceIOService::cameraGetPowerState() { return relayStateGet(3); }
  112. void DeviceIOService::cameraSetPowerState(bool camerapower) {
  113. logger->debug("cameraSetPowerState {}", camerapower);
  114. relayControl(3, camerapower);
  115. }
  116. /***********************************************************************************************************************
  117. * ===================================================================================================== *
  118. ***********************************************************************************************************************/
  119. bool DeviceIOService::lightGetPowerState() { return relayStateGet(4); }
  120. void DeviceIOService::lightSetPowerState(bool lightpower) {
  121. logger->debug("lightSetPowerState {}", lightpower);
  122. relayControl(4, lightpower);
  123. }
  124. #endif
  125. DeviceIOService::InputDeviceState DeviceIOService::getinputState() {
  126. DeviceIOService::InputDeviceState inputDeviceState;
  127. Modbus03Rx modbus03rx;
  128. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 4, 2, modbus03rx, kovertime));
  129. uint32_t regstate = uint32_t(modbus03rx.getReg(4)) | uint32_t(modbus03rx.getReg(5) << 16);
  130. inputDeviceState.state = regstate;
  131. return inputDeviceState;
  132. }
  133. void DeviceIOService::inputStateMonitorLoop() {
  134. ThisThread thisThread;
  135. while (!thisThread.getExitFlag()) {
  136. try {
  137. uint32_t regstate = getinputState().state;
  138. for (size_t i = 0; i < 32; i++) {
  139. bool state = (regstate & (1 << i)) != 0;
  140. bool oldstate = (keystate & (1 << i)) != 0;
  141. if (state != oldstate) {
  142. logger->info("on {} state change, state={}", input_device_type2str(input_device_type_t(i)), state);
  143. onInputStateChange((input_device_type_t)i, state);
  144. }
  145. }
  146. } catch (const std::exception& e) {
  147. /**
  148. * @brief ,5
  149. */
  150. static tp_steady lastlogticket;
  151. if (tu_steady().elapsedTimeS(lastlogticket) > 5) {
  152. logger->error("inputStateMonitorLoop fail, {}", e.what());
  153. lastlogticket = tu_steady().now();
  154. }
  155. }
  156. thisThread.sleepForMs(50);
  157. }
  158. }
  159. uint32_t DeviceIOService::getInterTemperature() { return getReg(16); }
  160. DeviceIOService::env_sensor_state_t DeviceIOService::getEnvSensorState() {
  161. Modbus03Rx modbus03rx;
  162. env_sensor_state_t env_sensor_state = {0};
  163. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 48, 11, modbus03rx, kovertime));
  164. /**
  165. 48(16Byte) |
  166. 49(16Byte) |
  167. 50(16Byte) | temperature 湿=temperature/10
  168. 51(16Byte) | humidity 湿=humidity/10 (0->100%)
  169. 52(16Byte) |
  170. 53(16Byte) | pm2.5 ug/m³
  171. 54(16Byte) | pm10 ug/m³
  172. 55(16Byte) | co2 PPM
  173. 56(16Byte) | PPM
  174. 57(16Byte) | tvoc ppm
  175. 58(16Byte) | hcho mg/m3
  176. */
  177. env_sensor_state.wind_speed = modbus03rx.getReg(48);
  178. env_sensor_state.wind_direction = modbus03rx.getReg(49);
  179. env_sensor_state.temperature = modbus03rx.getReg(50);
  180. env_sensor_state.humidity = modbus03rx.getReg(51);
  181. env_sensor_state.noise = modbus03rx.getReg(52);
  182. env_sensor_state.pm2_5 = modbus03rx.getReg(53);
  183. env_sensor_state.pm10 = modbus03rx.getReg(54);
  184. env_sensor_state.co2 = modbus03rx.getReg(55);
  185. env_sensor_state.atmospheric_pressure = modbus03rx.getReg(56);
  186. env_sensor_state.tvoc = modbus03rx.getReg(57);
  187. env_sensor_state.hcho = modbus03rx.getReg(58);
  188. logger->debug(
  189. "getEnvSensorState, "
  190. "wind_speed={},wind_direction={},temperature={},humidity={},noise={},pm2_5={},pm10={},co2={},atmospheric_"
  191. "pressure={},tvoc={},hcho={}",
  192. env_sensor_state.wind_speed, env_sensor_state.wind_direction, env_sensor_state.temperature,
  193. env_sensor_state.humidity, env_sensor_state.noise, env_sensor_state.pm2_5, env_sensor_state.pm10,
  194. env_sensor_state.co2, env_sensor_state.atmospheric_pressure, env_sensor_state.tvoc, env_sensor_state.hcho);
  195. return env_sensor_state;
  196. }
  197. void DeviceIOService::fanGetState(int id, float& power, uint16_t& error) {
  198. int startindex = 0;
  199. if (id == 0) {
  200. startindex = 128;
  201. } else if (id == 1) {
  202. startindex = 136;
  203. } else {
  204. power = 0;
  205. error = 0;
  206. logger->error("fanGetState fail, id={},id is illegal", id);
  207. }
  208. Modbus03Rx modbus03rx;
  209. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, startindex, 2, modbus03rx, kovertime));
  210. power = modbus03rx.getReg(startindex);
  211. error = modbus03rx.getReg(startindex + 1);
  212. logger->debug("fanGetState, id={},power={},error={}", id, power, error);
  213. return;
  214. }
  215. float DeviceIOService::fanGetState(int id) {
  216. float power = 0;
  217. uint16_t error = 0;
  218. fanGetState(id, power, error);
  219. if (error != 0) {
  220. return -1;
  221. }
  222. return power;
  223. }
  224. void DeviceIOService::fanSetState(int id, float power) {
  225. logger->debug("fanSetState, id={},power={}", id, power);
  226. int startindex = 0;
  227. if (id == 0) {
  228. startindex = 128;
  229. } else if (id == 1) {
  230. startindex = 136;
  231. } else {
  232. logger->error("fanGetState fail, id={},id is illegal", id);
  233. return;
  234. }
  235. uint16_t reg[1];
  236. MODBUS_SET_REG(reg[0], uint16_t(power));
  237. EXEC_MODBUS(modbusMaster->modbus10(ksubboarddeviceid, startindex, 1, reg, kovertime));
  238. return;
  239. }
  240. void DeviceIOService::idcardread(bool& state, string& info) {
  241. /**
  242. * 64->127 | ,03,10
  243. * 64(16Byte) |
  244. * 65(16Byte) |
  245. * 65(16Byte) |
  246. * ..(16Byte) |
  247. * 127(16Byte) |
  248. */
  249. state = false;
  250. info = "";
  251. int datalen = 0;
  252. {
  253. Modbus03Rx modbus03rx;
  254. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 64, 1, modbus03rx, kovertime));
  255. datalen = modbus03rx.getReg(64);
  256. }
  257. if (datalen == 0) {
  258. logger->debug("idcardread, state={},info={}", state, info);
  259. return;
  260. }
  261. int readreg = datalen / 2 + datalen % 2 != 0 ? 1 : 0;
  262. {
  263. Modbus03Rx modbus03rx;
  264. EXEC_MODBUS(modbusMaster->modbus03(ksubboarddeviceid, 65, readreg, modbus03rx, kovertime));
  265. info = StringUtil().bytesToString(modbus03rx.getRegBegin(), datalen);
  266. }
  267. state = true;
  268. logger->debug("idcardread, state={},info={}", state, info);
  269. return;
  270. }