LearnSCADA

Part II · Chapter 5

Modbus RTU

For many people, RTU simply is Modbus: the Chapter 4 frame (address, PDU, error check) sent as compact binary bytes down a serial wire, usually the rugged two-wire bus called RS-485.

By the end of this chapter you can

  • Describe an RS-485 bus: daisy chain, A and B lines, termination, and bias.
  • Set and read serial settings such as "9600 8-E-1", and draw one character on the wire.
  • Explain how silence marks the edges of an RTU frame.
  • Say what the CRC does, trace it through a byte, and put it on the wire low byte first.

The wire: RS-485

Most RTU networks run over RS-485, an electrical standard built for exactly this job: reliable data over long distances, through electrically noisy plants, to many devices on one shared pair of wires. One bus can run over a thousand meters (about 1,200 m at typical Modbus speeds) and connect dozens of devices: 32 standard unit loads per segment, more with low-load transceivers or a repeater. You'll occasionally meet RS-232 too. The Modbus framing is identical, but RS-232 is point-to-point and short-range, so it can't form a multidrop bus.

An RS-485 bus is a daisy chain, not a star. The pair runs from device to device in a single line, and each device taps on as the line passes. The two conductors are usually labeled A and B. You'll also see D−/D+, −/+, or other names, and frustratingly, manufacturers don't agree on them. Most installations add a third conductor as a common signal ground.

An RS-485 daisy chain. A client and three servers connect in a single line to a twisted pair labeled A and B, plus a common wire. A 120 ohm termination resistor sits across A and B at each far end of the bus, and a bias network near the client holds the idle line in a known state. The two signal wires carry mirror-image square waves. A B COM mirror-image signals 120 Ω 120 Ω bias Client bus end Server 1 tap only Server 2 tap only Server 3 bus end One line, in and out of each device. Terminate only the two far ends.
Figure 5.1 · A Modbus RTU network on a two-wire RS-485 bus: devices daisy-chained on one pair (A and B), a 120 Ω terminator at each far end, and bias to hold the idle line steady.

Two practical details separate a bus that works from one that doesn't:

  • Termination. Each of the two far ends carries a resistor across A and B, typically 120 Ω to match the cable's impedance. It absorbs the signal at the end of the line so it doesn't reflect back and garble data on long or fast runs. Only the two ends, nowhere in the middle.
  • Bias. Gentle bias resistors, usually in one place on the bus, hold the line in a known state when nobody is transmitting, so the quiet between messages reads as a clean idle instead of random noise.

Many devices have switchable termination and bias. Knowing they exist saves hours when a long bus behaves erratically.

A and B aren't labeled the same everywhere One vendor's A is another's B, and some print D+/D− or +/− instead. If a correctly configured device won't answer, try swapping its two signal wires. Reversed polarity doesn't damage anything; it just stops communication.

Why two wires? Differential signaling

RS-485 is tough because it's differential. A receiver doesn't measure one wire against ground, which industrial noise easily corrupts. It looks only at the difference between A and B: which line is higher decides whether the bit is a one or a zero. Noise tends to strike both wires almost equally, pushing both voltages up or down together and leaving the difference nearly untouched. The signal rides in that difference, so the noise largely cancels.

Differential signaling. The top panel shows the A and B lines as mirror-image square waves measured against ground. A burst of noise pushes both lines up and down together. The bottom panel shows the difference between A and B, which stays clean and unchanged while the noise passes. A AND B, MEASURED AGAINST GROUND ground A B noise hits both wires WHAT THE RECEIVER READS: A − B A > B B > A The difference doesn't move: the noise cancels
Figure 5.2 · Differential signaling. The receiver reads the difference between A and B, not either line against ground. Noise that hits both wires equally cancels out.

Half-duplex: taking turns on one pair

