Technical reference Β· Doc CP-MODBUS-RTU Β· Rev 1 Β· June 2026
CoolPro Modbus RTU Communications Protocol
Communication parameters, frame timing, RJ45 pinout and bus topology, supported function codes, the full register map, data encoding with worked CRC, and example transactions for integrating the AERL CoolPro into a Modbus RTU network over RS485.
| Parameter | Value |
|---|---|
| Standard | Modbus RTU |
| Physical layer | RS485 Β· RJ45 |
| Default baud rate | 9600 bps |
| Frame format | 8Β·NΒ·1 |
| Default device address | 40 |
| CRC | CRC-16 (transmitted LSB first) |
1. Bus, connection & settings
The CoolPro provides access to real-time measurements and device information via the standard Modbus RTU protocol over RS485.
Communication parameters
| Parameter | Value |
|---|---|
| Baud rate | 9600 (default); configurable: 9600 / 19200 / 38400 / 57600 / 115200 |
| Data bits | 8 |
| Stop bits | 1 |
| Parity | None |
| Device address | 40 (default); configurable 1β247 |
| CRC | Modbus CRC-16 (transmitted LSB first) |
Frame timing
Modbus RTU frames are delimited by idle time on the bus: a frame is treated as complete once the bus has been silent for the inter-frame gap period. The CoolPro uses a fixed inter-frame gap of approximately 8Β ms, independent of the configured baud rate. This is comfortably wider than the 3.5-character silent interval required by the Modbus specification at every supported baud rate, so a standard-compliant master will interoperate without adjustment.
Physical connection (RJ45 pinout)
The CoolPro uses an 8-pin RJ45 connector for its RS485 interface (contacts numbered 1 to 8, left to right, viewed from the front). All other pins are unused.
| Pin | Signal |
|---|---|
| 3 | RS485-A (non-inverting) |
| 6 | RS485-B (inverting) |
| 8 | GND |
Network topology
The Modbus network is a linear bus, with short stubs branching from βTβ connectors on the main backbone to each device. The data lines must be terminated at each end of the bus with a 120Β Ξ© resistor between the RS485-A and RS485-B signals.
2. Supported function codes
0x03 Read Holding Registers
Read one or more configuration registers.
| Frame | Bytes | Notes |
|---|---|---|
| Request | [Device ID] [0x03] [Start Addr Hi] [Start Addr Lo] [Qty Hi] [Qty Lo] [CRC Lo] [CRC Hi] | Frame structure |
| Response | [Device ID] [0x03] [Byte Count] [Dataβ¦] [CRC Lo] [CRC Hi] | Frame structure |
| Request | 28 03 00 00 00 01 [CRC] | Read 1 register starting at 0 (device address) |
| Response | 28 03 02 00 28 [CRC] | Byte count = 2, value = 40 (0x0028) |
| Request | 28 03 00 00 00 03 [CRC] | Read 3 registers starting at 0 |
| Response | 28 03 06 00 28 00 00 00 00 [CRC] | Byte count = 6, three register values |
0x04 Read Input Registers
Read one or more input registers containing measurements or device information.
| Frame | Bytes | Notes |
|---|---|---|
| Request | [Device ID] [0x04] [Start Addr Hi] [Start Addr Lo] [Qty Hi] [Qty Lo] [CRC Lo] [CRC Hi] | Frame structure |
| Response | [Device ID] [0x04] [Byte Count] [Dataβ¦] [CRC Lo] [CRC Hi] | Frame structure |
| Request | 28 04 00 00 00 01 [CRC] | Read 1 register starting at 0 (input voltage in mV) |
| Response | 28 04 02 5F B4 [CRC] | Byte count = 2, value = 24500 (0x5FB4 = 24.5 V) |
| Request | 28 04 00 00 00 04 [CRC] | Read 4 registers starting at 0 (Vin, Iin, Vout, Iout) |
| Response | 28 04 08 5F B4 0C B2 5D C0 0C 80 [CRC] | Vin = 24.5 V, Iin = 3.25 A, Vout = 24.0 V, Iout = 3.20 A |
0x06 Write Single Register
Write a configuration register (device address, baud rate, or reset trigger).
| Frame | Bytes | Notes |
|---|---|---|
| Request | [Device ID] [0x06] [Register Hi] [Register Lo] [Value Hi] [Value Lo] [CRC Lo] [CRC Hi] | Frame structure |
| Response | [Device ID] [0x06] [Register Hi] [Register Lo] [Value Hi] [Value Lo] [CRC Lo] [CRC Hi] | Echo of request |
| Request | 28 06 00 00 00 2A [CRC] | Write device address = 42 |
| Response | 28 06 00 00 00 2A [CRC] | Echo confirms write |
3. Modbus register map
Addressing
Register reference numbers (4xxxx for holding registers, 3xxxx for input registers) are a documentation convention only. The value placed on the wire is the zero-based PDU address, shown in the Offset column β that is, on-wire address = reference number β 40001 (holding) or β 30001 (input) = the offset. Holding register 40001 is addressed on the wire as 0x0000 (function 0x03 / 0x06); input register 30001 is addressed on the wire as 0x0000 (function 0x04). The function code β not the reference range β selects the address space, so the same on-wire address 0x0000 reads the device address under 0x03 and the input voltage under 0x04.
Holding registers (FC 0x03, 0x06)
Configuration registers (read / write). All values are uint16.
| Address | Offset | Description | Range | Notes |
|---|---|---|---|---|
| 40001 | 0 | Device Address | 1β247 | Takes effect after reset |
| 40002 | 1 | Baud Rate Index | 0β4 | 0 = 9600, 1 = 19200, 2 = 38400, 3 = 57600, 4 = 115200; takes effect after reset |
| 40003 | 2 | Reset Command | β | Write 0xAA55 to trigger a reset; always reads 0 |
Reset register read-back: register 40003 is a write-only command trigger. A read always returns 0 regardless of the value last written β this is expected behaviour, not a fault. The written value initiates the reset and is never stored.
Input registers (FC 0x04) β live telemetry (offsets 0β7)
All values are uint16 with milliunit scaling.
| Address | Offset | Description | Unit | Conversion |
|---|---|---|---|---|
| 30001 | 0 | Input Voltage | mV | voltage_v = value / 1000 |
| 30002 | 1 | Input Current | mA | current_a = value / 1000 |
| 30003 | 2 | Output Voltage | mV | voltage_v = value / 1000 |
| 30004 | 3 | Output Current | mA | current_a = value / 1000 |
| 30005 | 4 | Temperature | mΒ°C | temp_c = value / 1000 |
| 30006 | 5 | Uptime (Low Word) | s | Low 16 bits of uptime |
| 30007 | 6 | Uptime (High Word) | s | High 16 bits of uptime |
| 30008 | 7 | Status Flags | β | Bit field (see below) |
Status Flags bit field (register 30008)
A 16-bit bit field. Each bit reports a specific system condition and can be set or cleared independently.
| Bit | Hex | Name | Description |
|---|---|---|---|
| 0 | 0x0001 | System Startup | Device is initialising (cleared once startup completes) |
| 1 | 0x0002 | Daily Reset | Daily reset has occurred (uptime counter reset) |
| 2 | 0x0004 | Input Measurement Fault | Fault communicating with the input measurement sensor |
| 3 | 0x0008 | Output Measurement Fault | Fault communicating with the output measurement sensor |
| 4 | 0x0010 | Calibration Invalid | Stored calibration data failed validation |
| 5 | 0x0020 | Calibration Missing | No calibration data stored |
| 6 | 0x0040 | Temperature Sensor Fault | Fault communicating with the temperature sensor |
| 7β15 | β | Reserved | Reserved for future use (currently 0) |
Device information registers (offsets 100β107)
| Address | Offset | Description | Type | Notes |
|---|---|---|---|---|
| 30101 | 100 | Serial Number Low | uint16 | Low 16 bits |
| 30102 | 101 | Serial Number High | uint16 | High 16 bits |
| 30103 | 102 | Hardware Revision | uint16 | e.g. 1, 2, 3 |
| 30104 | 103 | Firmware Major Version | uint16 | e.g. 1 |
| 30105 | 104 | Firmware Minor Version | uint16 | e.g. 0 |
| 30106 | 105 | Firmware Patch Version | uint16 | e.g. 0 |
| 30107 | 106 | Manufacture Date Low | uint16 | Unix timestamp low word |
| 30108 | 107 | Manufacture Date High | uint16 | Unix timestamp high word |
4. Data encoding
16-bit registers
Byte order is big-endian (MSB first). Example: value 24500 (0x5FB4) is transmitted as [0x5F, 0xB4].
Milliunit scaling
All measurements use milliunits so values carry as integers without floating point: voltage in millivolts (mV), current in milliamps (mA), temperature in millidegrees Celsius (mΒ°C) β divide by 1000 for volts, amps or Β°C. For example, an input-voltage reading of 24500 is 24.5Β V, and a temperature reading of 25800 is 25.8Β Β°C.
32-bit values
Uptime, serial number and manufacture date span two uint16 registers: low word first, high word second, big-endian within each register. Reconstruct with (high << 16) | low. Example β value 70000 (0x00011170) is stored as register N (low) = 0x1170 (4464), register N+1 (high) = 0x0001 (1). All values are transmitted as integers; no floating-point encoding is used.
| Quantity | Register value | Meaning |
|---|---|---|
| 24.5 V | 24500 | 24500 mV |
| 3.25 A | 3250 | 3250 mA |
| 25.8 Β°C | 25800 | 25800 mΒ°C |
| Uptime 70000 s | offset 5 = 4464, offset 6 = 1 | Combined: 0x0001_1170 |
CRC-16
Every frame ends with a 16-bit CRC computed over all preceding bytes using polynomial 0xA001 with an initial value of 0xFFFF, and transmitted low byte first.
| Frame (without CRC) | CRC-16 | On the wire (CRC appended, low byte first) |
|---|---|---|
28 04 00 00 00 01 | 0x3336 | 28 04 00 00 00 01 36 33 |
28 04 02 5F B4 | 0x71DD | 28 04 02 5F B4 DD 71 (response) |
5. Exception codes
Standard Modbus exception responses. Exception response frame: [Device ID] [Function Code + 0x80] [Exception Code] [CRC Lo] [CRC Hi]
| Code | Name | Description |
|---|---|---|
0x01 | Illegal Function | Function code not supported |
0x02 | Illegal Data Address | Register address invalid |
0x03 | Illegal Data Value | Value out of range |
0x04 | Slave Device Failure | Device cannot process the request |
6. Example transactions
All requests are addressed to device ID 0x28 (40). CRC bytes are shown as [CRC]; worked CRC values are given in Β§4 Data encoding.
Telemetry & identity
| Frame | Bytes | Notes |
|---|---|---|
| Read input voltage β FC 0x04, offset 0 | ||
| Request | 28 04 00 00 00 01 [CRC] | 8 bytes total |
| Response | 28 04 02 5F B4 [CRC] | 7 bytes; value 0x5FB4 = 24500 mV = 24.5 V |
| Read input current β FC 0x04, offset 1 | ||
| Request | 28 04 00 01 00 01 [CRC] | Read 1 register at offset 1 |
| Response | 28 04 02 0C B2 [CRC] | Value 0x0CB2 = 3250 mA = 3.25 A |
| Read temperature β FC 0x04, offset 4 | ||
| Request | 28 04 00 04 00 01 [CRC] | Read 1 register at offset 4 |
| Response | 28 04 02 64 C8 [CRC] | Value 0x64C8 = 25800 mΒ°C = 25.8 Β°C |
| Read serial number β FC 0x04, offsets 100β101 (split low / high word) | ||
| Request | 28 04 00 64 00 02 [CRC] | Option 1 β read both registers at offset 100 |
| Response | 28 04 04 30 39 00 00 [CRC] | Byte count = 4; Low = 0x3039, High = 0x0000 |
| Request | 28 04 00 64 00 01 [CRC] | Option 2 β read offset 100 individually |
| Response | 28 04 02 30 39 [CRC] | Low word = 0x3039 = 12345 |
| Request | 28 04 00 65 00 01 [CRC] | Read offset 101 individually |
| Response | 28 04 02 00 00 [CRC] | High word = 0x0000. Reconstruct: serial = 12345 |
Configuration writes
| Frame | Bytes | Notes |
|---|---|---|
| Read device address β FC 0x03, holding register 0 | ||
| Request | 28 03 00 00 00 01 [CRC] | Read 1 register at offset 0 |
| Response | 28 03 02 00 28 [CRC] | Value 0x0028 = 40 (device address) |
| Write device address β FC 0x06, holding register 0 | ||
| Request | 28 06 00 00 00 2A [CRC] | New device address = 42 (0x002A) |
| Response | 28 06 00 00 00 2A [CRC] | Echo. Changes take effect after a device reset |
| Trigger device reset β FC 0x06, holding register 2 | ||
| Request | 28 06 00 02 AA 55 [CRC] | Reset trigger value 0xAA55 |
| Response | 28 06 00 02 AA 55 [CRC] | Echo. Device resets immediately after sending the response |
7. Revision history
| Rev. | Date | Change | Approving officer |
|---|---|---|---|
| 1 | 2026-06-08 | Initial customer release | Matthew Wynne |
Integrating the CoolPro into a SCADA or monitoring system? Talk to our engineering team or see the CoolPro product page for datasheets and manuals.