Table of Contents
Aggregating codebase research done in various issues, and linking to some related others, to keep notes organized:
- https://github.com/networkupstools/nut/issues/123
- https://github.com/networkupstools/nut/issues/1299
- https://github.com/networkupstools/nut/issues/1712
- https://github.com/networkupstools/nut/issues/1717
- https://github.com/networkupstools/nut/pull/1719
- https://github.com/networkupstools/nut/issues/1727
- https://github.com/networkupstools/nut/issues/1728
PIDPATH, ALTPIDPATH, STATEPATH
After a bit more digging in current codebase, I can say that NUT unprivileged daemons (drivers and upsd) default to using the ALTPIDPATH in fact -- which in turn defaults to STATEPATH e.g. /var/state/ups since both daemon types exchange pipe files there so may write there, but some package recipes configure it to e.g. /var/run/nut.
This can be seen by code lines preparing a pidfn (usually) with altpidpath() (see common/common.c) in drivers/main.c, drivers/upsdrvctl.c and server/upsd.c.
And then it gets messy in same common/common.c with:
writepid()which optionally usesPIDPATH(as defined, no./nutsubdir) if filenameis not absolute, and withsendsignal()which combinesPIDPATH(as defined, no./nutsubdir) and theprognameto wrapsendsignalfn()(which reads PID from that absolute filename and signals the process in OS-dependent manner).
These latter usages imply that PIDPATH is expected to be writable by nut processes and should not be the root-secured system location (e.g. /var/run directly) unless NUT tools and daemons run as root; can be /tmp however.
I'll post a clean-up PR to clarify this in configure script comments and docs, and "reference" init-scripts and packaging templates which use $PIDPATH/nut to confuse matters more.
Also linking to #123 which creeps out to other big discussions on PID files :)
Checking references to the methods mentioned above wit a focus on PIDPATH usage in current state of master branch:
:; git grep -E '(writepid|sendsignal|altpidpath) *\('
-
clients/upslog.c
github.com/networkupstools/nut@ddbab26b5c/clients/upslog.c (L615-L617)--writepid(pidfilebase);just beforebecome_user()so expected to berootat that point and may use even a privilegedPIDPATHlocation. Thepidfilebaseisprogname or set by argument.
-
clients/upsmon.c -- the one explicitly documented consumer of
configure --with-pidpathgithub.com/networkupstools/nut@ddbab26b5c/clients/upsmon.c (L2369-L2392)-- signals an older (running) instance of itself, usingsendsignal(prog)(underPIDPATH) in some casesgithub.com/networkupstools/nut@ddbab26b5c/clients/upsmon.c (L2470-L2488)--writepid(prog)just beforebecome_user()(if running as parent-child pipe and changing privileges at all; saving child PID then), so expected to berootat that point and may use even a privilegedPIDPATHlocation.- Note that if upsmon gets split into two processes, the parent part at
github.com/networkupstools/nut@ddbab26b5c/clients/upsmon.c (L2034)runs (for non-Windows case) until either the child process exits, or until it sends the message to callshutdowncmd(asrootwhich is the purpose of this split). There is no separate PID file for the parent process.
-
drivers/main.c
github.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L903)preparesbufferwith absolute driver PID file name underaltpidpath(), used ingithub.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L918)andgithub.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L931-L933)to kill off an earlier instance if present, with full-pathsendsignalfn().github.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L949-L953)callspidfn=buffer; writepid(pidfn);to save the PID value before possibly forking and backgrounding the driver (if backgrounding is enabled).github.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L1145-L1148)callswritepid(pidfn);to save the PID value after possibly forking and backgrounding the driver (if backgrounding is enabled).- Note the PID file is neither saved nor queried in foreground mode (e.g. competing driver instances are not killed off either).
github.com/networkupstools/nut@ddbab26b5c/drivers/main.c (L1145-L1148)callssendsignal()only for WIN32 usecases (so not relying onPIDPATHfor POSIX builds)
-
drivers/upsdrvctl.c
github.com/networkupstools/nut@ddbab26b5c/drivers/upsdrvctl.c (L159-L174)tries absolutepidfnvariants underaltpidpath()tostop_driver()and exits if none of those is presentgithub.com/networkupstools/nut@ddbab26b5c/drivers/upsdrvctl.c (L185-L224)further instop_driver()uses the absolutely-pathedsendsignalfn()in POSIX use-cases
-
scripts/Windows/wininit.c
- two WIN32 usecases of
sendsignal()(so not relying onPIDPATHfor POSIX builds)
- two WIN32 usecases of
-
server/upsd.c :
github.com/networkupstools/nut@ddbab26b5c/server/upsd.c (L1600)preparespidfnunderaltpidpath()github.com/networkupstools/nut@ddbab26b5c/server/upsd.c (L1686-L1697)makes use ofsendsignal*()variants, withsendsignal()specifically called only for WIN32 usecases (so not relying onPIDPATHfor POSIX builds)github.com/networkupstools/nut@ddbab26b5c/server/upsd.c (L1842-L1853)useswritepid(pidfn)with absolute path (so not relying onPIDPATH)
Who does what to PID files?
Welcome to the Network UPS Tools (NUT) project Wiki, and feel free to contribute tricks and insights.
While there are several good entries in the menu, ones referenced most frequently in issue discussions include:
- Finding recent development iteration artifacts
- Building NUT for in-place upgrades or non-disruptive tests (including the build prerequisites for different platforms in-tree or as a rendered page on NUT website) and Using NIT (NUT Integration Test suite) sandbox
- Technicalities: Customizing (NUT) config files and scripts delivered by packaging
- Links to distribution packaging recipes and repository sections
- Troubleshooting
upsdrvctldrivers not starting ("insufficient permissions on everything" or "Can't claim USB device [VVVV:PPPP]@0/0: Entity not found") possibly due to nut-driver-enumerator (NDE) services having been there before you with NUT 2.8.x, and "insufficient permissions" when starting USB drivers for a different PoV on this; see also an example unit deployment detailed in NUT systemd service units page - Changing NUT daemon debug verbosity
- Building NUT integration for Home Assistant
- Running NUT in an LXC container
- Troubleshooting eventual disconnections (Data stale) and CyberPower Systems (CPS) know-how
- NUT for Windows
- NUT HCL and DDL
- Code contributions, PRs, PGP and DCO
- NUT CI farm
Also keep in mind the documentation links from NUT website and the FAQ in particular.