Cameras & sensorsTroubleshooting

Modbus 40xxx register offset: why your thermal camera returns no data

Why the 40xxx register in the manual is protocol address 1018 on the wire, why 1019 returns Modbus exception 02, and the offset fix with the frame bytes shown.

LumaSpec Vision10 min gelesen Auf LinkedIn teilen

Auf dieser Seite 9 Abschnitte
  1. 01Why does the camera answer exception 02 when you read the temperature register?
  2. 02What does the 40xxx prefix in the manual actually mean?
  3. 03Which address and quantity go on the wire for registers 401019-401020?
  4. 04How do you turn the two registers into a temperature in degrees Celsius?
  5. 05What else causes exception 02 when the offset is already correct?
  6. 06How does a GigE thermal camera feed a Modbus TCP network in the first place?
  7. 07How do you prove the fix before it reaches the PLC?
  8. 08Where else does this off-by-one bite on a mixed vision network?
  9. 09Questions

The manual says the hotspot temperature lives at holding registers 401019-401020. You send function code 03 for address 1019 and get back function code 83 with exception 02 instead of four data bytes. Nothing is broken: the camera is answering, and the exception is the answer. Documentation writes register numbers in the 4xxxx convention, which counts holding registers from one, while the Modbus TCP protocol counts addresses from zero on the wire. Subtract 400000, then subtract one more: register 401019 is protocol address 1018, hex 03FA, and the value spans two registers, so the quantity is two.

This page is for anyone wiring a thermal camera's Modbus TCP server into a PLC or SCADA system. You will leave with the corrected frame bytes, the float decoding arithmetic, a bench test plan, and the same rule applied to the rest of your network.

Why does the camera answer exception 02 when you read the temperature register?

Exception 02, illegal data address, is the camera telling you that the address you asked for does not exist in its register map: your frame requested protocol address 1019 (hex 03FB), while the manual's register 401019 actually lives at protocol address 1018 (hex 03FA).

Decode the exchange to see it. A request ending 6D 03 03 FB 00 01 that returns 6D 83 02 says three things: the leading byte echoes unit identifier 109, the 83 is function code 03 with the exception flag 0x80 set, and the trailing 02 is the illegal-data-address code. The Modbus specification defines exception 02 as a server unable to match the requested address-and-quantity combination to its map. Connection, port and unit identifier were all fine — the server answered within milliseconds. Your client showed no data because an exception frame carries no register values, only the complaint.

When the answer is silence rather than an exception, the fault sits one layer down. The thermal camera a vision SDK does not detect walks through that transport-level diagnosis.

What does the 40xxx prefix in the manual actually mean?

The 4xxxx prefix is a paper convention for naming holding registers, not part of the transmitted frame: 401019 means holding register number 1019 counted from one, so the zero-based address the protocol actually carries is 1019 − 1 = 1018, written on the wire as hex 03FA.

Two tables share this convention. Registers printed 3xxxx are input registers, read-only measurement values served with function code 04; registers printed 4xxxx are holding registers, served with function code 03. Five-digit notation (40001 through 49999) and six-digit notation (400001 through 465536) both appear in the field, and for this register they agree: strip the 4 and the leading zeros, then subtract one.

wire address = printed number − 40000 − 1 (5-digit notation) wire address = printed number − 400000 − 1 (6-digit notation) 401019 → 1019 − 1 = 1018 = 0x03FA

A third number is what your client tool displays, because tools differ: some accept the 40xxxx form and convert it for you, some want the one-based register number, and some want the raw zero-based address. The double-offset trap later in this page shows what happens when the tool converts as well.

Which address and quantity go on the wire for registers 401019-401020?

Send function code 03 with starting address 1018 (hex 03FA) and quantity 2, because the manual's 401019-401020 pair is one 32-bit value that begins one below the printed number and occupies two consecutive 16-bit registers.

Here is the corrected request, byte by byte, for unit identifier 109 (hex 6D):

