Repository navigation
Conversation
Reads LK's published Arc register list over Modbus TCP: per zone the room temperature, humidity, setpoint, override state, thermostat battery and signal strength, and how many of the zone's actuators are open. The list numbers registers from 1, so the wire address is the listed number minus one. Zones are found from a non-zero thermostat address, since an empty zone answers all zeros, and re-checked every half hour. The gateway is slow (up to about 3 s a read), so it is polled once a minute via set_poll_interval with a 180 s watchdog window, each zone is emitted as soon as it is read, and a register that fails three polls in a row is left alone until the next scan. Thermostat addresses are never emitted. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: hannesb90 <bruhn90@gmail.com>
In FTW the driver failed about every other poll. The test gateway is on Wi-Fi with 0.6-1.8 s round trips, so a read sometimes exceeds the host's 5 s request timeout, and the host then withholds the whole poll. - Two neighbouring zones are one request: 108 input registers from zone n's base cover zone n and n+1 (the gateway answers zeros between). - Setpoints, overrides and the operating mode are read every fifth poll. They are not re-emitted from an earlier read in between. - Serial and software version are one request. - A scan in which some zones did not answer keeps what the last scan said about them and is repeated after five polls. With three zones an ordinary poll is three requests instead of eight. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: hannesb90 <bruhn90@gmail.com>
hannesb90
marked this pull request as ready for review
November 10, 2026 16:15
miravoss26
reviewed
Nov 11, 2026
miravoss26
left a comment
There was a problem hiding this comment.
Adds a read-only LK Systems LK Arc gateway driver over Modbus TCP (zone temp, humidity, setpoint, override level).
- Security: nothing found. No writes, secrets, new dependencies or hosts. Control registers are only documented in a trailing comment, with a sensible note that a control step needs its own bounded lease.
- Correctness: range guards on temp, humidity and setpoint keep garbage register values out of the metrics. The override level conversion (255 to percent) rounds sensibly. Failure bookkeeping is per kind and address, so one dead register does not cost a timeout every poll.
- Note: verified on one gateway with three zones.
experimentalis the right status. No CI checks were attached when I looked.
Safe to merge from my read. I only skimmed the register map against the LK list, so a human should check that part.
Author
|
The register map has been checked by a human against the LK list. |
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
A new read-only driver for the LK Systems LK Arc underfloor heating gateway
over Modbus TCP. Toward srcfl/ftw#520: room temperatures from wall
thermostats on a heating system FTW cannot read today, for a later heat
planner to judge comfort by.
It emits metrics only, no power stream. Per zone with a paired thermostat:
zone_<n>_temp_c,zone_<n>_humidity_pct,zone_<n>_setpoint_czone_<n>_battery_pct,zone_<n>_signal_dbmzone_<n>_actuators_connected,zone_<n>_actuators_open_pct,zone_<n>_heating(any of the zone's actuators open)zone_<n>_override,zone_<n>_override_level_pctGateway-wide:
actuator_<a>_openfor each allocated actuator,lk_operating_mode(1 heating, 2 cooling) andlk_poll_ok.Driver evidence
lk_arc0.1.0, community tier.actuators.
(SENOFIEN.33.J.4, 2026-10-09), in the manifest's
upstream_docs. The listnumbers registers from 1 (
3:00101), so the wire address is the listednumber minus one. Confirmed on hardware: input 100 held zone 1's room
temperature and 101 its humidity.
drivers.NewLuaDriverwith areal Modbus TCP client, from a temporary program that is not part of
this PR) against the gateway, for two polls: all three zones reported
temperature, humidity, setpoint, battery, signal and actuator state, and
empty zones 4-12 were skipped. The temperatures (21.1, 20.8 and 19.0 °C)
matched a direct register read made a minute later.
POST /api/drivers/testcould not be used. It waits 8 s for thefirst telemetry, and one poll against this gateway takes longer (see
below). Telemetry reaches the store only when a poll ends.
make test-driver ID=lk_arcandmake checkpass.absent-register-report: every register settles.on an ordinary poll, settings every fifth poll. Deliberate breaks of the
zone pairing and of the settings cadence fail it.
invented-number-report: nothing invented.serial and thermostat addresses replaced by made-up numbers. It also
covers closed actuators, a negative temperature, an active override,
out-of-range values, no answer at all, one zone that stops answering,
and a register that keeps failing and is retried at the next scan.
Deliberate breaks of the give-up and the empty-zone check fail it.
The gateway is slow. It is on Wi-Fi here, with ping round trips of
0.6-1.8 s, and a single read took up to about 3 s, sometimes past the
host's 5 s request timeout. The host withholds a whole poll's telemetry
when any read in it fails to reach the device, and the first version
of this PR (eight requests per poll) failed about every other poll in
FTW. The driver therefore keeps requests few:
n's base cover zone n and n+1, within Modbus' 125 (the gateway
answers zeros, not an exception, for the undocumented addresses in
between, checked across 0-5000);
poll, and not re-emitted from an earlier read in between;
some zones did not answer keeps what the last scan said about them
and is repeated after five polls;
host.set_poll_interval(an intervalreturned from
driver_pollis capped at 30 s by the host) and asksfor a 180 s watchdog window via
host.set_watchdog_timeout_s;next scan.
With three zones an ordinary poll is three requests (actuators, zones
1-2, zone 3). After that change the driver ran as a configured FTW
driver for ten minutes: every poll succeeded, none failed.
The gateway accepts one TCP connection at a time, and closes an
idle one between polls (FTW logs a reconnect before each poll, with no
failed read). A second Modbus client on the same gateway makes FTW's
reads time out.
"Gateway number of zones" (
3:00051) read 0 on a gateway with threepaired zones, so it is not used. A zone counts as present when its
thermostat address is non-zero. An empty zone answers all zeros.
How often a thermostat updates its reading is not measured yet. The
readings changed between polls minutes apart, so it is not hours as with
some battery sensors.
What the gateway reports for a thermostat that has lost contact is
unknown. The list documents no stale flag, and none of the test
thermostats dropped out.
The gateway answered any unit id.
ders: [heatpump]is the closest of the allowed DER kinds. The gatewayis a heating controller, not a heat pump.
Safety
The thermostat addresses (SN/MAC) are read only to tell a paired zone from an
empty one, and are never emitted or logged. Only read function codes 3 and 4
are used.
Control evidence
required: not applicable, read-only.The register list has per-zone target temperature, override and override
level (0-255 = 0-100 % actuator opening). They are noted at the end of the
driver for a later control step. The list says nothing about the gateway
taking control back by itself, so that step needs its own lease and a
default that clears the override.
Checks
Signed-off-by.make test-driver ID=lk_arcmake check🤖 Generated with Claude Code