#118 refactored RTU unit types

This commit is contained in:
Mikayla Fischler 2023-02-21 12:27:16 -05:00
parent 7247d8a828
commit 424097973d
15 changed files with 146 additions and 169 deletions

View File

@ -31,7 +31,8 @@ local MQ__COMM_CMD = {
---@param smem plc_shared_memory ---@param smem plc_shared_memory
---@param init function ---@param init function
function threads.thread__main(smem, init) function threads.thread__main(smem, init)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -277,7 +278,8 @@ end
-- RPS operation thread -- RPS operation thread
---@param smem plc_shared_memory ---@param smem plc_shared_memory
function threads.thread__rps(smem) function threads.thread__rps(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -416,7 +418,8 @@ end
-- communications sender thread -- communications sender thread
---@param smem plc_shared_memory ---@param smem plc_shared_memory
function threads.thread__comms_tx(smem) function threads.thread__comms_tx(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -490,7 +493,8 @@ end
-- communications handler thread -- communications handler thread
---@param smem plc_shared_memory ---@param smem plc_shared_memory
function threads.thread__comms_rx(smem) function threads.thread__comms_rx(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -564,7 +568,8 @@ end
-- apply setpoints -- apply setpoints
---@param smem plc_shared_memory ---@param smem plc_shared_memory
function threads.thread__setpoint_control(smem) function threads.thread__setpoint_control(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()

View File

@ -1,6 +1,7 @@
local comms = require("scada-common.comms") local comms = require("scada-common.comms")
local ppm = require("scada-common.ppm") local ppm = require("scada-common.ppm")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
local modbus = require("rtu.modbus") local modbus = require("rtu.modbus")
@ -11,7 +12,7 @@ local PROTOCOL = comms.PROTOCOL
local DEVICE_TYPE = comms.DEVICE_TYPE local DEVICE_TYPE = comms.DEVICE_TYPE
local ESTABLISH_ACK = comms.ESTABLISH_ACK local ESTABLISH_ACK = comms.ESTABLISH_ACK
local SCADA_MGMT_TYPE = comms.SCADA_MGMT_TYPE local SCADA_MGMT_TYPE = comms.SCADA_MGMT_TYPE
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local print = util.print local print = util.print
local println = util.println local println = util.println
@ -223,12 +224,11 @@ function rtu.comms(version, modem, local_port, server_port, range, conn_watchdog
local advertisement = {} local advertisement = {}
for i = 1, #units do for i = 1, #units do
local unit = units[i] --@type rtu_unit_registry_entry local unit = units[i] ---@type rtu_unit_registry_entry
local type = comms.rtu_t_to_unit_type(unit.type)
if type ~= nil then if type ~= nil then
local advert = { local advert = {
type, unit.type,
unit.index, unit.index,
unit.reactor unit.reactor
} }

View File

@ -27,7 +27,7 @@ local turbinev_rtu = require("rtu.dev.turbinev_rtu")
local RTU_VERSION = "beta-v0.11.2" local RTU_VERSION = "beta-v0.11.2"
local rtu_t = types.rtu_t local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local print = util.print local print = util.print
local println = util.println local println = util.println
@ -151,7 +151,7 @@ local function main()
-- check for duplicate entries -- check for duplicate entries
for i = 1, #units do for i = 1, #units do
local unit = units[i] ---@type rtu_unit_registry_entry local unit = units[i] ---@type rtu_unit_registry_entry
if unit.reactor == io_reactor and unit.type == rtu_t.redstone then if unit.reactor == io_reactor and unit.type == RTU_UNIT_TYPE.REDSTONE then
-- duplicate entry -- duplicate entry
local message = util.c("configure> skipping definition block #", entry_idx, " for reactor ", io_reactor, local message = util.c("configure> skipping definition block #", entry_idx, " for reactor ", io_reactor,
" with already defined redstone I/O") " with already defined redstone I/O")
@ -224,23 +224,28 @@ local function main()
---@class rtu_unit_registry_entry ---@class rtu_unit_registry_entry
local unit = { local unit = {
uid = 0, uid = 0, ---@type integer
name = "redstone_io", name = "redstone_io", ---@type string
type = rtu_t.redstone, type = RTU_UNIT_TYPE.REDSTONE, ---@type RTU_UNIT_TYPE
index = entry_idx, index = entry_idx, ---@type integer
reactor = io_reactor, reactor = io_reactor, ---@type integer
device = capabilities, -- use device field for redstone ports device = capabilities, ---@type table use device field for redstone ports
is_multiblock = false, is_multiblock = false, ---@type boolean
formed = nil, ---@type boolean|nil formed = nil, ---@type boolean|nil
rtu = rs_rtu, ---@type rtu_device|rtu_rs_device rtu = rs_rtu, ---@type rtu_device|rtu_rs_device
modbus_io = modbus.new(rs_rtu, false), modbus_io = modbus.new(rs_rtu, false),
pkt_queue = nil, ---@type mqueue|nil pkt_queue = nil, ---@type mqueue|nil
thread = nil thread = nil ---@type parallel_thread|nil
} }
table.insert(units, unit) table.insert(units, unit)
log.debug(util.c("init> initialized RTU unit #", #units, ": redstone_io (redstone) [1] for reactor ", io_reactor)) local for_message = "facility"
if io_reactor > 0 then
for_message = util.c("reactor ", io_reactor)
end
log.debug(util.c("configure> initialized RTU unit #", #units, ": redstone_io (redstone) [1] for ", for_message))
unit.uid = #units unit.uid = #units
end end
@ -274,7 +279,7 @@ local function main()
local type = nil local type = nil
local rtu_iface = nil ---@type rtu_device local rtu_iface = nil ---@type rtu_device
local rtu_type = "" local rtu_type = nil ---@type RTU_UNIT_TYPE
local is_multiblock = false local is_multiblock = false
local formed = nil ---@type boolean|nil local formed = nil ---@type boolean|nil
@ -291,7 +296,7 @@ local function main()
if type == "boilerValve" then if type == "boilerValve" then
-- boiler multiblock -- boiler multiblock
rtu_type = rtu_t.boiler_valve rtu_type = RTU_UNIT_TYPE.BOILER_VALVE
rtu_iface = boilerv_rtu.new(device) rtu_iface = boilerv_rtu.new(device)
is_multiblock = true is_multiblock = true
formed = device.isFormed() formed = device.isFormed()
@ -303,7 +308,7 @@ local function main()
end end
elseif type == "turbineValve" then elseif type == "turbineValve" then
-- turbine multiblock -- turbine multiblock
rtu_type = rtu_t.turbine_valve rtu_type = RTU_UNIT_TYPE.TURBINE_VALVE
rtu_iface = turbinev_rtu.new(device) rtu_iface = turbinev_rtu.new(device)
is_multiblock = true is_multiblock = true
formed = device.isFormed() formed = device.isFormed()
@ -315,7 +320,7 @@ local function main()
end end
elseif type == "inductionPort" then elseif type == "inductionPort" then
-- induction matrix multiblock -- induction matrix multiblock
rtu_type = rtu_t.induction_matrix rtu_type = RTU_UNIT_TYPE.IMATRIX
rtu_iface = imatrix_rtu.new(device) rtu_iface = imatrix_rtu.new(device)
is_multiblock = true is_multiblock = true
formed = device.isFormed() formed = device.isFormed()
@ -327,7 +332,7 @@ local function main()
end end
elseif type == "spsPort" then elseif type == "spsPort" then
-- SPS multiblock -- SPS multiblock
rtu_type = rtu_t.sps rtu_type = RTU_UNIT_TYPE.SPS
rtu_iface = sps_rtu.new(device) rtu_iface = sps_rtu.new(device)
is_multiblock = true is_multiblock = true
formed = device.isFormed() formed = device.isFormed()
@ -339,15 +344,15 @@ local function main()
end end
elseif type == "solarNeutronActivator" then elseif type == "solarNeutronActivator" then
-- SNA -- SNA
rtu_type = rtu_t.sna rtu_type = RTU_UNIT_TYPE.SNA
rtu_iface = sna_rtu.new(device) rtu_iface = sna_rtu.new(device)
elseif type == "environmentDetector" then elseif type == "environmentDetector" then
-- advanced peripherals environment detector -- advanced peripherals environment detector
rtu_type = rtu_t.env_detector rtu_type = RTU_UNIT_TYPE.ENV_DETECTOR
rtu_iface = envd_rtu.new(device) rtu_iface = envd_rtu.new(device)
elseif type == ppm.VIRTUAL_DEVICE_TYPE then elseif type == ppm.VIRTUAL_DEVICE_TYPE then
-- placeholder device -- placeholder device
rtu_type = "virtual" rtu_type = RTU_UNIT_TYPE.VIRTUAL
rtu_iface = rtu.init_unit().interface() rtu_iface = rtu.init_unit().interface()
else else
local message = util.c("configure> device '", name, "' is not a known type (", type, ")") local message = util.c("configure> device '", name, "' is not a known type (", type, ")")
@ -358,18 +363,18 @@ local function main()
---@class rtu_unit_registry_entry ---@class rtu_unit_registry_entry
local rtu_unit = { local rtu_unit = {
uid = 0, uid = 0, ---@type integer
name = name, name = name, ---@type string
type = rtu_type, type = rtu_type, ---@type RTU_UNIT_TYPE
index = index, index = index, ---@type integer
reactor = for_reactor, reactor = for_reactor, ---@type integer
device = device, device = device, ---@type table
is_multiblock = is_multiblock, is_multiblock = is_multiblock, ---@type boolean
formed = formed, ---@type boolean|nil formed = formed, ---@type boolean|nil
rtu = rtu_iface, ---@type rtu_device|rtu_rs_device rtu = rtu_iface, ---@type rtu_device|rtu_rs_device
modbus_io = modbus.new(rtu_iface, true), modbus_io = modbus.new(rtu_iface, true),
pkt_queue = mqueue.new(), ---@type mqueue|nil pkt_queue = mqueue.new(), ---@type mqueue|nil
thread = nil thread = nil ---@type parallel_thread|nil
} }
rtu_unit.thread = threads.thread__unit_comms(__shared_memory, rtu_unit) rtu_unit.thread = threads.thread__unit_comms(__shared_memory, rtu_unit)
@ -385,7 +390,7 @@ local function main()
for_message = util.c("reactor ", for_reactor) for_message = util.c("reactor ", for_reactor)
end end
log.debug(util.c("configure> initialized RTU unit #", #units, ": ", name, " (", rtu_type, ") [", index, "] for ", for_message)) log.debug(util.c("configure> initialized RTU unit #", #units, ": ", name, " (", types.rtu_type_to_string(rtu_type), ") [", index, "] for ", for_message))
rtu_unit.uid = #units rtu_unit.uid = #units
end end

View File

@ -15,7 +15,7 @@ local modbus = require("rtu.modbus")
local threads = {} local threads = {}
local rtu_t = types.rtu_t local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local print = util.print local print = util.print
local println = util.println local println = util.println
@ -28,7 +28,8 @@ local COMMS_SLEEP = 100 -- (100ms, 2 ticks)
-- main thread -- main thread
---@param smem rtu_shared_memory ---@param smem rtu_shared_memory
function threads.thread__main(smem) function threads.thread__main(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -93,8 +94,9 @@ function threads.thread__main(smem)
-- we are going to let the PPM prevent crashes -- we are going to let the PPM prevent crashes
-- return fault flags/codes to MODBUS queries -- return fault flags/codes to MODBUS queries
local unit = units[i] local unit = units[i]
println_ts(util.c("lost the ", unit.type, " on interface ", unit.name)) local type_name = types.rtu_type_to_string(unit.type)
log.warning(util.c("lost the ", unit.type, " unit peripheral on interface ", unit.name)) println_ts(util.c("lost the ", type_name, " on interface ", unit.name))
log.warning(util.c("lost the ", type_name, " unit peripheral on interface ", unit.name))
break break
end end
end end
@ -129,51 +131,51 @@ function threads.thread__main(smem)
-- found, re-link -- found, re-link
unit.device = device unit.device = device
if unit.type == "virtual" then if unit.type == RTU_UNIT_TYPE.VIRTUAL then
resend_advert = true resend_advert = true
if type == "boilerValve" then if type == "boilerValve" then
-- boiler multiblock -- boiler multiblock
unit.type = rtu_t.boiler_valve unit.type = RTU_UNIT_TYPE.BOILER_VALVE
elseif type == "turbineValve" then elseif type == "turbineValve" then
-- turbine multiblock -- turbine multiblock
unit.type = rtu_t.turbine_valve unit.type = RTU_UNIT_TYPE.TURBINE_VALVE
elseif type == "inductionPort" then elseif type == "inductionPort" then
-- induction matrix multiblock -- induction matrix multiblock
unit.type = rtu_t.induction_matrix unit.type = RTU_UNIT_TYPE.IMATRIX
elseif type == "spsPort" then elseif type == "spsPort" then
-- SPS multiblock -- SPS multiblock
unit.type = rtu_t.sps unit.type = RTU_UNIT_TYPE.SPS
elseif type == "solarNeutronActivator" then elseif type == "solarNeutronActivator" then
-- SNA -- SNA
unit.type = rtu_t.sna unit.type = RTU_UNIT_TYPE.SNA
elseif type == "environmentDetector" then elseif type == "environmentDetector" then
-- advanced peripherals environment detector -- advanced peripherals environment detector
unit.type = rtu_t.env_detector unit.type = RTU_UNIT_TYPE.ENV_DETECTOR
else else
resend_advert = false resend_advert = false
log.error(util.c("virtual device '", unit.name, "' cannot init to an unknown type (", type, ")")) log.error(util.c("virtual device '", unit.name, "' cannot init to an unknown type (", type, ")"))
end end
end end
if unit.type == rtu_t.boiler_valve then if unit.type == RTU_UNIT_TYPE.BOILER_VALVE then
unit.rtu = boilerv_rtu.new(device) unit.rtu = boilerv_rtu.new(device)
-- if not formed, indexing the multiblock functions would have resulted in a PPM fault -- if not formed, indexing the multiblock functions would have resulted in a PPM fault
unit.formed = util.trinary(device.__p_is_faulted(), false, nil) unit.formed = util.trinary(device.__p_is_faulted(), false, nil)
elseif unit.type == rtu_t.turbine_valve then elseif unit.type == RTU_UNIT_TYPE.TURBINE_VALVE then
unit.rtu = turbinev_rtu.new(device) unit.rtu = turbinev_rtu.new(device)
-- if not formed, indexing the multiblock functions would have resulted in a PPM fault -- if not formed, indexing the multiblock functions would have resulted in a PPM fault
unit.formed = util.trinary(device.__p_is_faulted(), false, nil) unit.formed = util.trinary(device.__p_is_faulted(), false, nil)
elseif unit.type == rtu_t.induction_matrix then elseif unit.type == RTU_UNIT_TYPE.IMATRIX then
unit.rtu = imatrix_rtu.new(device) unit.rtu = imatrix_rtu.new(device)
-- if not formed, indexing the multiblock functions would have resulted in a PPM fault -- if not formed, indexing the multiblock functions would have resulted in a PPM fault
unit.formed = util.trinary(device.__p_is_faulted(), false, nil) unit.formed = util.trinary(device.__p_is_faulted(), false, nil)
elseif unit.type == rtu_t.sps then elseif unit.type == RTU_UNIT_TYPE.SPS then
unit.rtu = sps_rtu.new(device) unit.rtu = sps_rtu.new(device)
-- if not formed, indexing the multiblock functions would have resulted in a PPM fault -- if not formed, indexing the multiblock functions would have resulted in a PPM fault
unit.formed = util.trinary(device.__p_is_faulted(), false, nil) unit.formed = util.trinary(device.__p_is_faulted(), false, nil)
elseif unit.type == rtu_t.sna then elseif unit.type == RTU_UNIT_TYPE.SNA then
unit.rtu = sna_rtu.new(device) unit.rtu = sna_rtu.new(device)
elseif unit.type == rtu_t.env_detector then elseif unit.type == RTU_UNIT_TYPE.ENV_DETECTOR then
unit.rtu = envd_rtu.new(device) unit.rtu = envd_rtu.new(device)
else else
log.error(util.c("failed to identify reconnected RTU unit type (", unit.name, ")"), true) log.error(util.c("failed to identify reconnected RTU unit type (", unit.name, ")"), true)
@ -185,8 +187,10 @@ function threads.thread__main(smem)
unit.modbus_io = modbus.new(unit.rtu, true) unit.modbus_io = modbus.new(unit.rtu, true)
println_ts("reconnected the " .. unit.type .. " on interface " .. unit.name) local type_name = types.rtu_type_to_string(unit.type)
log.info("reconnected the " .. unit.type .. " on interface " .. unit.name) local message = util.c("reconnected the ", type_name, " on interface ", unit.name)
println_ts(message)
log.info(message)
if resend_advert then if resend_advert then
rtu_comms.send_advertisement(units) rtu_comms.send_advertisement(units)
@ -231,7 +235,8 @@ end
-- communications handler thread -- communications handler thread
---@param smem rtu_shared_memory ---@param smem rtu_shared_memory
function threads.thread__comms(smem) function threads.thread__comms(smem)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
@ -304,11 +309,12 @@ end
---@param smem rtu_shared_memory ---@param smem rtu_shared_memory
---@param unit rtu_unit_registry_entry ---@param unit rtu_unit_registry_entry
function threads.thread__unit_comms(smem, unit) function threads.thread__unit_comms(smem, unit)
local public = {} ---@class thread ---@class parallel_thread
local public = {}
-- execute thread -- execute thread
function public.exec() function public.exec()
log.debug("rtu unit thread start -> " .. unit.type .. "(" .. unit.name .. ")") log.debug(util.c("rtu unit thread start -> ", types.rtu_type_to_string(unit.type), "(", unit.name, ")"))
-- load in from shared memory -- load in from shared memory
local rtu_state = smem.rtu_state local rtu_state = smem.rtu_state
@ -319,8 +325,8 @@ function threads.thread__unit_comms(smem, unit)
local last_f_check = 0 local last_f_check = 0
local detail_name = util.c(unit.type, " (", unit.name, ") [", unit.index, "] for reactor ", unit.reactor) local detail_name = util.c(types.rtu_type_to_string(unit.type), " (", unit.name, ") [", unit.index, "] for reactor ", unit.reactor)
local short_name = util.c(unit.type, " (", unit.name, ")") local short_name = util.c(types.rtu_type_to_string(unit.type), " (", unit.name, ")")
if packet_queue == nil then if packet_queue == nil then
log.error("rtu unit thread created without a message queue, exiting...", true) log.error("rtu unit thread created without a message queue, exiting...", true)
@ -368,25 +374,25 @@ function threads.thread__unit_comms(smem, unit)
local type, device = ppm.mount(iface) local type, device = ppm.mount(iface)
if device ~= nil then if device ~= nil then
if type == "boilerValve" and unit.type == rtu_t.boiler_valve then if type == "boilerValve" and unit.type == RTU_UNIT_TYPE.BOILER_VALVE then
-- boiler multiblock -- boiler multiblock
unit.device = device unit.device = device
unit.rtu = boilerv_rtu.new(device) unit.rtu = boilerv_rtu.new(device)
unit.formed = device.isFormed() unit.formed = device.isFormed()
unit.modbus_io = modbus.new(unit.rtu, true) unit.modbus_io = modbus.new(unit.rtu, true)
elseif type == "turbineValve" and unit.type == rtu_t.turbine_valve then elseif type == "turbineValve" and unit.type == RTU_UNIT_TYPE.TURBINE_VALVE then
-- turbine multiblock -- turbine multiblock
unit.device = device unit.device = device
unit.rtu = turbinev_rtu.new(device) unit.rtu = turbinev_rtu.new(device)
unit.formed = device.isFormed() unit.formed = device.isFormed()
unit.modbus_io = modbus.new(unit.rtu, true) unit.modbus_io = modbus.new(unit.rtu, true)
elseif type == "inductionPort" and unit.type == rtu_t.induction_matrix then elseif type == "inductionPort" and unit.type == RTU_UNIT_TYPE.IMATRIX then
-- induction matrix multiblock -- induction matrix multiblock
unit.device = device unit.device = device
unit.rtu = imatrix_rtu.new(device) unit.rtu = imatrix_rtu.new(device)
unit.formed = device.isFormed() unit.formed = device.isFormed()
unit.modbus_io = modbus.new(unit.rtu, true) unit.modbus_io = modbus.new(unit.rtu, true)
elseif type == "spsPort" and unit.type == rtu_t.sps then elseif type == "spsPort" and unit.type == RTU_UNIT_TYPE.SPS then
-- SPS multiblock -- SPS multiblock
unit.device = device unit.device = device
unit.rtu = sps_rtu.new(device) unit.rtu = sps_rtu.new(device)
@ -433,7 +439,7 @@ function threads.thread__unit_comms(smem, unit)
end end
if not rtu_state.shutdown then if not rtu_state.shutdown then
log.info(util.c("rtu unit thread ", unit.type, "(", unit.name, " restarting in 5 seconds...")) log.info(util.c("rtu unit thread ", types.rtu_type_to_string(unit.type), "(", unit.name, " restarting in 5 seconds..."))
util.psleep(5) util.psleep(5)
end end
end end

View File

@ -3,13 +3,10 @@
-- --
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types")
---@class comms ---@class comms
local comms = {} local comms = {}
local rtu_t = types.rtu_t
local insert = table.insert local insert = table.insert
local max_distance = nil local max_distance = nil
@ -80,17 +77,6 @@ local DEVICE_TYPE = {
CRDN = 3 -- coordinator device type for establish CRDN = 3 -- coordinator device type for establish
} }
---@enum RTU_UNIT_TYPE
local RTU_UNIT_TYPE = {
REDSTONE = 0, -- redstone I/O
BOILER_VALVE = 1, -- boiler mekanism 10.1+
TURBINE_VALVE = 2, -- turbine, mekanism 10.1+
IMATRIX = 3, -- induction matrix
SPS = 4, -- SPS
SNA = 5, -- SNA
ENV_DETECTOR = 6 -- environment detector
}
---@enum PLC_AUTO_ACK ---@enum PLC_AUTO_ACK
local PLC_AUTO_ACK = { local PLC_AUTO_ACK = {
FAIL = 0, -- failed to set burn rate/burn rate invalid FAIL = 0, -- failed to set burn rate/burn rate invalid
@ -129,7 +115,6 @@ comms.CAPI_TYPE = CAPI_TYPE
comms.ESTABLISH_ACK = ESTABLISH_ACK comms.ESTABLISH_ACK = ESTABLISH_ACK
comms.DEVICE_TYPE = DEVICE_TYPE comms.DEVICE_TYPE = DEVICE_TYPE
comms.RTU_UNIT_TYPE = RTU_UNIT_TYPE
comms.PLC_AUTO_ACK = PLC_AUTO_ACK comms.PLC_AUTO_ACK = PLC_AUTO_ACK
@ -719,52 +704,4 @@ function comms.capi_packet()
return public return public
end end
-- convert rtu_t to RTU unit type
---@nodiscard
---@param type rtu_t
---@return RTU_UNIT_TYPE|nil
function comms.rtu_t_to_unit_type(type)
if type == rtu_t.redstone then
return RTU_UNIT_TYPE.REDSTONE
elseif type == rtu_t.boiler_valve then
return RTU_UNIT_TYPE.BOILER_VALVE
elseif type == rtu_t.turbine_valve then
return RTU_UNIT_TYPE.TURBINE_VALVE
elseif type == rtu_t.induction_matrix then
return RTU_UNIT_TYPE.IMATRIX
elseif type == rtu_t.sps then
return RTU_UNIT_TYPE.SPS
elseif type == rtu_t.sna then
return RTU_UNIT_TYPE.SNA
elseif type == rtu_t.env_detector then
return RTU_UNIT_TYPE.ENV_DETECTOR
end
return nil
end
-- convert RTU unit type to rtu_t
---@nodiscard
---@param utype RTU_UNIT_TYPE
---@return rtu_t|nil
function comms.advert_type_to_rtu_t(utype)
if utype == RTU_UNIT_TYPE.REDSTONE then
return rtu_t.redstone
elseif utype == RTU_UNIT_TYPE.BOILER_VALVE then
return rtu_t.boiler_valve
elseif utype == RTU_UNIT_TYPE.TURBINE_VALVE then
return rtu_t.turbine_valve
elseif utype == RTU_UNIT_TYPE.IMATRIX then
return rtu_t.induction_matrix
elseif utype == RTU_UNIT_TYPE.SPS then
return rtu_t.sps
elseif utype == RTU_UNIT_TYPE.SNA then
return rtu_t.sna
elseif utype == RTU_UNIT_TYPE.ENV_DETECTOR then
return rtu_t.env_detector
end
return nil
end
return comms return comms

View File

@ -70,6 +70,48 @@ function types.new_zero_coordinate() return { x = 0, y = 0, z = 0 } end
-- ENUMERATION TYPES -- -- ENUMERATION TYPES --
--#region --#region
---@enum RTU_UNIT_TYPE
types.RTU_UNIT_TYPE = {
VIRTUAL = 0, -- virtual device
REDSTONE = 1, -- redstone I/O
BOILER_VALVE = 2, -- boiler mekanism 10.1+
TURBINE_VALVE = 3, -- turbine, mekanism 10.1+
IMATRIX = 4, -- induction matrix
SPS = 5, -- SPS
SNA = 6, -- SNA
ENV_DETECTOR = 7 -- environment detector
}
types.RTU_UNIT_NAMES = {
"redstone",
"boiler_valve",
"turbine_valve",
"induction_matrix",
"sps",
"sna",
"environment_detector"
}
-- safe conversion of RTU UNIT TYPE to string
---@nodiscard
---@param utype RTU_UNIT_TYPE
---@return string
function types.rtu_type_to_string(utype)
if utype == types.RTU_UNIT_TYPE.VIRTUAL then
return "virtual"
elseif utype == types.RTU_UNIT_TYPE.REDSTONE or
utype == types.RTU_UNIT_TYPE.BOILER_VALVE or
utype == types.RTU_UNIT_TYPE.TURBINE_VALVE or
utype == types.RTU_UNIT_TYPE.IMATRIX or
utype == types.RTU_UNIT_TYPE.SPS or
utype == types.RTU_UNIT_TYPE.SNA or
utype == types.RTU_UNIT_TYPE.ENV_DETECTOR then
return types.RTU_UNIT_NAMES[utype]
else
return ""
end
end
---@enum TRI_FAIL ---@enum TRI_FAIL
types.TRI_FAIL = { types.TRI_FAIL = {
OK = 0, OK = 0,
@ -215,17 +257,6 @@ types.FLUID = {
SUPERHEATED_SODIUM = "mekanism:superheated_sodium" SUPERHEATED_SODIUM = "mekanism:superheated_sodium"
} }
---@alias rtu_t string
types.rtu_t = {
redstone = "redstone",
boiler_valve = "boiler_valve",
turbine_valve = "turbine_valve",
induction_matrix = "induction_matrix",
sps = "sps",
sna = "sna",
env_detector = "environment_detector"
}
---@alias rps_trip_cause ---@alias rps_trip_cause
---| "ok" ---| "ok"
---| "dmg_crit" ---| "dmg_crit"

View File

@ -1,6 +1,7 @@
local comms = require("scada-common.comms") local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local mqueue = require("scada-common.mqueue") local mqueue = require("scada-common.mqueue")
local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
local svqtypes = require("supervisor.session.svqtypes") local svqtypes = require("supervisor.session.svqtypes")
@ -12,7 +13,7 @@ local SCADA_MGMT_TYPE = comms.SCADA_MGMT_TYPE
local SCADA_CRDN_TYPE = comms.SCADA_CRDN_TYPE local SCADA_CRDN_TYPE = comms.SCADA_CRDN_TYPE
local UNIT_COMMAND = comms.UNIT_COMMAND local UNIT_COMMAND = comms.UNIT_COMMAND
local FAC_COMMAND = comms.FAC_COMMAND local FAC_COMMAND = comms.FAC_COMMAND
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local SV_Q_CMDS = svqtypes.SV_Q_CMDS local SV_Q_CMDS = svqtypes.SV_Q_CMDS
local SV_Q_DATA = svqtypes.SV_Q_DATA local SV_Q_DATA = svqtypes.SV_Q_DATA

View File

@ -1,7 +1,7 @@
local comms = require("scada-common.comms") local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local mqueue = require("scada-common.mqueue") local mqueue = require("scada-common.mqueue")
local rsio = require("scada-common.rsio") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
local svqtypes = require("supervisor.session.svqtypes") local svqtypes = require("supervisor.session.svqtypes")
@ -20,7 +20,7 @@ local rtu = {}
local PROTOCOL = comms.PROTOCOL local PROTOCOL = comms.PROTOCOL
local SCADA_MGMT_TYPE = comms.SCADA_MGMT_TYPE local SCADA_MGMT_TYPE = comms.SCADA_MGMT_TYPE
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local print = util.print local print = util.print
local println = util.println local println = util.println
@ -113,7 +113,7 @@ function rtu.new_session(id, in_queue, out_queue, timeout, advertisement, facili
end end
local type_string = util.strval(u_type) local type_string = util.strval(u_type)
if type(u_type) == "number" then type_string = util.strval(comms.advert_type_to_rtu_t(u_type)) end if type(u_type) == "number" then type_string = types.rtu_type_to_string(u_type) end
-- create unit by type -- create unit by type

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -7,7 +6,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local boilerv = {} local boilerv = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local TXN_TYPES = { local TXN_TYPES = {
@ -39,7 +38,7 @@ local PERIODICS = {
function boilerv.new(session_id, unit_id, advert, out_queue) function boilerv.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.BOILER_VALVE then if advert.type ~= RTU_UNIT_TYPE.BOILER_VALVE then
log.error("attempt to instantiate boilerv RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate boilerv RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -7,7 +6,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local envd = {} local envd = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local TXN_TYPES = { local TXN_TYPES = {
@ -30,7 +29,7 @@ local PERIODICS = {
function envd.new(session_id, unit_id, advert, out_queue) function envd.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.ENV_DETECTOR then if advert.type ~= RTU_UNIT_TYPE.ENV_DETECTOR then
log.error("attempt to instantiate envd RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate envd RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -7,7 +6,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local imatrix = {} local imatrix = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local TXN_TYPES = { local TXN_TYPES = {
@ -39,7 +38,7 @@ local PERIODICS = {
function imatrix.new(session_id, unit_id, advert, out_queue) function imatrix.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.IMATRIX then if advert.type ~= RTU_UNIT_TYPE.IMATRIX then
log.error("attempt to instantiate imatrix RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate imatrix RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,6 +1,4 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local mqueue = require("scada-common.mqueue")
local rsio = require("scada-common.rsio") local rsio = require("scada-common.rsio")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -9,7 +7,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local redstone = {} local redstone = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local IO_PORT = rsio.IO local IO_PORT = rsio.IO
@ -54,7 +52,7 @@ local PERIODICS = {
function redstone.new(session_id, unit_id, advert, out_queue) function redstone.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.REDSTONE then if advert.type ~= RTU_UNIT_TYPE.REDSTONE then
log.error("attempt to instantiate redstone RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate redstone RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -7,7 +6,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local sna = {} local sna = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local TXN_TYPES = { local TXN_TYPES = {
@ -36,7 +35,7 @@ local PERIODICS = {
function sna.new(session_id, unit_id, advert, out_queue) function sna.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.SNA then if advert.type ~= RTU_UNIT_TYPE.SNA then
log.error("attempt to instantiate sna RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate sna RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local types = require("scada-common.types") local types = require("scada-common.types")
local util = require("scada-common.util") local util = require("scada-common.util")
@ -7,7 +6,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local sps = {} local sps = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
local TXN_TYPES = { local TXN_TYPES = {
@ -39,7 +38,7 @@ local PERIODICS = {
function sps.new(session_id, unit_id, advert, out_queue) function sps.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.SPS then if advert.type ~= RTU_UNIT_TYPE.SPS then
log.error("attempt to instantiate sps RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate sps RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end

View File

@ -1,4 +1,3 @@
local comms = require("scada-common.comms")
local log = require("scada-common.log") local log = require("scada-common.log")
local mqueue = require("scada-common.mqueue") local mqueue = require("scada-common.mqueue")
local types = require("scada-common.types") local types = require("scada-common.types")
@ -9,7 +8,7 @@ local unit_session = require("supervisor.session.rtu.unit_session")
local turbinev = {} local turbinev = {}
local RTU_UNIT_TYPE = comms.RTU_UNIT_TYPE local RTU_UNIT_TYPE = types.RTU_UNIT_TYPE
local DUMPING_MODE = types.DUMPING_MODE local DUMPING_MODE = types.DUMPING_MODE
local MODBUS_FCODE = types.MODBUS_FCODE local MODBUS_FCODE = types.MODBUS_FCODE
@ -51,7 +50,7 @@ local PERIODICS = {
function turbinev.new(session_id, unit_id, advert, out_queue) function turbinev.new(session_id, unit_id, advert, out_queue)
-- type check -- type check
if advert.type ~= RTU_UNIT_TYPE.TURBINE_VALVE then if advert.type ~= RTU_UNIT_TYPE.TURBINE_VALVE then
log.error("attempt to instantiate turbinev RTU for type '" .. advert.type .. "'. this is a bug.") log.error("attempt to instantiate turbinev RTU for type '" .. types.rtu_type_to_string(advert.type) .. "'. this is a bug.")
return nil return nil
end end