Newer
Older
SCADA / plc / GRFICS_Workstation_Docs / Documents / attack.st
root on 8 May 2022 14 KB playing with modbus day #1
  1. FUNCTION_BLOCK scale_to_real
  2. VAR_INPUT
  3. raw_input_value : UINT;
  4. END_VAR
  5. VAR_OUTPUT
  6. scaled_real : REAL;
  7. END_VAR
  8. VAR_INPUT
  9. real_max : REAL;
  10. real_min : REAL;
  11. END_VAR
  12. VAR
  13. raw_max : UINT := 65535;
  14. raw_min : UINT := 0;
  15. rate : REAL;
  16. offset : REAL;
  17. END_VAR
  18.  
  19. rate := (real_max - real_min) / UINT_TO_REAL(raw_max - raw_min);
  20. offset := real_min - UINT_TO_REAL(raw_min)*rate;
  21. scaled_real := UINT_TO_REAL(raw_input_value)*rate + offset;
  22. END_FUNCTION_BLOCK
  23.  
  24. FUNCTION_BLOCK scale_to_uint
  25. VAR_INPUT
  26. real_in : REAL;
  27. END_VAR
  28. VAR_OUTPUT
  29. uint_out : UINT;
  30. END_VAR
  31. VAR
  32. DIV1_OUT : REAL;
  33. MUL4_OUT : REAL;
  34. REAL_TO_UINT6_OUT : UINT;
  35. END_VAR
  36.  
  37. DIV1_OUT := DIV(real_in, 100.0);
  38. MUL4_OUT := MUL(DIV1_OUT, 65535.0);
  39. REAL_TO_UINT6_OUT := REAL_TO_UINT(MUL4_OUT);
  40. uint_out := REAL_TO_UINT6_OUT;
  41. END_FUNCTION_BLOCK
  42.  
  43. FUNCTION_BLOCK composition_control
  44. VAR
  45. a_in_purge_real : REAL := 47.00;
  46. END_VAR
  47. VAR_INPUT
  48. a_in_purge : UINT := 32000;
  49. END_VAR
  50. VAR
  51. a_setpoint_real : REAL := 47.00;
  52. END_VAR
  53. VAR_INPUT
  54. a_setpoint : UINT := 32000;
  55. curr_pos : UINT := 16000;
  56. END_VAR
  57. VAR
  58. valve_pos_real : REAL := 25.0;
  59. pos_update_real : REAL := 0.0;
  60. valve_pos_nominal : REAL := 25.0;
  61. END_VAR
  62. VAR_OUTPUT
  63. new_pos : UINT := 16000;
  64. END_VAR
  65. VAR
  66. composition_k : REAL := 1.0;
  67. composition_ti : REAL := 99.0;
  68. cycle_time : TIME := T#50ms;
  69. scale_to_real3 : scale_to_real;
  70. scale_to_real2 : scale_to_real;
  71. scale_to_uint0 : scale_to_uint;
  72. comp_max : REAL := 100.0;
  73. comp_min : REAL := 0.0;
  74. pos_max : REAL := 100.0;
  75. pos_min : REAL := 0.0;
  76. scale_to_real0 : scale_to_real;
  77. SUB45_OUT : REAL;
  78. MUL46_OUT : REAL;
  79. ADD42_OUT : REAL;
  80. LIMIT44_OUT : REAL;
  81. END_VAR
  82.  
  83. scale_to_real3(raw_input_value := a_in_purge, real_max := comp_max, real_min := comp_min);
  84. a_in_purge_real := scale_to_real3.scaled_real;
  85. scale_to_real2(raw_input_value := a_setpoint, real_max := comp_max, real_min := comp_min);
  86. a_setpoint_real := scale_to_real2.scaled_real;
  87. SUB45_OUT := SUB(a_setpoint_real, a_in_purge_real);
  88. MUL46_OUT := MUL(SUB45_OUT, composition_k);
  89. pos_update_real := MUL46_OUT;
  90. scale_to_real0(raw_input_value := curr_pos, real_max := pos_max, real_min := pos_min);
  91. valve_pos_real := scale_to_real0.scaled_real;
  92. ADD42_OUT := ADD(valve_pos_real, pos_update_real);
  93. LIMIT44_OUT := LIMIT(pos_min, ADD42_OUT, pos_max);
  94. scale_to_uint0(real_in := LIMIT44_OUT);
  95. new_pos := scale_to_uint0.uint_out;
  96. END_FUNCTION_BLOCK
  97.  
  98. FUNCTION_BLOCK initialize_sp
  99. VAR CONSTANT
  100. flow_sp_c : UINT := 13107;
  101. a_sp_c : UINT := 65535;
  102. press_sp_c : UINT := 65535;
  103. over_sp_c : UINT := 65535;
  104. level_sp_c : UINT := 65535;
  105. END_VAR
  106. VAR_OUTPUT
  107. flow_sp : UINT;
  108. a_sp : UINT;
  109. press_sp : UINT;
  110. over_sp : UINT;
  111. level_sp : UINT;
  112. END_VAR
  113. VAR
  114. MOVE3_OUT : UINT;
  115. MOVE7_OUT : UINT;
  116. MOVE11_OUT : UINT;
  117. MOVE15_OUT : UINT;
  118. MOVE19_OUT : UINT;
  119. END_VAR
  120.  
  121. MOVE3_OUT := MOVE(a_sp_c);
  122. a_sp := MOVE3_OUT;
  123. MOVE7_OUT := MOVE(flow_sp_c);
  124. flow_sp := MOVE7_OUT;
  125. MOVE11_OUT := MOVE(over_sp_c);
  126. over_sp := MOVE11_OUT;
  127. MOVE15_OUT := MOVE(level_sp_c);
  128. level_sp := MOVE15_OUT;
  129. MOVE19_OUT := MOVE(press_sp_c);
  130. press_sp := MOVE19_OUT;
  131. END_FUNCTION_BLOCK
  132.  
  133. FUNCTION_BLOCK pressure_control
  134. VAR
  135. pressure_real : REAL := 2700.0;
  136. END_VAR
  137. VAR_INPUT
  138. pressure : UINT := 58981;
  139. END_VAR
  140. VAR
  141. pressure_sp_real : REAL := 2700.0;
  142. END_VAR
  143. VAR_INPUT
  144. pressure_sp : UINT := 58981;
  145. curr_pos : UINT := 30000;
  146. END_VAR
  147. VAR
  148. valve_pos_real : REAL := 39.25;
  149. pos_update_real : REAL := 0.0;
  150. valve_pos_nominal : REAL := 39.25;
  151. END_VAR
  152. VAR_OUTPUT
  153. valve_pos : UINT := 25886;
  154. END_VAR
  155. VAR
  156. pressure_k : REAL := 20.0;
  157. pressure_ti : REAL := 999.0;
  158. cycle_time : TIME := T#50ms;
  159. scale_to_real5 : scale_to_real;
  160. scale_to_real4 : scale_to_real;
  161. scale_to_uint0 : scale_to_uint;
  162. pressure_max : REAL := 3200.00;
  163. pressure_min : REAL := 0.0;
  164. pos_min : REAL := 0.0;
  165. pos_max : REAL := 100.0;
  166. scale_to_real0 : scale_to_real;
  167. SUB57_OUT : REAL;
  168. MUL60_OUT : REAL;
  169. SUB53_OUT : REAL;
  170. LIMIT55_OUT : REAL;
  171. END_VAR
  172.  
  173. scale_to_real5(raw_input_value := pressure, real_max := pressure_max, real_min := pressure_min);
  174. pressure_real := scale_to_real5.scaled_real;
  175. scale_to_real4(raw_input_value := pressure_sp, real_max := pressure_max, real_min := pressure_min);
  176. pressure_sp_real := scale_to_real4.scaled_real;
  177. SUB57_OUT := SUB(pressure_sp_real, pressure_real);
  178. MUL60_OUT := MUL(SUB57_OUT, pressure_k);
  179. pos_update_real := MUL60_OUT;
  180. scale_to_real0(raw_input_value := curr_pos, real_max := pos_max, real_min := pos_min);
  181. valve_pos_real := scale_to_real0.scaled_real;
  182. SUB53_OUT := SUB(valve_pos_real, pos_update_real);
  183. LIMIT55_OUT := LIMIT(pos_min, SUB53_OUT, pos_max);
  184. scale_to_uint0(real_in := LIMIT55_OUT);
  185. valve_pos := scale_to_uint0.uint_out;
  186. END_FUNCTION_BLOCK
  187.  
  188. FUNCTION_BLOCK flow_control
  189. VAR
  190. flow_k : REAL := 1.0;
  191. flow_ti : REAL := 999.0;
  192. flow_td : REAL := 0.0;
  193. END_VAR
  194. VAR_INPUT
  195. product_flow : UINT := 6554;
  196. END_VAR
  197. VAR
  198. product_flow_real : REAL := 100.0;
  199. cycle_time : TIME := T#50ms;
  200. pos_update_real : REAL := 0.0;
  201. curr_pos_real : REAL := 60.9;
  202. END_VAR
  203. VAR_OUTPUT
  204. new_pos : UINT := 35000;
  205. END_VAR
  206. VAR_INPUT
  207. curr_pos : UINT := 35000;
  208. END_VAR
  209. VAR
  210. flow_set_real : REAL := 100.0;
  211. END_VAR
  212. VAR_INPUT
  213. flow_set_in : UINT := 6554;
  214. END_VAR
  215. VAR
  216. scale_to_real0 : scale_to_real;
  217. scale_to_real1 : scale_to_real;
  218. flow_max : REAL := 500.0;
  219. flow_min : REAL := 0.0;
  220. pos_min : REAL := 0.0;
  221. pos_max : REAL := 100.0;
  222. scale_to_real2 : scale_to_real;
  223. scale_to_uint0 : scale_to_uint;
  224. SUB59_OUT : REAL;
  225. MUL60_OUT : REAL;
  226. ADD58_OUT : REAL;
  227. LIMIT40_OUT : REAL;
  228. END_VAR
  229.  
  230. scale_to_real0(raw_input_value := product_flow, real_max := flow_max, real_min := flow_min);
  231. product_flow_real := scale_to_real0.scaled_real;
  232. scale_to_real1(raw_input_value := flow_set_in, real_max := flow_max, real_min := flow_min);
  233. flow_set_real := scale_to_real1.scaled_real;
  234. SUB59_OUT := SUB(flow_set_real, product_flow_real);
  235. MUL60_OUT := MUL(SUB59_OUT, flow_k);
  236. pos_update_real := MUL60_OUT;
  237. scale_to_real2(raw_input_value := curr_pos, real_max := pos_max, real_min := pos_min);
  238. curr_pos_real := scale_to_real2.scaled_real;
  239. ADD58_OUT := ADD(curr_pos_real, pos_update_real);
  240. LIMIT40_OUT := LIMIT(pos_min, ADD58_OUT, pos_max);
  241. scale_to_uint0(real_in := LIMIT40_OUT);
  242. new_pos := scale_to_uint0.uint_out;
  243. END_FUNCTION_BLOCK
  244.  
  245. FUNCTION_BLOCK level_control
  246. VAR_INPUT
  247. liquid_level : UINT;
  248. level_sp : UINT := 30000;
  249. curr_pos : UINT;
  250. END_VAR
  251. VAR_OUTPUT
  252. new_pos : UINT;
  253. END_VAR
  254. VAR
  255. cycle_time : TIME := T#50ms;
  256. level_k : REAL := 10.0;
  257. level_ti : REAL := 99999.0;
  258. scale_to_real0 : scale_to_real;
  259. level_max : REAL := 100.0;
  260. level_min : REAL := 0.0;
  261. pos_max : REAL := 100.0;
  262. pos_min : REAL := 0.0;
  263. level_real : REAL := 44.18;
  264. pos_real : REAL := 47.0;
  265. pos_update_real : REAL := 0.0;
  266. sp_real : REAL := 44.18;
  267. scale_to_real1 : scale_to_real;
  268. scale_to_real2 : scale_to_real;
  269. scale_to_uint0 : scale_to_uint;
  270. SUB32_OUT : REAL;
  271. MUL33_OUT : REAL;
  272. SUB30_OUT : REAL;
  273. LIMIT25_OUT : REAL;
  274. END_VAR
  275.  
  276. scale_to_real0(raw_input_value := liquid_level, real_max := level_max, real_min := level_min);
  277. level_real := scale_to_real0.scaled_real;
  278. scale_to_real1(raw_input_value := curr_pos, real_max := pos_max, real_min := pos_min);
  279. pos_real := scale_to_real1.scaled_real;
  280. scale_to_real2(raw_input_value := level_sp, real_max := level_max, real_min := level_min);
  281. sp_real := scale_to_real2.scaled_real;
  282. SUB32_OUT := SUB(sp_real, level_real);
  283. MUL33_OUT := MUL(SUB32_OUT, level_k);
  284. pos_update_real := MUL33_OUT;
  285. SUB30_OUT := SUB(pos_real, pos_update_real);
  286. LIMIT25_OUT := LIMIT(pos_min, SUB30_OUT, pos_max);
  287. scale_to_uint0(real_in := LIMIT25_OUT);
  288. new_pos := scale_to_uint0.uint_out;
  289. END_FUNCTION_BLOCK
  290.  
  291. FUNCTION_BLOCK scale_to_signed
  292. VAR_INPUT
  293. input_uint : UINT;
  294. END_VAR
  295. VAR_OUTPUT
  296. output_int : INT;
  297. END_VAR
  298. VAR
  299. DIV3_OUT : UINT;
  300. ABS8_OUT : UINT;
  301. UINT_TO_INT9_OUT : INT;
  302. END_VAR
  303.  
  304. DIV3_OUT := DIV(input_uint, 2);
  305. ABS8_OUT := ABS(DIV3_OUT);
  306. UINT_TO_INT9_OUT := UINT_TO_INT(ABS8_OUT);
  307. output_int := UINT_TO_INT9_OUT;
  308. END_FUNCTION_BLOCK
  309.  
  310. FUNCTION_BLOCK pressure_override
  311. VAR
  312. pressure_real : REAL := 2700.0;
  313. END_VAR
  314. VAR_INPUT
  315. pressure : UINT := 58981;
  316. curr_sp : UINT := 58981;
  317. END_VAR
  318. VAR
  319. curr_sp_real : REAL := 2700.0;
  320. product_sp_real : REAL := 100.0;
  321. sp_update : REAL := 0.0;
  322. product_sp_nominl : REAL := 100.0;
  323. END_VAR
  324. VAR_OUTPUT
  325. product_sp : UINT := 13107;
  326. END_VAR
  327. VAR
  328. override_sp_real : REAL := 2900.0;
  329. END_VAR
  330. VAR_INPUT
  331. override_sp : UINT := 63350;
  332. END_VAR
  333. VAR
  334. override_k : REAL := 1.0;
  335. override_ti : REAL := 99999.0;
  336. cycle_time : TIME := T#50ms;
  337. scale_to_real7 : scale_to_real;
  338. pressure_max : REAL := 3000.0;
  339. pressure_min : REAL := 0.0;
  340. flow_max : REAL := 500.0;
  341. flow_min : REAL := 0.0;
  342. scale_to_real0 : scale_to_real;
  343. SUB86_OUT : REAL;
  344. MUL87_OUT : REAL;
  345. MAX84_OUT : REAL;
  346. ADD85_OUT : REAL;
  347. LIMIT67_OUT : REAL;
  348. DIV73_OUT : REAL;
  349. MUL75_OUT : REAL;
  350. REAL_TO_UINT79_OUT : UINT;
  351. END_VAR
  352.  
  353. scale_to_real7(raw_input_value := pressure, real_max := pressure_max, real_min := pressure_min);
  354. pressure_real := scale_to_real7.scaled_real;
  355. SUB86_OUT := SUB(override_sp_real, pressure_real);
  356. MUL87_OUT := MUL(SUB86_OUT, override_k);
  357. MAX84_OUT := MAX(MUL87_OUT, 0.0);
  358. sp_update := MAX84_OUT;
  359. scale_to_real0(raw_input_value := curr_sp, real_max := flow_max, real_min := flow_min);
  360. curr_sp_real := scale_to_real0.scaled_real;
  361. ADD85_OUT := ADD(curr_sp_real, sp_update);
  362. LIMIT67_OUT := LIMIT(50.0, ADD85_OUT, 150.0);
  363. product_sp_real := LIMIT67_OUT;
  364. DIV73_OUT := DIV(product_sp_real, 500.0);
  365. MUL75_OUT := MUL(DIV73_OUT, 65535.0);
  366. REAL_TO_UINT79_OUT := REAL_TO_UINT(MUL75_OUT);
  367. product_sp := REAL_TO_UINT79_OUT;
  368. END_FUNCTION_BLOCK
  369.  
  370. PROGRAM main
  371. VAR
  372. flow_control0 : flow_control;
  373. first_run : BOOL := True;
  374. END_VAR
  375. VAR
  376. flow_set AT %MW0 : UINT;
  377. a_setpoint AT %MW1 : UINT;
  378. pressure_sp AT %MW2 : UINT;
  379. override_sp AT %MW3 : UINT;
  380. level_sp AT %MW4 : UINT;
  381. END_VAR
  382. VAR
  383. composition_control0 : composition_control;
  384. scale_to_signed0 : scale_to_signed;
  385. END_VAR
  386. VAR
  387. f1_valve_pos AT %IW0 : UINT;
  388. f1_flow AT %IW1 : UINT;
  389. f2_valve_pos AT %IW2 : UINT;
  390. f2_flow AT %IW3 : UINT;
  391. purge_valve_pos AT %IW4 : UINT;
  392. purge_flow AT %IW5 : UINT;
  393. product_valve_pos AT %IW6 : UINT;
  394. product_flow AT %IW7 : UINT;
  395. pressure AT %IW8 : UINT;
  396. level AT %IW9 : UINT;
  397. a_in_purge AT %IW10 : UINT;
  398. b_in_purge AT %IW11 : UINT;
  399. c_in_purge AT %IW12 : UINT;
  400. f1_valve_sp AT %QW0 : UINT;
  401. f2_valve_sp AT %QW1 : UINT;
  402. purge_valve_sp AT %QW2 : UINT;
  403. product_valve_sp AT %QW3 : UINT;
  404. END_VAR
  405. VAR
  406. product_valve_safe : UINT := 0;
  407. purge_valve_safe : UINT := 65535;
  408. f1_valve_safe : UINT;
  409. f2_valve_safe : UINT;
  410. pressure_control0 : pressure_control;
  411. END_VAR
  412. VAR
  413. hmi_pressure AT %MW20 : INT;
  414. hmi_level AT %MW21 : INT;
  415. hmi_f1_valve_pos AT %MW22 : INT;
  416. hmi_f1_flow AT %MW23 : INT;
  417. hmi_f2_valve_pos AT %MW24 : INT;
  418. hmi_f2_flow AT %MW25 : INT;
  419. hmi_purge_valve_pos AT %MW26 : INT;
  420. hmi_purge_flow AT %MW27 : INT;
  421. hmi_product_valve_pos AT %MW28 : INT;
  422. hmi_product_flow AT %MW29 : INT;
  423. scan_count AT %MW30 : UINT;
  424. END_VAR
  425. VAR
  426. scale_to_signed1 : scale_to_signed;
  427. scale_to_signed2 : scale_to_signed;
  428. scale_to_signed3 : scale_to_signed;
  429. scale_to_signed4 : scale_to_signed;
  430. scale_to_signed5 : scale_to_signed;
  431. scale_to_signed6 : scale_to_signed;
  432. scale_to_signed7 : scale_to_signed;
  433. scale_to_signed8 : scale_to_signed;
  434. scale_to_signed9 : scale_to_signed;
  435. pressure_override0 : pressure_override;
  436. level_control0 : level_control;
  437. END_VAR
  438. VAR_EXTERNAL
  439. run_bit : BOOL;
  440. END_VAR
  441. VAR
  442. run_bit0 : BOOL := True;
  443. initialize_sp0 : initialize_sp;
  444. ADD87_OUT : UINT;
  445. GE91_OUT : BOOL;
  446. MOVE92_ENO : BOOL;
  447. MOVE92_OUT : UINT;
  448. END_VAR
  449.  
  450. initialize_sp0(EN := first_run);
  451. IF initialize_sp0.ENO THEN
  452. first_run := FALSE; (*reset*)
  453. END_IF;
  454. IF initialize_sp0.ENO THEN
  455. flow_set := initialize_sp0.flow_sp;
  456. END_IF;
  457. IF initialize_sp0.ENO THEN
  458. a_setpoint := initialize_sp0.a_sp;
  459. END_IF;
  460. IF initialize_sp0.ENO THEN
  461. pressure_sp := initialize_sp0.press_sp;
  462. END_IF;
  463. IF initialize_sp0.ENO THEN
  464. override_sp := initialize_sp0.over_sp;
  465. END_IF;
  466. IF initialize_sp0.ENO THEN
  467. level_sp := initialize_sp0.level_sp;
  468. END_IF;
  469. flow_control0(product_flow := product_flow, curr_pos := f1_valve_pos, flow_set_in := flow_set);
  470. f1_valve_sp := flow_control0.new_pos;
  471. pressure_control0(pressure := pressure, pressure_sp := pressure_sp, curr_pos := purge_valve_pos);
  472. purge_valve_sp := pressure_control0.valve_pos;
  473. composition_control0(a_in_purge := a_in_purge, a_setpoint := a_setpoint, curr_pos := f2_valve_pos);
  474. f2_valve_sp := composition_control0.new_pos;
  475. pressure_override0(pressure := pressure, curr_sp := flow_set, override_sp := override_sp);
  476. flow_set := pressure_override0.product_sp;
  477. level_control0(liquid_level := level, level_sp := level_sp, curr_pos := product_valve_pos);
  478. product_valve_sp := level_control0.new_pos;
  479. scale_to_signed0(input_uint := pressure);
  480. hmi_pressure := scale_to_signed0.output_int;
  481. scale_to_signed1(input_uint := level);
  482. hmi_level := scale_to_signed1.output_int;
  483. scale_to_signed2(input_uint := f1_valve_pos);
  484. hmi_f1_valve_pos := scale_to_signed2.output_int;
  485. scale_to_signed3(input_uint := f2_valve_pos);
  486. hmi_f2_valve_pos := scale_to_signed3.output_int;
  487. scale_to_signed4(input_uint := purge_valve_pos);
  488. hmi_purge_valve_pos := scale_to_signed4.output_int;
  489. scale_to_signed5(input_uint := product_valve_pos);
  490. hmi_product_valve_pos := scale_to_signed5.output_int;
  491. scale_to_signed6(input_uint := f1_flow);
  492. hmi_f1_flow := scale_to_signed6.output_int;
  493. scale_to_signed7(input_uint := f2_flow);
  494. hmi_f2_flow := scale_to_signed7.output_int;
  495. scale_to_signed8(input_uint := purge_flow);
  496. hmi_purge_flow := scale_to_signed8.output_int;
  497. scale_to_signed9(input_uint := product_flow);
  498. hmi_product_flow := scale_to_signed9.output_int;
  499. ADD87_OUT := ADD(scan_count, 1);
  500. scan_count := ADD87_OUT;
  501. GE91_OUT := GE(scan_count, 32000);
  502. MOVE92_OUT := MOVE(EN := GE91_OUT, IN := 0, ENO => MOVE92_ENO);
  503. IF MOVE92_ENO THEN
  504. scan_count := MOVE92_OUT;
  505. END_IF;
  506. END_PROGRAM
  507.  
  508.  
  509. CONFIGURATION Config0
  510.  
  511. RESOURCE Res0 ON PLC
  512. VAR_GLOBAL
  513. run_bit AT %QX0.0 : BOOL;
  514. END_VAR
  515. TASK MainTask(INTERVAL := T#50ms,PRIORITY := 0);
  516. PROGRAM instance0 WITH MainTask : main;
  517. END_RESOURCE
  518. END_CONFIGURATION
Buy Me A Coffee