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.

465 lines
14 KiB

2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
1 year ago
2 years ago
2 years ago
2 years ago
2 years ago
2 years ago
1 year ago
2 years ago
1 year ago
2 years ago
1 year ago
  1. #include "hardware.hpp"
  2. #include <stddef.h>
  3. #include <stdio.h>
  4. #include "main.h"
  5. #include "project.hpp"
  6. #include <string.h>
  7. //
  8. // #include "sdk/components/single_axis_motor_control_v2/single_axis_motor_control_v2.hpp"
  9. #include "sdk/hal/zhal.hpp"
  10. #include "sdk\components\m3078\m3078_code_scaner.hpp"
  11. #include "sdk\components\tmc\ic\ztmc4361A.hpp"
  12. #include "sdk\components\tmc\ic\ztmc5130.hpp"
  13. //
  14. #include "driver/preportional_valve_ctrl.hpp"
  15. #include "sdk\components\huacheng_sensor\dp600_pressure_sensor.hpp"
  16. #include "sdk\components\zcan_module\huacheng_pressure_sensor.hpp"
  17. #include "sdk\components\zcan_module\zcan_basic_order_module.hpp"
  18. #include "sdk\components\zcan_module\zcan_pump_ctrl_module.hpp"
  19. #include "sdk\components\zcan_module\zcan_trigle_warning_light_ctl_module.hpp"
  20. using namespace iflytop;
  21. #define TAG "main"
  22. TMC5130 m_motor1;
  23. TMC5130 m_motor2;
  24. ZGPIO triLight_R;
  25. ZGPIO triLight_G;
  26. ZGPIO triLight_Y;
  27. ZGPIO triLight_BEEP;
  28. ZCanBasicOrderModule m_basicOrderModule;
  29. ZCanPumpCtrlModule m_pumpCtrlModule;
  30. ZCanTrigleWarningLightCtlModule m_warningLightCtlModule;
  31. HuachengPressureSensor m_huachengPressureSensor;
  32. DP600PressureSensor m_dp600PressureSensor2;
  33. DP600PressureSensor m_dp600PressureSensor3;
  34. DP600PressureSensor m_dp600PressureSensor4;
  35. ZGPIO IO_PD13_IN;
  36. ZGPIO IO_PC7_IN;
  37. ZGPIO OUT_PD14;
  38. ZGPIO OUT_PD15;
  39. void setmotor(TMC5130 *motor, int16_t acc_rpm2, int16_t rpm, int16_t idlepower, int16_t power) {
  40. int32_t ppm = rpm / 60.0 * 51200;
  41. int32_t acc = acc_rpm2 / 60.0 * 51200;
  42. int16_t _idlepower = 1;
  43. int16_t _power = 31;
  44. if (idlepower > 0 && idlepower < 31) {
  45. _idlepower = idlepower;
  46. }
  47. if (power > 0 && power < 31) {
  48. _power = power;
  49. }
  50. motor->setIHOLD_IRUN(_idlepower, _power, 10); // 5W
  51. motor->setAcceleration(acc);
  52. motor->setDeceleration(acc);
  53. motor->rotate(ppm);
  54. }
  55. PreportionalValveCtrl m_PreportionalValveHost;
  56. int32_t preportional_valve_is_busy(int32_t *busy) {
  57. int32_t valve1state = 0;
  58. int32_t valve2state = 0;
  59. int32_t err = 0;
  60. *busy = 1;
  61. err = m_PreportionalValveHost.isBusy(1, &valve1state);
  62. if (err != 0) return err;
  63. err = m_PreportionalValveHost.isBusy(2, &valve2state);
  64. if (err != 0) return err;
  65. if (valve1state == 0 && valve2state == 0) {
  66. *busy = 0;
  67. } else {
  68. *busy = 1;
  69. }
  70. return 0;
  71. }
  72. void air_compressor_read_pressure(int32_t *ack) { //
  73. DP600PressureSensor::sensor_data_t d = m_huachengPressureSensor.readsensordata(2);
  74. *ack = d.value;
  75. }
  76. void Hardware::initialize(int deviceId) {
  77. m_device_id = deviceId;
  78. IO_PD13_IN.initAsInput(PD13, ZGPIO::kMode_nopull, ZGPIO::kIRQ_noIrq, false /*mirror*/);
  79. IO_PC7_IN.initAsInput(PC7, ZGPIO::kMode_nopull, ZGPIO::kIRQ_noIrq, false /*mirror*/);
  80. {
  81. TMC5130::cfg_t cfg = {.hspi = &MOTOR_SPI, .enn_pin = MOTOR1_ENN, .csn_pin = MOTOR1_CSN};
  82. m_motor1.initialize(&cfg);
  83. int32_t chipv = m_motor1.readChipVERSION();
  84. ZLOGI(TAG, "m_motor1:%lx", chipv);
  85. while (!m_motor1.ping()) {
  86. ZLOGI(TAG, "waitting for motor1 become ready");
  87. HAL_Delay(100);
  88. }
  89. m_motor1.reInitialize();
  90. m_motor1.setIHOLD_IRUN(1, 20, 0);
  91. m_motor1.setMotorShaft(true);
  92. m_motor1.setAcceleration(300000);
  93. m_motor1.setDeceleration(300000);
  94. // m_motor1.rotate(1000000);
  95. auto gstate = m_motor1.getGState();
  96. ZLOGI(TAG, "motor1: reset:%d drv_err:%d uv_cp:%d", gstate.reset, gstate.drv_err, gstate.uv_cp);
  97. }
  98. {
  99. TMC5130::cfg_t cfg = {.hspi = &MOTOR_SPI, .enn_pin = MOTOR2_ENN, .csn_pin = MOTOR2_CSN};
  100. m_motor2.initialize(&cfg);
  101. int32_t chipv = m_motor2.readChipVERSION();
  102. ZLOGI(TAG, "m_motor2:%lx", chipv);
  103. while (!m_motor2.ping()) {
  104. ZLOGI(TAG, "waitting for motor2 become ready");
  105. HAL_Delay(100);
  106. }
  107. m_motor2.reInitialize();
  108. m_motor2.setIHOLD_IRUN(1, 20, 0); // 5W
  109. m_motor2.setMotorShaft(true);
  110. m_motor2.setAcceleration(300000);
  111. m_motor2.setDeceleration(300000);
  112. auto gstate = m_motor2.getGState();
  113. ZLOGI(TAG, "motor2: reset:%d drv_err:%d uv_cp:%d", gstate.reset, gstate.drv_err, gstate.uv_cp);
  114. // m_motor2.rotate(1000000);
  115. }
  116. triLight_R.initAsOutput(PD8, ZGPIO::kMode_nopull, true, false);
  117. triLight_G.initAsOutput(PD7, ZGPIO::kMode_nopull, true, false);
  118. triLight_Y.initAsOutput(PD9, ZGPIO::kMode_nopull, true, false);
  119. triLight_BEEP.initAsOutput(PD10, ZGPIO::kMode_nopull, true, false);
  120. m_PreportionalValveHost.initialize(&huart2);
  121. #if 1
  122. m_dp600PressureSensor2.initialize(&huart3, 2);
  123. m_dp600PressureSensor3.initialize(&huart3, 3);
  124. m_dp600PressureSensor4.initialize(&huart3, 4);
  125. OUT_PD14.initAsOutput(PD14, ZGPIO::kMode_nopull, false, true);
  126. OUT_PD15.initAsOutput(PD15, ZGPIO::kMode_nopull, true, false);
  127. #endif
  128. }
  129. void air_compressor_ch_select(int32_t val) {
  130. if (val == 2) { // 内管路
  131. OUT_PD15.setState(1);
  132. } else if (val == 1) { // 空气
  133. OUT_PD15.setState(0);
  134. }
  135. }
  136. void dumpdp600data(DP600PressureSensor::sensor_data_t *data) {
  137. ZLOGI(TAG, "value:%d", data->value);
  138. ZLOGI(TAG, "zero_point:%d", data->zero_point);
  139. ZLOGI(TAG, "range_full_point:%d", data->range_full_point);
  140. ZLOGI(TAG, "precision:%d", data->precision);
  141. ZLOGI(TAG, "pressure_unit:%d", data->pressure_unit);
  142. }
  143. void packet_kcmd_read_huacheng_pressure_sensor_data(int id, DP600PressureSensor::sensor_data_t *dp600data, uint8_t *receipt, int32_t &receiptsize) {
  144. receipt[0] = id;
  145. receipt[1] = 0;
  146. receipt[2] = dp600data->precision;
  147. receipt[3] = dp600data->pressure_unit;
  148. memcpy(receipt + 4, &dp600data->value, 2);
  149. memcpy(receipt + 6, &dp600data->zero_point, 2);
  150. memcpy(receipt + 8, &dp600data->range_full_point, 2);
  151. receiptsize = 10;
  152. }
  153. int32_t Hardware::process_rx_packet(from_where_t fromwhere, uint8_t *packet, int32_t len, uint8_t *receipt, int32_t &receiptsize, bool &matching) {
  154. Cmdheader_t *cmdheader = (Cmdheader_t *)packet;
  155. if (fromwhere == kuart) printf("rx: cmdid:%d subcmdid:%d id:%d\n", cmdheader->cmdid, cmdheader->subcmdid, cmdheader->data[0]);
  156. /**
  157. * @brief Ping
  158. */
  159. PROCESS_CMD(kcmd_ping, 0, m_device_id) {
  160. receipt[0] = cmdheader->data[0];
  161. receiptsize = 1;
  162. return 0;
  163. }
  164. /**
  165. * @brief
  166. */
  167. PROCESS_CMD(kcmd_peristaltic_pump_ctl, 1, 1) {
  168. int16_t acc = *(int16_t *)(&cmdheader->data[2]);
  169. int16_t rpm = *(int16_t *)(&cmdheader->data[4]);
  170. int16_t idlepower = cmdheader->data[6];
  171. int16_t power = cmdheader->data[7];
  172. printf("kcmd_peristaltic_pump_ctl 1 acc:%d rpm:%d idlepower:%d power:%d\n", acc, rpm, idlepower, power);
  173. setmotor1(acc, rpm, idlepower, power);
  174. receipt[0] = cmdheader->data[0];
  175. receiptsize = 1;
  176. return 0;
  177. }
  178. /**
  179. * @brief -
  180. */
  181. PROCESS_CMD(kcmd_peristaltic_pump_ctl, 1, 2) {
  182. int16_t acc = *(int16_t *)(&cmdheader->data[2]);
  183. int16_t rpm = *(int16_t *)(&cmdheader->data[4]);
  184. int16_t idlepower = cmdheader->data[6];
  185. int16_t power = cmdheader->data[7];
  186. printf("kcmd_peristaltic_pump_ctl 2 acc:%d rpm:%d idlepower:%d power:%d\n", acc, rpm, idlepower, power);
  187. setmotor2(acc, rpm, idlepower, power);
  188. receipt[0] = cmdheader->data[0];
  189. receiptsize = 1;
  190. return 0;
  191. }
  192. /**
  193. * @brief
  194. */
  195. PROCESS_CMD(kcmd_triple_warning_light_ctl, 0, 1) {
  196. /**
  197. * @brief 0:
  198. * cmd:
  199. * [0]:SENSORID
  200. * [2]:
  201. * [3]:
  202. * [4]:绿
  203. * [5]:
  204. * ack : b0:id
  205. * ack_datalen : 1
  206. */
  207. uint8_t id = cmdheader->data[0];
  208. uint8_t r = cmdheader->data[2];
  209. uint8_t g = cmdheader->data[3];
  210. uint8_t b = cmdheader->data[4];
  211. uint8_t beep = cmdheader->data[5];
  212. triLight_R.setState(r != 0);
  213. triLight_G.setState(g != 0);
  214. triLight_Y.setState(b != 0);
  215. triLight_BEEP.setState(beep != 0);
  216. receipt[0] = cmdheader->data[0];
  217. receiptsize = 1;
  218. }
  219. if ((cmdheader->cmdid == (uint16_t)kcmd_air_compressor_valve1_set) && (cmdheader->subcmdid == 0)) {
  220. uint32_t val = *(uint32_t *)(&cmdheader->data[0]);
  221. ZLOGI(TAG, "kcmd_air_compressor_valve1_set:%d", val);
  222. OUT_PD14.setState(val != 0);
  223. matching = true;
  224. }
  225. if ((cmdheader->cmdid == (uint16_t)kcmd_air_compressor_valve2_set) && (cmdheader->subcmdid == 0)) {
  226. uint32_t val = *(uint32_t *)(&cmdheader->data[0]);
  227. ZLOGI(TAG, "kcmd_air_compressor_valve2_set:%d", val);
  228. OUT_PD14.setState(val != 0);
  229. matching = true;
  230. }
  231. if ((cmdheader->cmdid == (uint16_t)kcmd_proportional_read_state) && (cmdheader->subcmdid == 0)) {
  232. matching = true;
  233. int32_t ack = 0;
  234. int32_t ecode = preportional_valve_is_busy(&ack);
  235. int32_t *p_receipt_32 = (int32_t *)receipt;
  236. *p_receipt_32 = ack;
  237. receiptsize = 4;
  238. }
  239. if ((cmdheader->cmdid == (uint16_t)kcmd_proportional_set_valve) && (cmdheader->subcmdid == 0)) {
  240. int32_t para0 = *(int32_t *)(&cmdheader->data[0]);
  241. int32_t para1 = *(int32_t *)(&cmdheader->data[4]);
  242. if (para0 == 1) {
  243. matching = true;
  244. m_PreportionalValveHost.setValvePos(1, para1);
  245. } else if (para0 == 2) {
  246. matching = true;
  247. m_PreportionalValveHost.setValvePos(2, para1);
  248. }
  249. }
  250. if ((cmdheader->cmdid == (uint16_t)kcmd_air_compressor_ch_select) && (cmdheader->subcmdid == 0)) {
  251. int32_t para0 = *(int32_t *)(&cmdheader->data[0]);
  252. air_compressor_ch_select(para0);
  253. }
  254. static DP600PressureSensor::sensor_data_t dp600data;
  255. if ((cmdheader->cmdid == (uint16_t)kcmd_air_compressor_read_pressure) && (cmdheader->subcmdid == 0)) {
  256. matching = true;
  257. bool suc = m_dp600PressureSensor2.readVal(&dp600data);
  258. if (!suc) return 1002;
  259. int32_t *p_receipt_32 = (int32_t *)receipt;
  260. *p_receipt_32 = dp600data.value;
  261. receiptsize = 4;
  262. }
  263. #if 1
  264. if ((cmdheader->cmdid == (uint16_t)kcmd_read_evaporation_bin_water_detection)) {
  265. matching = true;
  266. ((int32_t *)receipt)[0] = IO_PC7_IN.getState(); // 高有效
  267. receiptsize = 4;
  268. return 0;
  269. }
  270. if ((cmdheader->cmdid == (uint16_t)kcmd_read_device_bottom_water_detection_sensor)) {
  271. matching = true;
  272. ((int32_t *)receipt)[0] = !IO_PD13_IN.getState(); // 低有效
  273. receiptsize = 4;
  274. return 0;
  275. }
  276. #endif
  277. /**
  278. * @brief
  279. */
  280. PROCESS_CMD(kcmd_read_huacheng_pressure_sensor, 0, 1) {
  281. static ModbusBlockHost modbusBlockHost;
  282. modbusBlockHost.initialize(&huart3);
  283. int16_t val[1] = {0};
  284. bool suc = modbusBlockHost.readReg03Muti(1, 0x00, (uint16_t *)val, 1, 50);
  285. if (!suc) return 1002;
  286. dp600data.precision = 3;
  287. dp600data.pressure_unit = 1;
  288. dp600data.value = val[0];
  289. dp600data.zero_point = 0;
  290. dp600data.range_full_point = 0;
  291. packet_kcmd_read_huacheng_pressure_sensor_data(cmdheader->data[0], &dp600data, receipt, receiptsize);
  292. if (fromwhere == kuart) {
  293. dumpdp600data(&dp600data);
  294. }
  295. return 0;
  296. }
  297. /**
  298. * @brief
  299. */
  300. PROCESS_CMD(kcmd_read_huacheng_pressure_sensor, 0, 2) {
  301. bool suc = m_dp600PressureSensor2.readVal(&dp600data);
  302. if (!suc) return 1002;
  303. packet_kcmd_read_huacheng_pressure_sensor_data(cmdheader->data[0], &dp600data, receipt, receiptsize);
  304. if (fromwhere == kuart) {
  305. dumpdp600data(&dp600data);
  306. }
  307. return 0;
  308. }
  309. /**
  310. * @brief
  311. */
  312. PROCESS_CMD(kcmd_read_huacheng_pressure_sensor, 0, 3) {
  313. bool suc = m_dp600PressureSensor3.readVal(&dp600data);
  314. if (!suc) return 1002;
  315. packet_kcmd_read_huacheng_pressure_sensor_data(cmdheader->data[0], &dp600data, receipt, receiptsize);
  316. if (fromwhere == kuart) {
  317. dumpdp600data(&dp600data);
  318. }
  319. return 0;
  320. }
  321. /**
  322. * @brief
  323. */
  324. PROCESS_CMD(kcmd_read_huacheng_pressure_sensor, 0, 4) {
  325. bool suc = m_dp600PressureSensor4.readVal(&dp600data);
  326. if (!suc) return 1002;
  327. packet_kcmd_read_huacheng_pressure_sensor_data(cmdheader->data[0], &dp600data, receipt, receiptsize);
  328. if (fromwhere == kuart) {
  329. dumpdp600data(&dp600data);
  330. }
  331. return 0;
  332. }
  333. return 0;
  334. }
  335. void Hardware::loop() {}
  336. TMC5130 *Hardware::getMotor1() { return &m_motor1; }
  337. TMC5130 *Hardware::getMotor2() { return &m_motor2; }
  338. typedef struct motor_state_cache_t {
  339. int16_t acc_rpm2;
  340. int16_t rpm;
  341. int16_t idlepower;
  342. int16_t power;
  343. };
  344. motor_state_cache_t m_motor1_cache;
  345. motor_state_cache_t m_motor2_cache;
  346. void Hardware::setmotor1(int16_t acc_rpm2, int16_t rpm, int16_t idlepower, int16_t power) { //
  347. setmotor(&m_motor1, acc_rpm2, rpm, idlepower, power);
  348. m_motor1_cache.acc_rpm2 = acc_rpm2;
  349. m_motor1_cache.rpm = rpm;
  350. m_motor1_cache.idlepower = idlepower;
  351. m_motor1_cache.power = power;
  352. }
  353. void Hardware::recovermotor1() {
  354. m_motor1.reInitialize();
  355. setmotor(&m_motor1, m_motor1_cache.acc_rpm2, m_motor1_cache.rpm, m_motor1_cache.idlepower, m_motor1_cache.power);
  356. }
  357. bool Hardware::ismotor1error() {
  358. DevStatusReg_t sreg1 = m_motor1.getDevStatus();
  359. GState_t gstate1 = m_motor1.getGState();
  360. if (gstate1.reset) {
  361. ZLOGE(TAG, "motor1 driver trigger illegal reset");
  362. return true;
  363. }
  364. if (sreg1.ola || sreg1.olb) {
  365. ZLOGE(TAG, "motor1 driver trigger ola olb");
  366. return true;
  367. }
  368. return false;
  369. }
  370. void Hardware::setmotor2(int16_t acc_rpm2, int16_t rpm, int16_t idlepower, int16_t power) { //
  371. setmotor(&m_motor2, acc_rpm2, rpm, idlepower, power);
  372. m_motor2_cache.acc_rpm2 = acc_rpm2;
  373. m_motor2_cache.rpm = rpm;
  374. m_motor2_cache.idlepower = idlepower;
  375. m_motor2_cache.power = power;
  376. }
  377. void Hardware::recovermotor2() {
  378. m_motor2.reInitialize();
  379. setmotor(&m_motor2, m_motor2_cache.acc_rpm2, m_motor2_cache.rpm, m_motor2_cache.idlepower, m_motor2_cache.power);
  380. }
  381. bool Hardware::ismotor2error() {
  382. DevStatusReg_t sreg2 = m_motor2.getDevStatus();
  383. GState_t gstate2 = m_motor2.getGState();
  384. if (gstate2.reset) {
  385. ZLOGE(TAG, "motor2 driver trigger illegal reset");
  386. return true;
  387. }
  388. if (sreg2.ola || sreg2.olb) {
  389. ZLOGE(TAG, "motor2 driver trigger ola olb");
  390. return true;
  391. }
  392. return false;
  393. }