Field Bytes Meaning
Transaction identifier 00 01 echoed in the response
Protocol identifier 00 00 fixed at zero for Modbus
Length 00 06 six bytes follow this field
Unit identifier 6D device 109
Function code 03 read holding registers
Starting address 03 FA decimal 1018
Quantity 00 02 two 16-bit registers

The address arithmetic: 1018 ÷ 256 = 3 remainder 250, and 250 is hex FA, so the byte pair 03 FA carries 1018. A healthy response reads 00 01 00 00 00 07 6D 03 04 42 48 00 00 — length field 0x0007, function code 03 echoed, byte count 04, then the four data bytes 42 48 00 00. One read with quantity 2 replaces two single-register reads, and it guarantees the pair comes from one update rather than two.

How do you turn the two registers into a temperature in degrees Celsius?

Join the two words high-first and decode the 32 bits as an IEEE 754 float: (0x4248 << 16) | 0x0000 gives 0x42480000, which decodes to exactly 50.0 °C, and most industrial thermal devices publish the pair in this form.

raw = (word_1019 << 16) | word_1020 most significant word first value = IEEE 754 float32 with bit pattern raw check: 0x42480000 → exponent 0x84 = 132 → scale 2^(132 − 127) = 32 fraction 0x480000 / 2^23 = 0.5625 → (1 + 0.5625) × 32 = 50.0 °C

If the number comes out absurd, suspect word order before you suspect the address. Swapped words — 0x00004248 — decode as a denormal near 2.4e-41, which every float printer renders as almost zero; that signature means the low word arrived first, so swap and decode again. Some manuals skip floats and publish a scaled integer instead: a scale of 0.1 °C per count turns a register value of 245 into 24.5 °C.

Close the loop on the bench either way: hold a warm cup in view and watch the decoded number rise, then fall as it cools. The longer path from raw counts to a calibrated temperature is its own subject — the raw thermal counts to temperature guide covers the calibration side.

What else causes exception 02 when the offset is already correct?

After the off-by-one fix, exception 02 usually comes from a second offset applied by your tool or gateway, a quantity that overruns the end of the block, or a register map that differs from the manual; test each with a one-register read at a known address.

Work down the list; each test settles one item in a read or two.

  1. The tool already converts. Many desktop clients accept 40xxxx-style entries or carry a zero-based-addressing switch, so typing 1018 into a tool that subtracts one for you reads address 1017. Test: read the same register in your own code and in the tool, then compare values.
  2. A gateway remaps the space. A TCP-to-serial gateway serving several devices folds each slave's registers into one large map, so the camera's 1018 may sit at another offset behind it. Test: read a register the gateway's own map guarantees, then work outward.
  3. The quantity crosses the end of the block. The specification judges the address-and-quantity combination, so a valid start with a quantity that runs past the last register returns 02. Test: repeat the read with quantity 1 at exactly 1018, then read 1019 on its own.
  4. The value lives in the other table. A temperature published as an input register (3xxxx) and read with function code 03 earns exception 02 on some devices and 01 on others. Test: send function code 04 to the same address.
  5. The map differs from the manual. Firmware variants shift register blocks. Test: scan with quantity 1 across a window such as addresses 1000 to 1050, note where reads succeed, and match a live value to a known scene such as an ambient view.

How does a GigE thermal camera feed a Modbus TCP network in the first place?

A camera that serves its data over GigE has no Modbus registers of its own: the temperature values arrive in the image stream or the SDK, and a small bridge program or gateway publishes them as holding registers for the PLC, which is where the addressing rule above applies.

The bridge is ordinary code: an acquisition loop that lifts the temperature values out of the camera's stream or SDK and serves them through a Modbus TCP server library on a small controller. The thermal camera data over RTSP and Modbus TCP on embedded Linux guide builds exactly this pattern, and the 16-bit thermal export guide shows how full temperature resolution survives the trip. When you write the server, you own the addresses: publish the temperature at a protocol address you document, and spare the next integrator the 40xxx archaeology.

A 640 × 512 LWIR camera over GigE slots into the line side, and a 640 × 512 LWIR module over USB3 suits a host-side bridge:

