Skip to content

ragtech: make the iout_calib ups.conf override actually take effect - #3795

Open
juslex wants to merge 3 commits into
networkupstools:masterfrom
juslex:fix/ragtech-iout-calib-override
Open

juslex wants to merge 3 commits into
networkupstools:masterfrom
juslex:fix/ragtech-iout-calib-override

Conversation

@juslex

@juslex juslex commented Oct 21, 2026

Copy link
Copy Markdown
Contributor

upsdrv_initups() parses the iout_calib option into iout_calib, but upsdrv_initinfo(), which main.c runs afterwards, then assigned the value of register 0xF3 over it unconditionally. Since the UPS always answers that read, the documented option had no effect at all.

This change remembers whether the option was given and, in that case, only logs the register value (at -D) instead of overwriting the configured one. Without the option, behaviour is unchanged.

Why it matters

Rebadged units. A "One Up Nitro 2000", whose firmware reports the Easy 2000 TI model id, stores 70 in register 0xF3 where 140 is correct, so output.current and ups.load came out exactly twice the real value; the implied output VA even exceeded the input power measured at the wall. With the override working, output.current matches the load's measured consumption across a three-point load sweep (idle, ~305 W and ~555 W of DC load: 2.02x, 1.96x and 2.12x correction, i.e. a constant factor of two, not a non-linearity).

This has been running on that unit in production since early August.

The man page now documents the precedence and how to calibrate against a clamp meter or a known load.

Note on #3716

#3716 (battery runtime model) inserts its rt_enabled block right above the 0xF3 read in upsdrv_initinfo(), so whichever lands second needs a trivial textual rebase: keep both blocks, with this change's iout_calib_override check after the runtime block. There is no semantic overlap, but the runtime model derives its load from output.current, so on units like the one above this fix is what makes the runtime estimate meaningful. Happy to rebase after #3716 is merged.

🤖 Generated with Claude Code

upsdrv_initups() parsed the "iout_calib" option into iout_calib, but
upsdrv_initinfo() -- which main.c runs afterwards -- then assigned the
value of register 0xF3 over it unconditionally. Whenever the UPS
answered that read, which is always, the documented option had no
effect at all.

Remember whether the option was given and keep the register value out
of the way in that case, logging what the register reported so the
difference stays visible with -D.

This matters on rebadged units. A "One Up Nitro 2000" reports the Easy
2000 TI model id and stores 70 in register 0xF3 where 140 is correct,
so output.current and ups.load come out exactly twice the real value --
the implied output VA exceeded the input power measured at the wall.
With the override working, output.current agrees with the load's
measured consumption across a three-point load sweep (idle, ~305 W and
~555 W of DC load: 2.02x, 1.96x and 2.12x correction, i.e. a constant
factor of two rather than a non-linearity).

Also document the precedence and how to calibrate against a clamp
meter in the man page.

Signed-off-by: juslex <66561713+juslex@users.noreply.github.com>
@github-actions

github-actions Bot commented Oct 21, 2026 •

Copy link
Copy Markdown

A ZIP file with standard source tarball and another tarball with pre-built docs for commit 841b2fe is temporarily available: NUT-tarballs-PR-3795.zip.

juslex and others added 2 commits October 21, 2026 16:11
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Signed-off-by: juslex <66561713+juslex@users.noreply.github.com>
@AppVeyorBot

Copy link
Copy Markdown

✅ Build nut 2.8.5.5890-master completed (commit 452f92751b by @jimklimov)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants