Write Modbus RTU multimeter values to KNX/EIB bus group addresses
Example: Write Modbus RTU multimeter values to KNX/EIB bus group addresses
Task
Read two parameters (3-phase system voltage, 3-phase system current) from ABB DMTME Multimeter and store the data in the KNX group addresses. Make sure to connect LM2 with Modbus device correctly, RS485 A with -, RS485 B with +.
Adding KNX objects
In Objects tab two new KNX objects should be added. In this case:
- 5/5/1 – for writing 3-phase system voltage
- 5/5/2 – for writing 3-phase system current
Modbus program
- In Logic Machine -> Scripting a new Resident script should be added which will periodically run the program and update KNX group addresses with Modbus data readings
- Click on the Editor icon of the respective script to jump to Scripting editor where the following program is added
- -- init modbus on first script execution
- if not mb then
- require('luamodbus')
- mb = luamodbus.rtu()
- mb:open('/dev/ttyS2', 9600, 'E', 8, 1, 'H')
- mb:connect()
- end
-
- -- sets slave ID to read/write data from/to
- mb:setslave(20)
-
- -- read 3-phase system voltage from 32-bit register
- r1, r2 = mb:readregisters(0x1000, 2)
- result = bit.lshift(r1, 16) + r2
- grp.write('5/5/1',result)
-
- -- read 3-phase system current from 32-bit register
- r1, r2 = mb:readregisters(0x100E, 2)
- result = bit.lshift(r1, 16) + r2
- grp.write('5/5/2',result)
Note! Modbus data is most often read and written as 16-bit registers. If a 32-bit is required, these values have to be read as a pair of registers, like in this example.
Note! All data addresses in Modbus messages are referenced to zero. The first occurrence of a data item is addressed as item number zero. For example: The coil known as ‘coil 1’ in a programmable controller is addressed as coil 0000 in the data address field of a Modbus message.
Read encoded Modbus values
To read and decode 32bit float value from Modbus meter use this example
- r1, r2 = mb:readregisters(3000, 2)
-
- if r1 then
- value = bit.lshift(r1, 16) + r2
- value = lmcore.inttohex(value, 4)
- value = knxdatatype.decode(value, dt.float32)
-
- grp.write('5/5/1', value)
- end
Visualizing Modbus objects
By using grp.write command assign Modbus object to KNX object and then use this new KNX object in the visualization.
More Modbus communication commands
- Open Modbus TCP connection:
- if not mb then
- require('luamodbus')
- mb = luamodbus.tcp()
- mb:open('192.168.1.1', 1502)
- mb:connect()
- end
- Reads count registers/coils from the start address and return all values on success and nil, error description on error:
- mb:readcoils(start, count)
- mb:readdiscreteinputs(start, count)
- mb:readregisters(start, count)
- mb:readinputregisters(start, count)
- Write values to registers/coils from the start address. Single write will be used when only one value is supplied, multiple write otherwise. Returns all of values written on success and nil, error description on error:
- mb:writebits(start, v1, [v2, [v3, ...]])
- mb:writeregisters(start, v1, [v2, [v3, ...]])
- Read slave internal data. Returns values on success and nil, error description on error:
- mb:reportslaveid()