A two-wire RS-485 bus is half-duplex: the same pair carries traffic both ways, but only one device may transmit at a time. That suits Modbus perfectly. Chapter 3's one-question-at-a-time discipline (the client speaks then listens; a server speaks only to answer) stops being mere manners and becomes a physical necessity. If two devices drove the pair at once, their signals would collide and both would be lost.

So each device switches its transmitter on only while it's sending, then releases the line. That turnaround happens in the quiet gaps between messages.

Serial settings that must match

Before two devices can exchange a single byte, they must agree on how each byte's bits are timed and shaped. Four settings are configured identically at both ends, and a mismatch is one of the most common reasons a freshly wired bus produces nothing but silence.

  • Baud rate: the speed in bits per second. 9600 and 19200 are common; 38400 and 115200 are widely supported.
  • Data bits: always 8 for RTU, because RTU sends whole bytes.
  • Parity: an optional check bit on each character (even, odd, or none) that catches some single-bit errors.
  • Stop bits: one or two, marking the end of each character.

They're written compactly: 9600 8-E-1 means 9600 baud, 8 data bits, even parity, 1 stop bit.

SettingTypical valuesNotes
Baud rate9600, 19200, 38400Must match exactly at both ends
Data bits8Always 8 for Modbus RTU
ParityEven, Odd, NoneEven is the specified default
Stop bits1 or 2Use 2 when parity is None, so every character stays 11 bits long

Here's what those settings produce on the wire. The line idles high. A start bit (low) announces a character, the eight data bits follow least significant bit first, then the parity bit, then the stop bit returns the line high. At 8-E-1 that's 11 bits per byte.

The byte 0x03 sent as one character at 8-E-1. The line idles high, drops for the start bit, then carries the data bits least significant first: 1, 1, 0, 0, 0, 0, 0, 0. The even parity bit is 0 because the data has two ones. The stop bit returns the line high. A highlight steps across the eleven bit cells in order. Byte 0x03 = 0000 0011, sent at 8-E-1 idle idle 0110 0000 001 start D0D1D2D3 D4D5D6D7 parity stop 8 data bits, least significant bit first even: two 1s → 0 1 start + 8 data + 1 parity + 1 stop = 11 bit times per byte
Figure 5.3 · A single character on a serial line: a start bit, eight data bits, an optional parity bit, and one or two stop bits. Every byte of an RTU frame travels in this shape.

Framing by silence

Here's the cleverest idea in RTU. A serial line is just a stream of characters with no built-in marker for "a new message starts here." RTU's answer is time. A frame is a burst of characters sent back to back, bracketed by silence: a gap of at least 3.5 character times (the time to send three and a half bytes at the current speed) marks the boundary. Once the line has been quiet that long, the next byte to arrive starts a fresh frame.

Inside a frame it works in reverse: the bytes must arrive in a tight stream with no gap longer than about 1.5 character times. A longer pause in the middle tells the receiver the frame was interrupted, and it throws the frame away.

Two timelines of the serial line. Top: the request 01 03 00 00 00 04 44 09 is sent back to back, followed by at least 3.5 character times of silence, then the server's 13-byte response and another silence. A cursor sweeps the line, and once the quiet after the request is long enough, the receiver treats the request as complete. Bottom: the same request with a pause longer than 1.5 character times in the middle, which the receiver discards. A GOOD EXCHANGE 01 03 00 00 00 04 44 09 Request ≥ 3.5 char ≈ 4.0 ms Response (13 bytes) ≥ 3.5 char Quiet for 3.5 characters: request complete, check the CRC A BROKEN FRAME 01 03 00 00 00 04 44 09 > 1.5 char gap Pause inside the frame: the receiver discards it, and the client sees silence.
Figure 5.4 · RTU frames are separated by silence: at least 3.5 character times between frames, and no gap longer than 1.5 character times inside one.

This framing is elegant and needs no special start or stop bytes, but it makes RTU sensitive to timing. Software reaching a serial port through layers of operating-system buffering, or a USB adapter or radio that delivers data in bursts, can smear these gaps. That's one reason dependable serial hardware matters more than it first appears.

