This document intends to detail the change log for relatively recent work (roughly since the source code was tracked in Git).
This change log section represents git commits in range v2.8.5..HEAD (commits 0e051f9f6..1c4ab78c6).
ifnamelen to satisfy compiler warnings
.pwfile lacks trailing newline and is
read same way on different systems [#3331]
... obsolete, use
$(…)" warnings that e.g. ksh93 (the /bin/sh on illumos and
Solaris) prints in syntax-check mode for each use of backticks,
which NUT scripts use deliberately for portability: on current
master, "ksh -n" printed 1442 of these for 47 scripts, which buried
the 15 other warnings it had. The output is captured before
filtering, so the syntax check exit code is kept. The filter uses
$(EGREP) with bracket expressions, rather than "grep -F", for older
grep implementations. Checked with SHELL_PROGS="dash ksh bash"
(ksh 93u\+m/1.0.8): all scripts pass, no backticks warnings are
left, the other ksh warnings are still shown; and that syntax
errors in a POSIX or a Bourne-Again shell script fail the check,
naming the file and the shell. Spellcheck and distcheck-light pass.
Closes: #1058 Closes: #1059 Co-Authored-By: Claude Opus 5.5
<noreply@anthropic.com>
CI_AUTOGEN_STABLE_VERSION never appeared in a release
so not worth mentioning in these notes [#3759]
X.Y.Z.0(.0...) [#3759]
make clean, and others succumb to git clean -fdX.
Jenkinsfile-dynamatrix [#3757]
.bat for
cmd steps, .ps1 for ps. Script names are numbered by the
position of their section among the AppVeyor pipeline script phases
(02-install, 03-before_build, …, 08-after_test), so the numbers
stay stable if more phases get used later. The commands are moved
verbatim (same order). AppVeyor checks the exit code of each line
in inline scripts, but only of the last one for a called .bat, so
each command is followed by an errorlevel check to keep failing
fast (with the original exit code). init stays inline, as it
runs before the repository is cloned. The trailing ccache stats of
after_test are now reported by the .bat before (not after) the
artifact link message. Use of coding helper tools and AI
disclosed: Claude Code was used. Co-Authored-By: Claude Opus 5.5
<noreply@anthropic.com>
\%s.dll Add
combase, hid, setupapi, shfolder, wship6 and xmllite to the list of
OS-provided DLLs, which were reported as not found (strings
matcher) for every NUT for Windows bundle on AppVeyor. The
%s.dll format-string filter missed a \%s.dll hit (backslash
path separator in a format string); read later stripped the
backslash, so it was reported as not found as %s.dll. Allow a
leading path. Checked against the AppVeyor build 5659 bundle:
identical DLL list, these 7 warnings gone, no new ones. Use of
coding helper tools and AI disclosed: Claude Code was used.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
strings
scanned whole files, including debug sections: for the NUT for
Windows bundle (616MB of -g3 binaries) that produced 561MB of text,
all piped through tr/grep/sort, which dominated the DLL scan of
make install-win-bundle (\~2 min in the first pass on AppVeyor).
With strings -d (data sections only, as older binutils did by
default) it is 2.8MB, and the same candidate DLL names. Fall back
to a whole-file scan if strings lacks the option. Similarly use
objdump -p (private headers, with the PE import table and ELF
NEEDED entries) instead of -x, which also dumped symbol tables
and relocations (37MB vs 9.8MB of text here). Checked against the
AppVeyor build 5659 bundle: identical results and warnings to the
original script. Use of coding helper tools and AI disclosed:
Claude Code was used. Co-Authored-By: Claude Opus 5.5
<noreply@anthropic.com>
|| \ typo (vs. |\| \ line continuation), which ran a command
named \ and then the cp -L fallback unconditionally. Use of
coding helper tools and AI disclosed: Claude Code was used.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
init, and run the long bash steps
(prereqs, build, check, spellcheck, bundle) under timeout with
the time left. If they would run past it, the job fails instead,
and APPVEYOR_SAVE_CACHE_ON_ERROR keeps what was built, with at
least \~5 minutes left for 7z, artifacts and the cache save. Use of
coding helper tools and AI disclosed: Claude Code was used.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
make still generates nut_version.h from Git, so programs report
the actual version. Use of coding helper tools and AI disclosed:
Claude Code was used. Co-Authored-By: Claude Opus 5.5
<noreply@anthropic.com>
find per DLL name over DESTDIR and over
each input directory. Once recursion reaches e.g. /mingw64/bin,
this means hundreds of walks over a large directory, which is slow
on MSYS2 (about 5 minutes of make install-win-bundle in AppVeyor
CI). List those locations once per call and match base names with
awk. Listing order is kept, so the first hit is the same file as
before. Use of coding helper tools and AI disclosed: Claude Code
was used. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
upscli_get_default_connect_timeout() returns void and writes
through its argument, while strarr_alloc() takes size_t and
initialises the allocated pointers to NULL. This makes the
documented declarations usable against the current headers.
Correct the daisychain alarm guidance: the count aggregates alarms
within an update cycle, so an empty later device does not cancel an
earlier device’s alarm. Include status-buffer initialisation and
the status_commit() then alarm_commit() order used by the SNMP
driver to retain the aggregate alarm state. Align Qx and SNMP
mapping references with their actual types. Repair protocol, API,
appendix and upgrade-file references, point SSL context references
to the official OpenSSL documentation, and direct SNMP extension
readers to the existing guide. Remove GitHub SVN instructions
following the service’s retirement; correct the USB expansion and
frame the listed HID vendors as examples. Validation passed:
original API declarations fail against the current headers and
corrected declarations compile; extracted daisychain helpers
confirm alarm-count behaviour. Source checks, real renders of all
changed manuals, single-page and chunked guides, rendered links,
spelling, ASCII/whitespace checks and make -j2 distcheck-light
pass. The official OpenSSL destination returned HTTP 200 with the
correct documentation title. The unchanged libnutclient_tcp
warning and 27 baseline maintainer-guide spelling diagnostics
reproduce unchanged. AI assistance: GPT-6 Astra coordinated the
work and performed the final review; GPT-6.1 Sol assisted with
checks and drafting.
DEADTIME to suppress polling warnings, but
this delays the protection applied when a UPS last known to be on
battery becomes unreachable. Point readers to
POLLFAIL_LOG_THROTTLE_MAX and NOCOMMWARNTIME for the
corresponding log and notification controls. Clarify that losing
UPS communication does not immediately shut down every computer:
the last known UPS state, DEADTIME and configured power
requirements determine the response. Keep the warning about
powering communication equipment from managed outlets. Also correct
the certificate-expiry comparison, remove the startup-only claim
about upsd device definitions, and align the debug stream and
polling-interval descriptions with the implementation. Document
the existing scanner thread limit, complete the notification lists
and replace the outdated SSL-directive disclaimer with links to the
configuration manuals. This changes documentation only. Validation
passed: source and notification-inventory checks, real HTML and
roff renders of all changed manuals, single-page and chunked
guides, affected links, spelling, ASCII/whitespace checks and make
distcheck-light. The unchanged libnutclient_tcp rendering
warning reproduces on the baseline. AI assistance: GPT-6 Astra
coordinated the work and performed the final review; GPT-6.1 Sol
assisted with checks and drafting.
usbhid-ups's
onlinedischarge_onbattery spelling and replace belkinunv's
claim that it has no configuration settings with a reference to its
documented options. Document Microdowell shutdown and restart
delays, including their defaults and bounds. Distinguish the stored
shutdown delay from the minimum six-second delay used when sending
a command. Explain that runtime updates affect the running instance
and configured values are loaded again on restart, including a
separate -k invocation; this matters when preparing a shutdown
command. Document NHS model-name overrides and bypass-alarm
control, including their limits and defaults. Add the two existing
option names to the spelling dictionary. No driver behaviour
changes. Validation passed: registered-option and implementation
checks, real HTML and roff renders of all four changed manuals, the
Belkin section link, spelling, ASCII/whitespace checks and make
distcheck-light. Source-extracted checks exercise Microdowell
defaults, bounds and command construction, and NHS model and alarm
handling with surrounding operations stubbed. No physical UPS was
exercised. The unchanged libnutclient_tcp rendering warning
reproduces on the baseline. AI assistance: GPT-6 Astra coordinated
the work and performed the final review; GPT-6.1 Sol assisted with
checks and drafting.
timestamps too [#3669]
upsset.cgi [#3668]
microdowell driver,
but the RS232 port of this unit transmits nothing at all (see
#3712), so the USB entry is listed separately and conservatively at
level 2. Not mapped on purpose, both documented in the source:
UPS.PowerSummary. PercentLoad is declared but stayed 0 throughout
that battery run with a real load, and RunTimeToEmpty always reads
0xFFFF ("unknown"). Output voltage is also left out - the declared
Output.Voltage field is constant on this firmware, while an
undocumented field one byte earlier does track the line.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
apcmicrolink driver
into one [#3714]
NEWS.adoc and UPGRADING.adoc
drivers/apcmicrolink-usb.c, drivers/apcmicrolink-usb.h, drivers/apcmicrolink.c: apcmicrolink: USB: keep the report’s zero padding away from the frame scanner Every tunnel Input report carries one Microlink record followed by 0x00 padding up to the report’s fixed size (observed on a Smart-UPS X 1500, FW "UPS 16.0": a 35-byte record plus 28 zero bytes, in 13,040 of 13,040 reports). The frame scanner works on a byte stream and takes the first offset at which the checksum validates. Leading zero bytes are invisible to the Fletcher-mod-255 checksum, so a record whose last check byte is 0xFF (and whose byte 32 is non-zero) also validates one byte early. The scanner then takes it for a page 0, the guard from f0a4525 rightly rejects that page 0 ("ignoring implausible page0
upsd block [#3709]
mfr and model string options and their defaults for
liebert, whose manual previously said it had no extra settings.
For hwmon_ina219, I documented sysfs_dir and its port=auto
condition, corrected the hwmon directory path, and added the
integer range and default for the low battery threshold. I also
added a NEWS entry. I checked each description against the option
registration and consuming code. The affected man pages and HTML
pages build through the project recipes and pass the manual checks.
ASCII and whitespace checks, and make distcheck-light, passed.
Full make spellcheck passed with a local dictionary supplement
for kernel's and firmware's, which also fail on unchanged
upstream with the installed Aspell dictionary; the project
dictionary is unchanged. Related to #2422. This covers the two
driver manuals and leaves the wider option audit open. I prepared
this change with assistance from OpenAI Codex.
upssched -l narrows each
timer’s time_t expiry to long before printing it. On systems
with 64-bit time_t and 32-bit long, dates beyond January 2038
can be truncated or displayed as negative timestamps. Use the
existing intmax_t formatting convention and add a regression that
checks the actual LIST-TIMERS response around the 2038 boundary
and in 2100. Related to #3096. Validated with native
Windows/MinGW64 failing-before/passing-after checks and the full
CLI using disposable pipes, including a short timer and
cancellation. Linux normal and forced-fallback checks, the
configured test suite and distcheck-light passed. The changed
release notes render correctly through the project’s HTML target.
Spellchecks used a temporary dictionary containing two pre-existing
rejected possessives; the project dictionary is unchanged. AI
assistance: OpenAI Codex was used to prepare the change and tests.
nutupsdrv(8) example for
cancelling a pending shutdown through the existing sdcommands
facility, with a cross-reference to ups.conf(5). The text
explains command-line precedence, fallback ordering and why the
driver daemon must be stopped for this override. The example uses
-F to keep the driver in the foreground. #2686 introduced the
functionality requested in #1677; this change documents its use
from the command line. I verified the configured command override,
reversed option ordering, unknown-command failure and fallback
ordering against an isolated serial simulator using a fresh build
of a66c0090. I built the man page, HTML manual and release notes,
and ran make distcheck-light with the dummy-ups driver
selection. The distribution check passed with a temporary Aspell
supplement for existing kernel's and firmware's spelling
failures; the repository dictionary is unchanged. AI assistance:
OpenAI Codex, using gpt-6-astra with xhigh reasoning effort.
jq for NUT CI Swarm style agents
make spellcheck passes. Refs:
https://github.com/networkupstools/nut/issues/1039 Co-Authored-By:
Claude Opus 5 <noreply@anthropic.com>
unittest module on some systems [#3627]
unittest module [#3628]
tests/pynut-commands-test.py
and unittest module [#3628]
unittest current Python ecosystem
[#3627, #3628]
make check-NIT* runs [#1711]
NUT-Monitor merger note to the
client section [#3596]
NUT-Monitor fixes [PRs #3516, #3525]
drivers/apcmicrolink-maps.c: fix(apcmicrolink): read ups.beeper.status as a bitmask, not an enum ups.beeper.status matched the exact values 193/194 (0xC1/0xC2), taken from round-tripping PowerChute writes on one SCL500RM1UC. Decompiling PowerChute’s own CompositeAudibleAlarm class shows this is actually a bitmask: bit 0 (0x01) means enabled, bit 1 (0x02) means disabled. The 0xC1/0xC2 values only worked because that particular unit always sets two extra bits (0xC0) alongside the enabled/disabled bit. A second device (APC Smart-UPS X1500, SMX1500RM2U, reported in https://github.com/networkupstools/nut/issues/3587) reports 0x09
input.sensitivity is an opaque
string [#3591] Per investigation of current code posted in
https://github.com/networkupstools/nut/pull/3591#issuecomment-5558864820
common values include: auto, low, reduced, medium,
normal, high in various order and with 2 to 4 of these present
in particular drivers; also H, M, L; also Normal,
Reduced, Low (cased).
self.__widgets, but __attempt_reconnect() lives in the
gui_updater class, which has no __widgets attribute
(name-mangled to _gui_updater__widgets). The widgets belong to
the interface class and are reached, as the surrounding lines
already do, through self.__parent_class._interface__widgets. The
branch is taken whenever PyNUT.AuthConf.getAuthConf() returns an
object, which is the common case, so every reconnection attempt
raised: AttributeError: gui_updater object has no attribute
_gui_updaterwidgets In the Qt variants an exception escaping a
slot is fatal: PyQt turns it into qFatal() and the process aborts
(SIGABRT) instead of reconnecting. Reproduced on Arch Linux, PyQt6
6.11 / Qt 6.11.2, by restarting upsd while NUT-Monitor-py3qt6
(master, 59fad7a97) was connected. Same one-line fix applied to
the py3qt5, py3qt6 and py2gtk2 variants. Co-Authored-By: Claude
Fable 5.1 <noreply@anthropic.com>
syslog: huawei-ups2000: instcmd: command
[bypass.start] reg1 is negative huawei-ups2000: instcmd: command
[shutdown.return] reg1 is negative huawei-ups2000: instcmd: command
[shutdown.reboot] reg1 is negative huawei-ups2000: instcmd: command
[shutdown.reboot.graceful] reg1 is negative Because the regression
was introduced shortly after the initial driver was merged into the
upstream, these instant commands do no work in any NUT version
(with the exception of the earliest development build). This
problem was not discovered during pre-merge test for the same
reason: it’s a regression that occurred after the Pull Request was
merged. In huawei-ups2000, all instant commands are driven by a
lookup table to consolidate the logic to a central dispatcher. Some
commands are dispatched to a (*handler_func)(uint16_t reg1)
function, which is used to handle commands that needs additional
processing. Not all *handler_func actually reads "reg1", it’s an
optional argument. Because declaring the function to accept a
variadic or a (void *) would be over-engineering, a simple unsigned
16-bit value is used, *handler_func may or may not use it. During
the project-wide "fightwarn" refactor campaign, it was noticed that
"reg1" is stored in the lookup table as "int16_t" (-1 indicates an
unneeded register), but *handler_func accepts a "uint16_t". In case
that *handler_func doesn’t need the register ID from the lookup
table, "reg1" is implicitly converted from -1 to 65535. This is
harmless, since "reg1" is not actually used in this case.
Unfortunately, in an attempt to make the code "safe" by suppressing
compiler warning, an incorrect range check was added to the
function, which refuses to invoke *handler_func if "reg1" is
negative. As a result, all instant commands that don’t use "reg1"
are broken. These commands include bypass.start, shutdown.return,
shutdown.reboot, and shutdown.reboot.graceful. To fix this
problem, fix the implicit type conversion correctly by change the
"reg1" data type in the lookup table from "int16_t" to "uint16_t",
and remove the "negative reg1" check. As defensive programming. all
*handler_func that actually need "reg1" would check and abort if
"reg1" is 0. Fixes: e9f02e242acf ("drivers/huawei-ups2000.c:
instcmd(): range-check and cast for ups2000_write_register() and
handler_func()")
clients/upslog.c, clients/upsmon.c, clients/upsstats.c: Update multi-server clients to use per-connection SSL contexts [#3439] upsmon.c, upslog.c, upsstats.c: - Before connecting to each server, fetch per-server authconf with upscli_get_authconf_item() and create SSL context with upscli_get_or_create_ssl_context_authconf()
UPSCONN_t [#3439]
UPSCONN_t arg to
use desired cert with its password [#3439]
sock to use desired cert
with its password [#3439]
docs/Makefile.am, docs/apcmicrolink-descriptors.txt, docs/new-drivers.txt: docs(apcmicrolink): document the descriptor format the driver parses Adds docs/apcmicrolink-descriptors.txt, covering the frame/page/descriptor structure this driver parses: frames as [page id][width data bytes][2 byte checksum], the flat-blob assembly from page N at offset N * width, and the descriptor table that maps this wire structure to descriptor paths
qr/.../ to define regexes
[#1953]
model [#3581] At least when included into
tests, this code fails on some static analyzers: In file included
from fixreportdesctest-tripplite-hid.c:60:
../drivers/tripplite-hid.c: In function ‘tripplite_chemistry_fun’:
../drivers/tripplite-hid.c:179:14: error: argument 1 null where
non-null expected [-Werror=nonnull] 179 \| if
(!strcmp(model, "1003")) { | ~~~~~~~~~~ In
file included from fixreportdesctest-tripplite-hid.c:35:
/usr/include/string.h:156:12: note: in a call to function ‘strcmp’
declared ‘nonnull’ 156 \| extern int strcmp (const char *s1, const
char *s2) CC gpiotest-generic_gpio_liblocal.o \|
~~~ In function ‘tripplite_chemistry_fun’, inlined from
‘tripplite_chemistry_fun’ at ../drivers/tripplite-hid.c:171:20:
../drivers/tripplite-hid.c:184:14: error: argument 1 null where
non-null expected [-Werror=nonnull] 184 \| if
(!strcmp(model, "2005")) { | ~~~~~~~~~~
/usr/include/string.h: In function ‘tripplite_chemistry_fun’:
/usr/include/string.h:156:12: note: in a call to function ‘strcmp’
declared ‘nonnull’ 156 \| extern int strcmp (const char *s1, const
char *s2) | ~~\~ cc1: all warnings being treated as
errors
apcmicrolink driver with USB
HID support [#3579]
NEWS.adoc, data/cmdvartab, data/driver.list.in,
docs/man/apcmicrolink.txt, docs/nut-names.txt, docs/nut.dict,
drivers/Makefile.am, drivers/apcmicrolink-usb.c,
drivers/apcmicrolink-usb.h, drivers/apcmicrolink.c:
feat(apcmicrolink): add USB HID transport with HID-PDC fallback
Tunnel the Microlink protocol over USB HID interrupt IN/OUT for
models with no serial port (porttype = usb). Tested against a
single APC Smart-UPS 500 (SCL500RMI1UC); experimental even relative
to the rest of this already-experimental driver. - Session startup
on this hardware is intermittently unreliable and can take 90s\+ to
respond; refusing to start on handshake failure was the top "driver
won’t start" complaint. If the device also exposes standard HID
Power Device usages, start on that fallback data
(ups.status/battery.charge/battery.runtime) instead, and bring up
outlet-group data/commands automatically once the Microlink tunnel
connects, no restart needed. hid_fallback=no opts out. - USB read
timeout raised to 1s (vs 100ms serial) and handshake retries raised
to 10: this device’s interrupt pipe interleaves unrelated Input
reports with Microlink replies, and a 100ms/3 retry budget starves
the handshake before real data arrives. - Add load.cycle and
per-outlet-group instant commands (outlet.group.N.load.,
outlet.group.N.shutdown.), and outlet.group.N.switchable to mark
the unswitched main bank (group 0) as having no switching commands.
make memcheck-NIT{-sandbox,}{-devel,} attempts
voltronic MIB subdriver, bump
snmp-ups version [#3570]
val for all code
paths [#3563]
cypress/cypress_0665_5161_subdriver subdriver fix on
deployments and provided workaround instructions.
cypress/cypress_0665_5161_subdriver subdriver fix on
deployments and provided workaround instructions.
cypress_drain_quirk be
configured via ups.conf [#3563]
*.adoc do
dynacfgPipeline.appliesToChangedFilesRegex_FILES_TXT
docs/Makefile.am goal.
\\.\pipe\upssched, only fall back to it [#3525]
\n [#3525]
\n
[#3525]
reconnect_max_tries in one
place [#3541]
reconnect_max_tries setting for NUT drivers [#3541]
[admin@:12345] being treated
as localhost [#3329]
gui_status_message() call from __check_gui_fields [#3514] It
was causing relevant messages (like mismatches or discovery
results) to disappear instantly.
list <ups>
operation [#2567]
background() method [#3437]
SKIP: can't open existing event log NAMED_PIPE
messages [#3527]
cut * Consider starting AND
ending characters of input hash string for more randomness
make-oriented logs [#1711]
default-all-errors failure messages for
easier search in make-oriented logs [#1711]
scripts/python/app/NUT-Monitor-py3qt5.in, scripts/python/app/NUT-Monitor-py3qt6.in: NUT-Monitor: Add automatic reconnection mechanism for Qt5 and Qt6 - Add automatic reconnection when connection to NUT server is lost - Implement proper teardown of old PyNUTClient instances - Use specific exceptions (socket.error, ConnectionError, EOFError, OSError, PyNUT.PyNUTError) - Prevent multiple simultaneous reconnection attempts - Add was_online flag to track connection state changes
operator= [#3329]
.github/workflows/01-make-dist-worker.yml, .github/workflows/05-codeql.yml: build(deps): bump actions/cache from 5 to 6 Bumps actions/cache from 5 to 6. - Release notes - Changelog
.github/workflows/01-make-dist-worker.yml, .github/workflows/05-codeql.yml: build(deps): bump actions/checkout from 6 to 7 Bumps actions/checkout from 6 to 7. - Release notes - Changelog
case
WITH_SSL_CLIENT_CERTIDENT ... if WITH_SSL_CLIENT != none [#1711]
certutil or
openssl into prepare_NIT_certs() where we would inevitably use
them [#1711]
cp -prf failed [#1711]
--
--
and arrow with =>
file type parsing fails for text with some but not
other wide characters (so it is "data" and not some sort of
"text"). This test was added for C sources as well, but keep in
mind that the final authority is the actually used compilers -
which are free to complain or not.
unset CCACHE_DIR if provided but empty Notably,
ccache-3.7.12 in FreeBSD 15 breaks CI build with that complaint.
--
[#3447]
--
[#3447]
drivers/libusb1.c: use explicit context; drop per-close libusb_exit() [#598] The original code called libusb_init(NULL) on every nut_libusb_open() and libusb_exit(NULL) on every nut_libusb_close(), bumping and decrementing the default context’s refcount. That violates the documented contract for libusb_exit, which "should be called after closing all open devices and before your application terminates", and on certain firmware it wedges indefinitely: when libusb_exit hits the 1→0 transition it tears the context down, which waits on libusb’s internal sync primitives for outstanding URBs to drain. URBs orphaned by libusb_reset_device or by an unexpected device disconnect never drain, so the wait never returns. The deadlock is reachable from any reconnect path. It was first recognized by 4f84b7f92 ("don’t libusb_exit() when closing a previously opened device"), which dropped the call in nut_libusb_open()'s rematch loop. The fallthrough reconnect path in qx_command and the rest of the driver lifecycle still hit it. With the companion change in nutdrv_qx.c (a4813f868) that escalates persistent LIBUSB_ERROR_OVERFLOW to libusb_reset_device, the deadlock window opens on every escalation and was hit reproducibly on the 0665:5161 Cypress USB-serial bridge family (Salicru SPS, Ippon, ViewPower, Voltronic Power UPSes; see #598, #993, #2453). Switch to an explicit libusb context owned end-to-end: - Initialize once on the first nut_libusb_open() and register a matching one-shot atexit handler. - Remove libusb_exit() from nut_libusb_close(); the close path now only calls libusb_close(), which is non-blocking. - Replace libusb_get_device_list(NULL, …) with the explicit context so the default context is never touched.
usb_resetter --reset-device.
NEWS.adoc, data/driver.list.in, docs/man/Makefile.am, docs/man/ragtech.txt, docs/nut.dict, drivers/Makefile.am, drivers/ragtech.c, include/wincompat.h: ragtech: new driver for Ragtech UPSes (USB CDC-ACM, family 10) Targets Brazilian-built Ragtech "Easy Pro" / NEP / TORO / INNERGIE / OneUP devices that present themselves as USB CDC-ACM (VID 0x04D8, PID 0x000A, Microchip PIC firmware). Validated end-to-end against an Easy 2000 TI (reg 0x9A model id = 16) read out of a working OneUP Nitro 2000. Protocol — three opcodes observed in OEM traffic: 0x01 ADDR_HI ADDR_LO VALUE CKSUM write byte 0x02 ADDR_HI ADDR_LO MASK CKSUM AND mask (atomic bit-clear) 0x04 ADDR_HI ADDR_LO COUNT CKSUM read range CKSUM = (ADDR_HI \+ ADDR_LO + VALUE) & 0xFF The CDC-ACM channel ignores baud at the wire but DTR/RTS are interpreted by some Ragtech families as a remote shutdown signal — the driver forces both low after open and does NOT call ser_set_speed() to avoid the tcsetattr() DTR pulse that some Linux tty drivers perform. The full 30-byte main range (0x80..0x9D) plus V_IOUTCALIB (0xF3) and the oscillator calibration pair (0x202/0x203) are read; output frequency is interpolated per devices.xml formula rather than hard-coded. Twenty models from the family-10 device table populate ups.model, ups.realpower.nominal, output.voltage scaling, output.current scaling and battery voltage scaling. input.voltage.nominal switches between 115V and 220V dynamically based on the measured input. Instcmds implemented: shutdown.stayoff — aa 02 00 80 fe (clear AUTOSTART) \+ aa 01 00 98
scripts/Windows/dllldd.sh helper script
refinements [#3420]
ln to create hard links, and tell 7-zip to
store them as such, not as independent files (subject to 7zip
format du jour)
tr ':' '\n' that can be done once.
dirname calls (spawning those processes takes a few seconds in
MSYS2 on Windows), use one sed process.
strings outputs and findings [#3420]
touch -d "-10 seconds", hide the errors
(such request is known to be not too portable)
case.
openssl defaults and old(er) java keytool.
config.cache file from older runs moved to NUT v2.8.6 [#3108]
make
all-quick for less noise
RunTimeCalibrationStatus_BF is
explained in MPAO-98KJ7F_R1_EN Appendix B. This adds defines for
the bitfield and decodes it into
experimental.ups.calibration.result using a string join
converter.
PowerSystemError_BF is explained in MPAO-98KJ7F_R1_EN
Appendix B. This adds defines for the bitfield and decodes it as
alarms in the driver.
BatterySystemError_BF is explained in MPAO-98KJ7F_R1_EN
Appendix B. We were already using the bitfield for the RB
status, this adds defines for the bitfield and decodes it as alarms
in the driver.
_apc_modbus_handle_error function with a simpler retry
mechanism built into _apc_modbus_read_registers. The new
approach: - Retries register reads on ETIMEDOUT errors up to
modbus_retries times (configurable, default 3) - On non-timeout
errors or after retry exhaustion, closes the connection for
reconnection on the next update cycle - Removes the
platform-specific (WIN32/POSIX) timeout detection and the
flush-based recovery that didn’t work anyway (flush is already done
in _apc_modbus_reopen upon reconnection) Also adds a
modbus_retries driver option to configure the number of read
retry attempts, and improves logging for connection open/close
events. This change was inspired by a patch by @marcan to do the
same and from testing the behaviour of apcupsd, noticing that on
my USB unit it times out on read and only succeeds on the first
retry.
_apc_modbus_string_join did not zero terminate the
result in every case, like when all values are NULL.
certpasswd string.