Infrared cameras640 x 512 thermal camera, 8-14 μm, 50 Hz, GigE, FOV 88.5° × 73.2°, 9-24 V DC (LS-IRC-0044)LS-IRC-0044
Lens mount
C-mount
Interface
GigE
Resolution
Up to 3 MP
Spectrum
LWIR
$5,885.00 · quotedView and quote
Infrared camerasLWIR thermal camera module, USB3, 640×512 resolution (LS-IRC-0016)LS-IRC-0016
Interface
USB3
$3,999.00 · quotedView and quote

The GigE camera reads 8-14 μm through a C-mount, so its optics come from the thermal, SWIR and UV lenses category, and both parts sit in the infrared cameras range.

How do you prove the fix before it reaches the PLC?

Prove it with three reads on a desktop test client before any PLC code is written: read two registers at address 1018, repeat with a warm target in view, then read an address you know is empty and confirm the camera still answers 02 there.

Run the sequence once, in this order:

  • Read quantity 2 at address 1018. Success is byte count 04 and four data bytes. This proves the address and quantity before anything hard-codes them.
  • Put a warm target in view and read again. The decoded float should move by a plausible amount. This proves you decoded the live pair, not a nearby static configuration register.
  • Read a known-empty address. Expect 83 02 within milliseconds. This proves device exceptions arrive as events your PLC can alarm on, not as timeouts.
  • Log raw frames for the first shift. The 83 02 tail separates device exceptions from link faults in any later review.
  • Map the registers into the PLC image last, and mark them read-only.

Where else does this off-by-one bite on a mixed vision network?

Every register your vision system exchanges over Modbus TCP obeys the same wire rule, so the convention you settle on here — protocol address, quantity, word order — carries unchanged to register handshakes, coordinate arrays and polled camera blocks.

The same questions recur wherever vision meets a PLC. The register handshake for sending vision coordinates defines a shared block of holding registers, and its addresses obey the same number-minus-one rule on the wire. The guide to sizing a coordinate array's registers applies the same quantity arithmetic to arrays, and the single poll loop for several cameras on Modbus TCP covers the scheduling side. More write-ups in this line sit on the systems topic page.

If the camera side of your bridge is still an open line item, start at the camera finder or send us the register map through the contact page and we will look the addressing over with you.

Fragen

What is the difference between function code 03 and function code 04 for a temperature read?

Function code 03 reads holding registers, the table a manual marks 4xxxx. Function code 04 reads input registers, marked 3xxxx, which hold read-only measurement values. The address arithmetic is identical — 301019 and 401019 both reduce to protocol address 1018 — so only the function code changes. Use the one the manual states: querying the wrong table earns exception 02 on some devices and exception 01, illegal function, on others.

Why do I get a timeout instead of exception 02 sometimes?

A timeout means no response reached you, so the failure sits earlier than addressing: wrong IP address or subnet, Modbus TCP port 502 blocked or routed elsewhere, a unit identifier the device rejects, or the camera's Modbus service not enabled in its own settings. Exception 02 is the opposite case — the link and the server are proven working, and only the address combination is wrong.

Can one request bring in several temperature values at once?

Yes, when the values sit in consecutive registers. Reading quantity 8 from address 1018 returns four consecutive 32-bit floats in one transaction, and the specification allows up to 125 registers per read of holding or input registers. Keep each 32-bit value aligned to an even start address, and read scattered addresses as separate requests rather than dragging a block across unmapped space.

Does the same conversion apply to a serial Modbus RTU device?

Yes. The number-minus-one rule lives in the protocol data unit, which RTU and TCP share; RTU wraps the identical request with a slave address byte and a CRC instead of the MBAP header. A manual register 401019 is protocol address 1018 on a serial line too, and exception codes carry the same meanings. Only the connector, the wiring and the timing differ.

How fast can I poll the temperature register?

On a switched Ethernet network a two-register read completes in a few milliseconds, so polling every 100 to 250 milliseconds is a light, comfortable load for the device and the PLC. Polling faster rarely buys anything, because values refresh at the camera's frame rate: a 50 Hz camera such as the LS-IRC-0044 updates each published value at that rate already. Match the interval to how quickly your process actually changes.