Character-time calculator

QuantityTime

The CRC: catching corruption

The last two bytes of every RTU frame are the CRC, or cyclic redundancy check. Before sending, the transmitter runs every byte of the frame (address, function code, data) through a fixed procedure that boils them down to one 16-bit number, and appends it. The receiver runs the identical procedure over what it received and compares. If they match, the frame is almost certainly intact. If not, a byte was corrupted in transit, and the receiver silently discards the frame as if it never came.

The procedure is specific, sometimes written CRC-16/MODBUS. You don't need to derive it, but seeing it removes the mystery. The value starts at all ones, 0xFFFF. Each byte is mixed in with exclusive-or, then the value is shifted right one bit at a time, eight times. Whenever the bit shifted out was a 1, the value is combined with a fixed constant, the polynomial 0xA001. After the last byte, the 16-bit result is the CRC.

PYTHON — the Modbus CRC
def crc16(data):
    crc = 0xFFFF
    for byte in data:
        crc ^= byte
        for _ in range(8):
            if crc & 1:
                crc = (crc >> 1) ^ 0xA001
            else:
                crc >>= 1
    return crc

frame = bytes([0x01, 0x03, 0x00, 0x00, 0x00, 0x04])
crc = crc16(frame)
print(hex(crc))
print((frame + crc.to_bytes(2, "little")).hex(" "))
OUTPUT
0x944
01 03 00 00 00 04 44 09
Building the CRC for 01 03 00 00 00 04. The CRC register starts at FFFF. Each byte in turn is folded in, and the register reads 807E, 2140, F020, D8F1, 8419, and finally 0944. The result is appended to the frame low byte first, as 44 then 09. 01 03 00 00 00 04 44 09 CRC lo · hi CRC REGISTER FFFF 807E 2140 F020 D8F1 8419 0944 starts at FFFF 0x0944 low byte 44 first, then high byte 09 For each byte: XOR it in, then 8 × (shift right; if a 1 fell out, XOR A001) The receiver repeats the same work and compares its answer with the two CRC bytes it received.
Figure 5.5 · Building the CRC. Every byte of the frame is folded into a running 16-bit value; the result is appended to the frame and re-checked by the receiver.

Two facts about the CRC trip people up:

  1. It goes on the wire low byte first, the opposite of the big-endian order used everywhere else in the frame. The CRC value 0x0944 from our running example travels as 44 then 09.
  2. A bad CRC draws no exception. The receiver can't trust anything in a corrupted frame, not even the address, so it says nothing. To the client, a bad CRC looks exactly like silence, which is why CRC problems and wiring problems feel alike when you're troubleshooting.
Address Function code Data CRC
01address 03function 00 00start 0 00 04quantity 4 44CRC lo 09CRC hi

In practice you'll almost never compute a CRC by hand; every Modbus library does it. But knowing what it is keeps its failures from being baffling.

CRC step-through

CRCFFFF

StepWhat happensCRCBinary (lowest bit underlined)

Modbus RTU is the workhorse, and you now know its distinctive parts: the RS-485 bus it usually rides, the serial settings that must match, and the CRC and silence-based framing that make a serial frame self-contained. Before Ethernet, one more serial form: the older, human-readable Modbus ASCII, which trades RTU's efficiency for legibility.

Check your understanding

1. How does an RTU receiver know a frame has ended?

RTU has no delimiters and no length field. Silence of 3.5 character times separates frames.

2. A frame's CRC value is 0x0944. In what order do its bytes go on the wire?

The CRC is the one field sent low byte first, so 0x0944 travels as 44 09.

3. A server receives a frame whose CRC doesn't check out. What does the client see?

A corrupted frame can't be trusted, not even its address, so the server stays silent. That's why bad CRCs look like wiring faults.

4. Where do the 120 Ω termination resistors go on an RS-485 bus?

Termination absorbs the signal at the ends of the cable to stop reflections. Extra terminators in the middle load the bus and weaken the signal.