Compare commits

..

94 Commits

Author SHA1 Message Date
William Hubbs
ae7490929d update ChangeLog 2017-05-12 17:21:55 -05:00
William Hubbs
ddbd1caa35 supervise-daemon: save start time and respawn count before dropping privs 2017-05-12 17:19:29 -05:00
William Hubbs
a249651218 version 0.26.1 2017-05-12 17:19:01 -05:00
William Hubbs
e4bfb4530a update ChangeLog 2017-05-11 22:00:41 -05:00
William Hubbs
78e0042ecc man/rc-status: document changes for supervised daemons
rc-status now shows the amount of time a supervised daemon has been
active as well as the number of times it has been respawned during the
current respawn period.
2017-05-11 21:55:31 -05:00
William Hubbs
82e12e3092 rc-status: show uptimes and respawn counts for supervised daemons 2017-05-11 21:39:03 -05:00
William Hubbs
1ebef0d7a3 fix to_time_t to honor dst 2017-05-11 18:13:13 -05:00
William Hubbs
6b4050ab9c fix from_time_t function 2017-05-11 16:22:12 -05:00
William Hubbs
cf5e9aa2bb Move time_t conversions to rc-misc.c so they can be shared 2017-05-11 16:06:12 -05:00
William Hubbs
a3250e77d4 supervise-daemon: save start time and respawn count
This will allow rc-status to display an uptime and restart count for
supervised processes.
2017-05-11 13:54:20 -05:00
William Hubbs
df027ca472 supervise-daemon: fix our status when we give up on the child process 2017-05-11 11:36:42 -05:00
William Hubbs
4c89e3f5fa supervise-daemon:create multiple options from --respawn-limit
This creates --respawn-delay, --respawn-max and --respawn-period. It was
suggested that it would be easier to follow if the options were
separated.

This is for #126.
2017-05-10 18:13:23 -05:00
William Hubbs
3673040722 supervise-daemon: add a --respawn-limit option
Allow limiting the number of times supervise-daemon will attempt to respawn a
daemon once it has died to prevent infinite respawning. Also, set a
reasonable default limit (10 times in a 5 second period).

This is for issue #126.
2017-05-09 18:30:08 -05:00
William Hubbs
96c8ba2fb5 supervise-daemon: mark all open file descriptors FD_CLOEXEC 2017-04-29 13:48:45 -05:00
William Hubbs
47cf1d0c70 supervise-daemon:remove the controlling tty in the supervisor 2017-04-29 12:04:15 -05:00
William Hubbs
06a6a27e44 supervise-daemon: fix access to tty_fd and devnull_fd
Both the child and supervisor need access to these file descriptors.
2017-04-29 10:12:16 -05:00
William Hubbs
5de3798afc supervise-daemon: mark the service started when the supervisor is active 2017-04-29 09:41:07 -05:00
William Hubbs
6ac094a59c version 0.26 2017-04-19 17:24:44 -05:00
William Hubbs
84c81ca02d update ChangeLog 2017-04-17 12:35:12 -05:00
William Hubbs
0e3f872098 init: send term/kill signals as final step of shutdown 2017-04-17 12:23:45 -05:00
William Hubbs
5fd3747b19 reword the bugs section of the openrc-init man page 2017-04-14 11:11:07 -05:00
William Hubbs
4694900190 init: fix signal handling
The only signals we handle are SIGINT and SIGCHLD, so block all others
and unblock them in the child process before we start a rurnlevel.
2017-04-13 12:54:30 -05:00
William Hubbs
05738bfce1 init: add re-exec capability
This will allow the re-execution of the init process after upgrading
OpenRC.
2017-04-12 17:56:36 -05:00
i.Dark_Templar
6f88ee4ec6 bootmisc: do not remove ld-elf32.so.hints
File /var/run/ld-elf32.so.hints is used on FreeBSD 64bit multilib
This fixes #125.
2017-04-10 10:15:28 -05:00
William Hubbs
cc51bdca3b Add attribution to openrc-init.c and openrc-shutdown.c 2017-04-07 07:39:12 -05:00
William Hubbs
13ca79856e add init process
openrc-init.c and openrc-shutdown.c are based on code which was written by
James Hammons <jlhamm@acm.org>, so I would like to publically
thank him for his work.
2017-04-06 17:13:59 -05:00
i.Dark_Templar
79a9edc730 Fix make install on FreeBSD: don't try to install /etc/init.d/modules twice 2017-04-05 16:54:53 +03:00
Austin English
9eb669591e start-stop-daemon: warn if calling --start with --retry or --stop with --wait
This fixes #122
2017-04-03 10:43:40 -05:00
William Hubbs
55a87a30ec init.d/agetty.in: add -prefix keyword 2017-03-31 16:21:28 -05:00
William Hubbs
a912029462 init.d/mount-ro: change dependency on killprocs and savecache to after
killprocs always succeeds and savecache is not required by mount-ro, so
we can just start after both of these have run.
2017-03-31 13:39:42 -05:00
William Hubbs
1e90782797 agetty-guide: typo fix 2017-03-31 10:34:41 -05:00
William Hubbs
51a292e09b init.d: add agetty to ignore patterns 2017-03-28 17:52:53 -05:00
William Hubbs
50fccf47d4 sh/gendepends.sh.in: fix detection of service scripts
We do not need to care about the path on the shebang line of a service
script as long as the shebang line ends with "openrc-run".
This fixes #119 and #120.
2017-03-23 13:17:11 -05:00
William Hubbs
9bd63b5d4a update dependencies for clock service
The clock services had a very long list of "before" dependencies that
referred to other services within OpenRC. For ease of maintenance,
convert these to "after clock" dependencies in the individual services.
2017-03-16 10:16:39 -05:00
William Hubbs
48db17a93f update news file 2017-03-15 17:30:23 -05:00
William Hubbs
c333707cba Remove all occurances of 'before *' from dependencies
Using wildcards in dependencies causes issues when rc_parallel is set to
yes because it can lead to deadlocks.
All dependencies need to be explicit rather than implicit.

This is the first stage of moving this direction.
2017-03-14 18:04:31 -05:00
William Hubbs
5f5b1f7cbe init.d/sysfs.in: efivarfs tweaks
Since we check for /sys/firmware/efi/efivars, we do not need to check
for /sys/firmware/efi

Since Failing to mount efivarfs is not critical, we silence the error
message from mount.
2017-03-12 13:55:49 -05:00
William Hubbs
cfdf56475e version 0.25 2017-03-12 13:55:25 -05:00
William Hubbs
fde3902d06 update ChangeLog 2017-03-09 16:20:17 -06:00
William Hubbs
d7bbb0f583 add agetty service
The agetty service is an alternate way to manage gettys with agetty
under Linux which is separate from an external init system.
2017-03-09 15:23:02 -06:00
William Hubbs
21ca2b746c init.d/sysfs: drop modules completely from the dependencies
This is for #112.
2017-03-08 10:44:10 -06:00
William Hubbs
6a79aef015 init.d/sysfs: Do not load efivarfs module
My understanding is that the kernel can autoload this module. If it
doesn't, the module should be built in or loaded from an initramfs.

This fixes https://github.com/openrc/openrc/pulls/112.
2017-03-07 17:49:42 -06:00
William Hubbs
4a269674b7 make sure netmount and localmount start after root 2017-02-28 17:44:06 -06:00
William Hubbs
eea4decdd1 net-online: typo fix 2017-02-26 19:09:56 -06:00
William Hubbs
d4d0f25a48 net-online: updates to make the service more usable
- switch from attempting to ping the default gateway to a host outside
the local network, defaulting to google.com.
- along with this, change the name of the variable that requests a ping
test to include_ping_test so the meaning is more clear.
2017-02-26 13:51:50 -06:00
William Hubbs
1cb44092fc sh/rc-functions.sh.in: add get_bootparam_value function 2017-02-23 18:16:15 -06:00
William Hubbs
4207e46622 move init.d examples under support and install them 2017-02-22 14:45:16 -06:00
William Hubbs
f6ea16159e scripts: make sure the rc-sstat symlink is always replaced 2017-02-22 14:25:02 -06:00
William Hubbs
9047ea4cb0 install support files
These files have been in the distribution for some time but haven't been
installed. They are good examples of how to do things, so we should
install them.
2017-02-18 15:52:28 -06:00
William Hubbs
d7f5a696c1 support: rename all README files to README.md 2017-02-17 12:29:11 -06:00
William Hubbs
6f614cd3f3 Move deptree2dot to the support folder
Since deptree2dot and the perl requirement are completely optional, we
can move this tool to the support folder. This gives the user the option
of using it if they have perl installed, and means we do not have an
optional runtime dependency on perl.

Documentation for this tool has also been added to the support folder.

X-Gentoo-Bug: 600742
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=600742
2017-02-17 12:06:03 -06:00
William Pitcock
85c1930acf test/setup_env: ensure that eval_ecolors is available on the path.
The test environment previously used the system default paths instead of installing the necessary $PATH environment
variable to make finding eval_ecolors work.
This closes #117.

X-Gentoo-Bug: 374191.
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=374191.
2017-01-31 17:27:13 -06:00
Nicolas Porcel
96bd0c004c Fix typo in guide.md
This fixes #115.
2017-01-26 17:07:01 -06:00
William Hubbs
b693af9055 Revert "scripts: do not substitute for @SHELL@ in rc-sstat"
This reverts commit e2e652e469.
2017-01-26 15:39:19 -06:00
Doug Freed
6dcb692986 start-stop-daemon: allow all standard signals
Also we define the signalpair_item macro.
This fixes #113.

X-Gentoo-Bug: 604986
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604986
2017-01-25 17:48:52 -06:00
William Hubbs
e2e652e469 scripts: do not substitute for @SHELL@ in rc-sstat 2017-01-08 20:42:26 -06:00
William Hubbs
b73941f0c3 mountinfo: make the path to /proc/mounts a constant
This path should not be hard coded in the open call.
Linux prior to 2.4.19 did not have /proc/self/mounts, so for now I'm
making this value /proc/mounts everywhere, but that may change to
/proc/self/mounts on linux; I'm not sure we should care about <2.4.19.

X-Gentoo-Bug: 604646
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604646
2017-01-04 18:18:37 -06:00
Benda Xu
c304522131 Clean up warnings that can use the _unused macro
X-Gentoo-Bug: 604666
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604666
2017-01-04 17:18:35 -06:00
Benda Xu
92325b44ba Indentation fixes
X-Gentoo-Bug: 604666
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604666
2017-01-04 16:59:38 -06:00
Benda Xu
074d90f5a4 Drop the use of the _BSD_SOURCE macro on Linux
X-Gentoo-Bug: 604666
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604666
2017-01-04 16:59:24 -06:00
Benda Xu
7056b56b3c Drop the use of the _BSD_SOURCE macro on GNU/Hurd
X-Gentoo-Bug: 604666
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=604666
2017-01-04 16:58:52 -06:00
Doug Freed
d5c3b85e3f loopback: drop explicit route for BSD too 2016-12-21 18:00:02 +00:00
William Hubbs
1ab2249448 version 0.24 2016-12-21 11:50:22 -06:00
William Hubbs
a15cff21c6 update ChangeLog 2016-12-20 12:34:22 -06:00
Doug Freed
45aa36cc62 librc: detect loops in stacked runlevels and abort
This fixes #109.
X-Gentoo-Bug: 558700
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=558700
2016-12-19 18:24:31 -06:00
William Hubbs
d3f833179b sh/init.sh.Linux.in: remove unused check for Gnu/KFreeBSD
This script only runs on Linux, so the check will always be false.
2016-12-18 11:53:12 -06:00
William Hubbs
abe552b969 modules: get rid of printing each module on Linux
Now that we respect the module blacklists, don't print every module we
try to load, because it might not end up loaded due to the blacklist,
and modprobe doesn't consider that a failure.
2016-12-17 19:21:13 -06:00
Doug Freed
856eafb006 sh/init.sh.Linux.in: skip /proc test if no md5sum
This will also warn users if md5sum is missing, which serves as a pretty
good indicator that /usr is not mounted.
2016-12-17 23:27:37 +00:00
Robin H. Johnson
f27d60add9 sh/openrc-run.sh: expose default start/stop/status
Supervisor setups break easily when start/stop/status functions are not
default.

Applications that write multiple PIDs to a pidfile (eg HAProxy as
described in bug 601540), can also benefit from being able to call the
default start/stop/status with modified environment variables.

Expose the default start/stop/status functions as
default_start/stop/status, and use them for the defaults
start/stop/status.

Trivial usage example:
```
  stop()
  {
    t=$(mktemp)
    for pid in $(cat $pidfile) ; do
      echo $pid >$t
      pidfile=$t default_stop
    done
    rm -f $t
  }
```

X-Gentoo-Bug: 601540
X-Gentoo-Bug-URL: https://bugs.gentoo.org/601540
Signed-off-by: Robin H. Johnson <robbat2@gentoo.org>
2016-12-17 14:50:11 -08:00
Doug Freed
8ad460c54c Fix typos
Fixes #99
2016-12-17 18:41:02 +00:00
Doug Freed
72c0824961 localmount: add comment about types variable 2016-12-17 18:39:53 +00:00
Alan Somers
5b7e3490ef Localmount shouldn't mount remote filesystems
The /etc/init.d/localmount script has a syntax error that causes it to
attempt to mount remote filesystems, causing the boot to fail. The
script appends a "no" to each remote filesystem type, but it should only
be append the "no" to the beginning of the list.  This patch fixes
localmount on FreeBSD 12.0.  A review of the mount(8) manpage on Ubuntu
12.04 suggests that this patch is correct for Linux, too.
2016-12-17 13:35:58 -05:00
William Hubbs
dd61e6bfc3 rc.conf: fix the commented default setting for rc_logger
X-Gentoo-Bug: 601480
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=601480
2016-12-15 17:52:34 -06:00
Doug Freed
204971c6e2 runlevels: remove bad trailing backslash 2016-12-12 15:13:26 -05:00
William Hubbs
3552f0ae54 man/start-stop-daemon.8: clarify documentation about --pidfile option
The documentation implied that if you stop a daemon we handle multiple
pids in a pid file. This is not correct. We only handle the first pid.

X-Gentoo-Bug: https://bugs.gentoo.org/show_bug.cgi?id=601540
2016-12-05 12:25:52 -06:00
AndCycle
42cb848829 fix manual typo
This fixes #105.
2016-12-02 10:57:10 -06:00
William Hubbs
e0ac661419 split tmpfiles processing into opentmpfiles
The openntmpfiles package is designed so that it can be used on systems
independently of whether openrc is used.
2016-12-01 12:04:54 -06:00
Jason Zaman
6414c3bc39 selinux: fix SIGSEGV with invalid contexts
Fixes: https://github.com/openrc/openrc/issues/104
2016-11-17 12:03:12 -06:00
William Hubbs
4f9bd7e4db init.d/loopback.in: drop the route to the loopback interface on Linux
This is related to #103.
2016-11-03 12:47:01 -05:00
William Hubbs
bf539f2196 init.d/mount-ro: do not remount /usr read only if it is premounted
X-Gentoo-Bug: 573760
X-Gentoo-Bug: https://bugs.gentoo.org/show_bug.cgi?id=573760
2016-11-03 12:29:21 -05:00
William Hubbs
20b60ea904 conf.d/net-online: clarify comment about interfaces setting
This setting refers to all interfaces that support ethernet
2016-11-03 11:57:40 -05:00
William Hubbs
f53c8baef3 init.d/net-online: remove interfaces and timeout from local declarations
X-Gentoo-Bug:  598621
X-Gentoo-Bug-URL:  https://bugs.gentoo.org/show_bug.cgi?id=598621
2016-11-03 11:18:20 -05:00
William Hubbs
be06cd250e src/rc/rc: do not try to start services if fork fails 2016-11-01 17:31:57 -05:00
Robin H. Johnson
003657c973 init.d/loopback: drop scope on loopback
Busybox does not support the 'scope' argument on 'ip address add' or 'ip
route add', this is documented in BUSYBOX.md, but is no longer actually
needed, as the kernel does get it right without manual specification,
and the ifconfig variant already relies on the kernel to get it right.
This is part of #103.

X-Gentoo-Bug: 487208
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=487208
2016-10-25 10:49:14 -05:00
William Hubbs
4fd144c0a6 src/rc/rc-misc.c: report error if call to flock() fails
X-Gentoo-Bug: 597390
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=597390
2016-10-24 12:47:49 -05:00
Joe Maloney
c44c904a61 init.d.misc/wpa_supplicant: find wireless interface for FreeBSD
This fixes #101.
2016-10-16 11:10:57 -05:00
Sven Wegener
78146b0e14 do_service: Initialize idx to 0
If index is not explicitly specified for service_started_daemon, it will
look for daemons by random index.

This fixes #100.
2016-10-11 10:30:02 -05:00
William Hubbs
deaae7ab5c init.d/sysfs: load efivarfs module when booting in efi mode:1
The presence of /sys/firmware/efi is used to indicate that the system
was booted in efi mode.
2016-10-05 22:48:17 -05:00
William Hubbs
3d2c2f0b87 init.d/sysfs: fix efivarfs module test 2016-10-04 18:18:17 -05:00
William Hubbs
6a0c033a64 init.d/sysfs: fix efivarfs handling
Separate loading the module, if it isn't built in or loaded, from
mounting the file system.

This also makes sure the warning about configuring the module in
/etc/conf.d/modules or building it in is displayed only if it is loaded
successfully.

X-Gentoo-Bug: 595836
X-Gentoo-Bug-URL: https://bugs.gentoo.org/show_bug.cgi?id=595836
2016-10-04 12:06:58 -05:00
Doug Freed
6710316a18 openrc-run: fix double free 2016-09-30 17:29:56 -04:00
Doug Freed
61882821e0 init.d: Clean up some bad ewarn output 2016-09-28 15:00:40 -04:00
William Hubbs
969546bcf0 typo fix
X-Gentoo-Bug: 595306
X-Gentoo-Bug: https://bugs.gentoo.org/show_bug.cgi?id=595306
2016-09-27 19:39:02 -05:00
William Hubbs
d0ae7ffc25 version 0.23 2016-09-27 19:38:07 -05:00
112 changed files with 1835 additions and 1371 deletions

1357
ChangeLog

File diff suppressed because it is too large Load Diff

View File

@@ -13,7 +13,7 @@ MK= ${TOP}/mk
include ${TOP}/Makefile.inc
SUBDIR= conf.d etc init.d local.d man scripts sh src sysctl.d
SUBDIR= conf.d etc init.d local.d man scripts sh src support sysctl.d
# Build pkgconfig or not
MKPKGCONFIG?= yes

View File

@@ -1,3 +1,3 @@
NAME= openrc
VERSION= 0.22.3
VERSION= 0.26.1
PKG= ${NAME}-${VERSION}

37
NEWS.md
View File

@@ -3,6 +3,43 @@
This file will contain a list of notable changes for each release. Note
the information in this file is in reverse order.
## OpenRC-0.25
This version contains an OpenRC-specific implementation of init for
Linux which can be used in place of sysvinit or any other init process.
For information on its usage, see the man pages for openrc-init (8) and
openrc-shutdown (8).
## OpenRC-0.24.1
This version starts cleaning up the dependencies so that rc_parallel
will work correctly.
The first step in this process is to remove the 'before *' from the
depend functions in the clock services. This means some services not
controlled by OpenRC may now start before instead of after the clock
service. If it is important for these services to start after the clock
service, they need to have 'after clock' added to their depend
functions.
## OpenRC-0.24
Since the deptree2dot tool and the perl requirement are completely
optional, the deptree2dot tool has been moved to the support directory.
As a result, the MKTOOLS=yes/no switch has been removed from the makefiles.
This version adds the agetty service which can be used to spawn
agetty on a specific terminal. This is currently documented in the
agetty-guide.md file at the top level of this distribution.
## OpenRC-0.23
The tmpfiles.d processing code, which was part of previous versions of
OpenRC, has been separated into its own package [1]. If you need to
process systemd style tmpfiles.d files, please install this package.
[1] https://github.com/openrc/opentmpfiles
## OpenRC-0.22
In previous versions of OpenRC, configuration information was processed

View File

@@ -30,7 +30,6 @@ MKSELINUX=yes
MKSTATICLIBS=no
MKTERMCAP=ncurses
MKTERMCAP=termcap
MKTOOLS=yes
PKG_PREFIX=/usr/pkg
LOCAL_PREFIX=/usr/local
PREFIX=/usr/local
@@ -73,10 +72,6 @@ Obviously, if you're installing this onto a system that does not use
OpenRC by default then you may wish to backup the above listed files,
remove them and then install so that the OS hooks into OpenRC.
`init.d.misc` is not installed by default as the scripts will need
tweaking on a per distro basis. They are also non essential to the
operation of the system.
## Reporting Bugs
If you are using Gentoo Linux, bugs can be filed on their bugzilla under

18
agetty-guide.md Normal file
View File

@@ -0,0 +1,18 @@
# Setting up the agetty service in OpenRC
The agetty service is an OpenRC specific way to monitor and respawn a
getty, using agetty, on Linux. To use this method, make sure you aren't
spawning a getty manager for this port some other way (such as through
sysvinit/inittab), then run the following commands as root.
Note that [port] refers to the port you are spawning the getty on, for
example, tty1 or ttyS0. The full path to it, for example, /dev/tty1
should not be used.
```
# cd /etc/init.d
# ln -s agetty agetty.[port]
# cd /etc/conf.d
# cp agetty agetty.[port]
#rc-update add agetty.[port] [runlevel]
```

View File

@@ -1,8 +1,7 @@
include ../mk/net.mk
DIR= ${CONFDIR}
CONF= bootmisc fsck hostname localmount netmount swap urandom tmpfiles \
${CONF-${OS}}
CONF= bootmisc fsck hostname localmount netmount swap urandom ${CONF-${OS}}
ifeq (${MKNET},yes)
CONF+= network staticroute
@@ -13,8 +12,8 @@ include ${MK}/os.mk
CONF-FreeBSD= ipfw modules moused powerd rarpd savecore syscons
CONF-Linux= consolefont devfs dmesg hwclock keymaps killprocs modules mtab \
net-online
CONF-Linux= agetty consolefont devfs dmesg hwclock keymaps killprocs modules \
mtab net-online
CONF-NetBSD= moused rarpd savecore

8
conf.d/agetty Normal file
View File

@@ -0,0 +1,8 @@
# Set the baud rate of the terminal line
#baud=""
# set the terminal type
#termtype="linux"
# extra options to pass to agetty for this port
#agetty_options=""

View File

@@ -3,10 +3,13 @@
# default is all interfaces that support ethernet.
#interfaces=""
# This setting controls whether a ping to the default gateway is
# included in the test for network connectivity after all interfaces
# are active.
#ping_default_gateway=no
# This setting controls whether a ping test is included in the test for
# network connectivity after all interfaces are active.
#include_ping_test=no
# This setting is the host to attempt to ping if the above is yes.
# The default is google.com.
#ping_test_host=some.host.name
# The timeout setting controls how long the net-online service waits
# for the network to be configured.

View File

@@ -1,3 +0,0 @@
# Extra options for tmpfiles.sh
#tmpfiles_opts="--verbose"
tmpfiles_opts=""

View File

@@ -48,7 +48,7 @@
# /var/log/rc.log
# NOTE: Linux systems require the devfs service to be started before
# logging can take place and as such cannot log the sysinit runlevel.
#rc_logger="YES"
#rc_logger="NO"
# Through rc_log_path you can specify a custom log file.
# The default value is: /var/log/rc.log
@@ -178,6 +178,11 @@
# "xenU" - XenU Domain (Linux and NetBSD)
#rc_sys=""
# if you use openrc-init, which is currently only available on Linux,
# this is the default runlevel to activate after "sysinit" and "boot"
# when booting.
#rc_default_runlevel="default"
# on Linux and Hurd, this is the number of ttys allocated for logins
# It is used in the consolefont, keymaps, numlock and termencoding
# service scripts.

View File

@@ -14,7 +14,7 @@ trap : SIGINT SIGQUIT
# Try and use stuff in /lib over anywhere else so we can shutdown
# local mounts correctly.
LD_LIBRARY_PATH="/lib${LD_LIBRARY_PATH:+:}${LDLIBRARY_PATH}" ; export LD_LIBRARY_PATH
LD_LIBRARY_PATH="/lib${LD_LIBRARY_PATH:+:}${LD_LIBRARY_PATH}" ; export LD_LIBRARY_PATH
# If $TERM is not set then assume default of @TERM@
# This gives us a nice colour boot :)

View File

@@ -198,7 +198,7 @@ script:
command=
command_args=
pidfile=
``
```
Thus the 'smallest' service scripts can be half a dozen lines long

3
init.d/.gitignore vendored
View File

@@ -1,3 +1,4 @@
agetty
binfmt
modules-load
bootmisc
@@ -45,5 +46,3 @@ syslogd
termencoding
ttys
wscons
tmpfiles.dev
tmpfiles.setup

View File

@@ -2,8 +2,8 @@ include ../mk/net.mk
DIR= ${INITDIR}
SRCS= bootmisc.in fsck.in hostname.in local.in localmount.in loopback.in \
netmount.in osclock.in root.in savecache.in swap.in tmpfiles.setup.in \
swclock.in sysctl.in runsvdir.in urandom.in s6-svscan.in ${SRCS-${OS}}
netmount.in osclock.in root.in savecache.in swap.in swclock.in \
sysctl.in runsvdir.in urandom.in s6-svscan.in ${SRCS-${OS}}
BIN= ${OBJS}
# Are we installing our network scripts?
@@ -19,11 +19,11 @@ SRCS-FreeBSD= hostid.in modules.in moused.in newsyslog.in pf.in rarpd.in \
rc-enabled.in rpcbind.in savecore.in syslogd.in
# These are FreeBSD specific
SRCS-FreeBSD+= adjkerntz.in devd.in dumpon.in encswap.in ipfw.in \
modules.in modules-load.in mixer.in nscd.in powerd.in syscons.in
modules-load.in mixer.in nscd.in powerd.in syscons.in
SRCS-Linux= binfmt.in devfs.in dmesg.in hwclock.in consolefont.in keymaps.in \
killprocs.in modules.in modules-load.in mount-ro.in mtab.in numlock.in \
procfs.in net-online.in sysfs.in termencoding.in tmpfiles.dev.in
SRCS-Linux= agetty.in binfmt.in devfs.in dmesg.in hwclock.in consolefont.in \
keymaps.in killprocs.in modules.in modules-load.in mount-ro.in mtab.in \
numlock.in procfs.in net-online.in sysfs.in termencoding.in
# Generic BSD scripts
SRCS-NetBSD= hostid.in moused.in newsyslog.in pf.in rarpd.in rc-enabled.in \

View File

@@ -23,6 +23,7 @@ fi
depend()
{
after swclock
provide clock
# BSD adjkerntz needs to be able to write to /etc
if [ "$clock" = "UTC" -a -e /etc/wall_cmos_clock ] ||

32
init.d/agetty.in Normal file
View File

@@ -0,0 +1,32 @@
#!@SBINDIR@/openrc-run
# Copyright (c) 2017 The OpenRC Authors.
# See the Authors file at the top-level directory of this distribution and
# https://github.com/OpenRC/openrc/blob/master/AUTHORS
#
# This file is part of OpenRC. It is subject to the license terms in
# the LICENSE file found in the top-level directory of this
# distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
# This file may not be copied, modified, propagated, or distributed
# except according to the terms contained in the LICENSE file.
description="start agetty on a terminal line"
supervisor=supervise-daemon
port="${RC_SVCNAME#*.}"
term_type="${term_type:-linux}"
command=/sbin/agetty
command_args_foreground="${agetty_options} ${port} ${baud} ${termtype}"
pidfile="/run/${RC_SVCNAME}.pid"
depend() {
after local
keyword -prefix
}
start_pre() {
if [ -z "$port" ]; then
eerror "${RC_SVCNAME} cannot be started directly. You must create"
eerror "symbolic links to it for the ports you want to start"
eerror "agetty on and add those to the appropriate runlevels."
return 1
fi
}

View File

@@ -13,7 +13,7 @@ description="Register misc binary format handlers"
depend()
{
after procfs
after clock procfs
use modules devfs
keyword -docker -lxc -openvz -prefix -systemd-nspawn -vserver
}

View File

@@ -71,7 +71,8 @@ cleanup_var_run_dir()
ebegin "Cleaning /var/run"
for x in $(find /var/run ! -type d ! -name utmp \
! -name random-seed ! -name dev.db \
! -name ld-elf.so.hints ! -name ld.so.hints);
! -name ld-elf.so.hints ! -name ld-elf32.so.hints \
! -name ld.so.hints);
do
# Clean stale sockets
if [ -S "$x" ]; then

View File

@@ -13,6 +13,7 @@ description="Creates the dev database"
depend()
{
after clock
need localmount
}

View File

@@ -12,6 +12,7 @@
description="Configures a specific kernel dump device."
depend() {
after clock
need swap
keyword -jail -prefix
}

View File

@@ -15,6 +15,7 @@ _IFS="
depend()
{
after clock
use dev clock modules
keyword -docker -jail -lxc -openvz -prefix -systemd-nspawn -timeout -vserver -uml
}

View File

@@ -15,6 +15,7 @@ extra_commands="reset"
depend()
{
use root
after clock
before devd net
keyword -jail -prefix
}

View File

@@ -12,6 +12,7 @@
description="Sets the hostname of the machine."
depend() {
after clock
keyword -docker -lxc -prefix -systemd-nspawn
}

View File

@@ -33,8 +33,6 @@ depend()
want modules
if yesno $clock_adjfile; then
use root
else
before *
fi
keyword -docker -lxc -openvz -prefix -systemd-nspawn -uml -vserver -xenu
}

View File

@@ -14,7 +14,7 @@ description="Applies a keymap for the consoles."
depend()
{
need localmount termencoding
after bootmisc
after bootmisc clock
keyword -docker -lxc -openvz -prefix -systemd-nspawn -uml -vserver -xenu
}

View File

@@ -14,17 +14,18 @@ description="Mounts disks and swap according to /etc/fstab."
depend()
{
need fsck
use lvm modules mtab
after lvm modules
use lvm modules mtab root
after clock lvm modules root
keyword -docker -jail -lxc -prefix -systemd-nspawn -vserver
}
start()
{
# Mount local filesystems in /etc/fstab.
# The types variable must start with no, and must be a type
local critical= types="noproc" x= no_netdev= rc=
for x in $net_fs_list $extra_net_fs_list; do
types="${types},no${x}"
types="${types},${x}"
done
if [ "$RC_UNAME" = Linux ]; then

View File

@@ -13,6 +13,7 @@ description="Configures the loopback interface."
depend()
{
after clock
keyword -jail -prefix -systemd-nspawn -vserver
}
@@ -29,7 +30,6 @@ start()
else
ebegin "Bringing up network interface lo0"
ifconfig lo0 127.0.0.1 netmask 255.0.0.0
route -q add -inet 127.0.0.0 -netmask 255.0.0.0 127.0.0.1
fi
eend $?
}

View File

@@ -31,7 +31,7 @@ FreeBSD_modules()
Linux_modules()
{
# Should not fail if kernel do not have module
# Should not fail if kernel does not have module
# support compiled in ...
[ ! -f /proc/modules ] && return 0
@@ -48,22 +48,21 @@ Linux_modules()
x=${x%.*}
done
local list= x= xx= y= args= mpargs= cnt=0 a=
local list= x= xx= y= args= mpargs= a=
for x in $kv_variant_list ; do
eval list=\$modules_$(shell_var "$x")
[ -n "$list" ] && break
done
[ -z "$list" ] && list=$modules
[ -n "$list" ] && ebegin "Loading kernel modules"
for x in $list; do
a=${x#*:}
if [ "$a" = "$x" ]; then
unset mpargs
ebegin "Loading module $x"
else
x=${x%%:*}
mpargs="-o $a"
ebegin "Loading module $x as $a"
fi
aa=$(shell_var "$a")
xx=$(shell_var "$x")
@@ -75,10 +74,9 @@ Linux_modules()
done
[ -z "$args" ] && eval args=\$module_${aa}_args
[ -z "$args" ] && eval args=\$module_${xx}_args
eval modprobe --use-blacklist -q "$mpargs" "$x" "$args"
eend $? "Failed to load $x" && : $(( cnt += 1 ))
eval modprobe --use-blacklist --verbose "$mpargs" "$x" "$args"
done
einfo "Autoloaded $cnt module(s)"
[ -n "$list" ] && eend
}
start()

View File

@@ -13,7 +13,7 @@ description="Re-mount filesytems read-only for a clean reboot."
depend()
{
need killprocs savecache
after killprocs savecache
keyword -docker -lxc -openvz -prefix -systemd-nspawn -vserver
}

View File

@@ -13,6 +13,7 @@ description="Update /etc/mtab to match what the kernel knows about"
depend()
{
after clock
need root
keyword -prefix -systemd-nspawn
}

View File

@@ -15,6 +15,7 @@ depend()
{
after modules
need sysfs
provide network-online
keyword -docker -jail -lxc -openvz -prefix -systemd-nspawn -uml -vserver
}
@@ -27,19 +28,6 @@ get_interfaces()
done
}
get_default_gateway()
{
local cmd gateway
if command -v ip > /dev/null 2>&1; then
cmd="ip route show"
else
cmd=route
fi
set -- $($cmd | grep default)
[ "$2" != via ] && gateway="$2" || gateway="$3"
printf "%s" $gateway
}
start ()
{
local carriers configured dev gateway ifcount infinite
@@ -66,10 +54,15 @@ start ()
: $((timeout -= 1))
done
! $infinite && [ $timeout -eq 0 ] && rc=1
if [ $rc -eq 0 ] && yesno ${ping_default_gateway:-no}; then
gateway="$(get_default_gateway)"
if [ -n "$gateway" ] && ! ping -c 1 $gateway > /dev/null 2>&1; then
rc=1
include_ping_test=${include_ping_test:-${ping_default_gateway}}
if [ -n "${ping_default_gateway}" ]; then
ewarn "ping_default_gateway is deprecated, please use include_ping_test"
fi
if [ $rc -eq 0 ] && yesno ${include_ping_test:-no}; then
ping_test_host="${ping_test_host:-google.com}"
if [ -n "$ping_test_host" ]; then
ping -c 1 $ping_test_host > /dev/null 2>&1
rc=$?
fi
fi
eend $rc "The network is offline"

View File

@@ -20,10 +20,12 @@ depend()
*) mywant="$mywant nfsclient"; break ;;
esac
done
after root
config /etc/fstab
want $mywant
use afc-client amd openvpn
use dns
use root
keyword -docker -jail -lxc -prefix -systemd-nspawn -vserver
}

View File

@@ -18,7 +18,7 @@ __nl="
depend()
{
need localmount
after bootmisc
after bootmisc clock
if [ -n "$(interfaces)" ]; then
provide net
fi

View File

@@ -13,6 +13,7 @@ required_files="/etc/newsyslog.conf"
depend()
{
after clock
need localmount
keyword -prefix
}

View File

@@ -13,6 +13,7 @@ description="Mounts misc filesystems in /proc."
depend()
{
after clock
use devfs
want modules
need localmount

View File

@@ -13,6 +13,7 @@ description="Mount the root fs read/write"
depend()
{
after clock
need fsck
keyword -docker -jail -lxc -openvz -prefix -systemd-nspawn -vserver
}

View File

@@ -14,6 +14,7 @@ description="Saves a kernel dump."
depend()
{
need dumpon localmount
after clock
before encswap
keyword -jail -prefix
}

View File

@@ -1,4 +1,4 @@
#!@SBINDIR@/openrc-run
S#!@BINDIR@/openrc-run
# Copyright (c) 2009-2015 The OpenRC Authors.
# See the Authors file at the top-level directory of this distribution and
# https://github.com/OpenRC/openrc/blob/master/AUTHORS
@@ -14,9 +14,9 @@
description="Configures static routes."
__nl="
"
depend()
{
after clock
provide net
use network
keyword -jail -prefix -vserver

View File

@@ -11,6 +11,7 @@
depend()
{
after clock
before fsck
keyword -jail -prefix
}

View File

@@ -11,6 +11,7 @@
depend()
{
after clock
before localmount
keyword -docker -jail -lxc -openvz -prefix -systemd-nspawn -vserver
}

View File

@@ -13,7 +13,6 @@ description="Sets the local clock to the mtime of a given file."
depend()
{
before *
provide clock
keyword -docker -lxc -openvz -prefix -systemd-nspawn -uml -vserver -xenu
}

View File

@@ -10,6 +10,7 @@
# except according to the terms contained in the LICENSE file.
depend() {
after clock
need localmount
keyword -jail -prefix
}

View File

@@ -11,6 +11,7 @@
depend()
{
after clock
before bootmisc logger
keyword -prefix -systemd-nspawn -vserver
}

View File

@@ -15,7 +15,6 @@ sysfs_opts=nodev,noexec,nosuid
depend()
{
want modules
keyword -docker -lxc -prefix -systemd-nspawn -vserver
}
@@ -99,23 +98,12 @@ mount_misc()
fi
# set up kernel support for efivarfs
# The presence of /sys/firmware/efi indicates that the system was
# booted in efi mode.
if [ -d /sys/firmware/efi ]; then
if [ ! -d /sys/firmware/efi/efivars ] &&
modprobe -q efivarfs; then
ewarn "The efivarfs module needs to be configured in " \
"@SYSCONFDIR@/conf.d/modules or built in"
fi
if [ -d /sys/firmware/efi/efivars ] &&
! mountinfo -q /sys/firmware/efi/efivars; then
if grep -qs efivarfs /proc/filesystems; then
ebegin "Mounting efivarfs filesystem"
mount -n -t efivarfs -o ${sysfs_opts} \
efivarfs /sys/firmware/efi/efivars
eend $?
fi
fi
if [ -d /sys/firmware/efi/efivars ] &&
! mountinfo -q /sys/firmware/efi/efivars; then
ebegin "Mounting efivarfs filesystem"
mount -n -t efivarfs -o ${sysfs_opts} \
efivarfs /sys/firmware/efi/efivars 2> /dev/null
eend 0
fi
}

View File

@@ -22,6 +22,6 @@ depend()
provide logger
use net newsyslog
need localmount
after bootmisc
after bootmisc clock
keyword -prefix
}

View File

@@ -18,7 +18,7 @@ depend()
{
keyword -docker -lxc -openvz -prefix -systemd-nspawn -uml -vserver -xenu
use root
after bootmisc
after bootmisc clock
}
start()

View File

@@ -1,20 +0,0 @@
#!@SBINDIR@/openrc-run
# Copyright 1999-2012 Gentoo Foundation
# Released under the 2-clause BSD license.
description="Set up tmpfiles.d entries"
depend()
{
use dev-mount
before dev
keyword -prefix -vserver
}
start()
{
ebegin "Setting up tmpfiles.d entries for /dev"
@LIBEXECDIR@/sh/tmpfiles.sh --prefix=/dev --create --boot ${tmpfiles_opts}
eend $?
return 0
}

View File

@@ -1,19 +0,0 @@
#!@SBINDIR@/openrc-run
# Copyright 1999-2012 Gentoo Foundation
# Released under the 2-clause BSD license.
description="Set up tmpfiles.d entries"
depend()
{
need localmount
}
start()
{
ebegin "Setting up tmpfiles.d entries"
@LIBEXECDIR@/sh/tmpfiles.sh --exclude-prefix=/dev --create --remove --boot \
${tmpfiles_opts}
eend $?
return 0
}

View File

@@ -11,7 +11,7 @@
depend()
{
after fsck
after clock fsck
keyword -prefix
}

View File

@@ -14,6 +14,7 @@ description="Initializes the random number generator."
depend()
{
after clock
need localmount
keyword -docker -jail -lxc -openvz -prefix -systemd-nspawn
}

View File

@@ -11,6 +11,7 @@
depend()
{
after clock
need localmount
keyword -prefix
}

View File

@@ -9,7 +9,7 @@ MAN8= rc-service.8 rc-status.8 rc-update.8 openrc.8 openrc-run.8 \
service.8 start-stop-daemon.8 supervise-daemon.8
ifeq (${OS},Linux)
MAN8 += rc-sstat.8
MAN8 += rc-sstat.8 openrc-init.8 openrc-shutdown.8
endif
# Handy macro to create symlinks

46
man/openrc-init.8 Normal file
View File

@@ -0,0 +1,46 @@
.\" Copyright (c) 2017 The OpenRC Authors.
.\" See the Authors file at the top-level directory of this distribution and
.\" https://github.com/OpenRC/openrc/blob/master/AUTHORS
.\"
.\" This file is part of OpenRC. It is subject to the license terms in
.\" the LICENSE file found in the top-level directory of this
.\" distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
.\" This file may not be copied, modified, propagated, or distributed
.\" except according to the terms contained in the LICENSE file.
.\"
.Dd April 6, 2017
.Dt openrc-init 8 SMM
.Os OpenRC
.Sh NAME
.Nm openrc-init
.Nd the parent of all processes
.Sh SYNOPSIS
.Nm
.Sh DESCRIPTION
.Nm
is an init process which can be an alternative to sysvinit or any other
init process.
.Pp
To use
.Nm
configure your boot loader to invoke it or symlink it to /sbin/init.
Also, you will need to use
.Xr openrc-shutdown 8 ,
to halt, reboot or poweroff the system.
.Pp
The default runlevel is read from the init command line, the
rc_default_runlevel setting in rc.conf, the kernel command line, or it is
assumed to be "default" if it is not set in any of these places.
.Pp
.Nm
doesn't manage getty's directly, so you will need to manage them another
way. For example, you can use the agetty service script as described in
agetty-guide.md in this distribution.
.Sh BUGS
This was first released as part of OpenRC 0.25.
I do not know of any specific issues. However, since this is the first
release of openrc-init, please test and report any issues you find.
.Sh SEE ALSO
.Xr openrc-shutdown 8 ,
.Sh AUTHORS
.An William Hubbs <w.d.hubbs@gmail.com>

View File

@@ -97,7 +97,7 @@ String describing the extra command.
.It Ar supervisor
Supervisor to use to monitor this daemon. If this is unset or invalid,
start-stop-daemon will be used.
Currently, we support s6 from scarnet software, and supervise-daemon
Currently, we support s6 from skarnet software, and supervise-daemon
which is a light-weight supervisor internal to OpenRC.
To use s6, set
supervisor=s6.
@@ -167,6 +167,24 @@ Display name used for the above defined command.
Process name to match when signaling the daemon.
.It Ar stopsig
Signal to send when stopping the daemon.
.It Ar respawn_delay
Respawn delay
.Xr supervise-daemon 8
will use for this daemon. See
.Xr supervise-daemon 8
for more information about this setting.
.It Ar respawn_max
Respawn max
.Xr supervise-daemon 8
will use for this daemon. See
.Xr supervise-daemon 8
for more information about this setting.
.It Ar respawn_period
Respawn period
.Xr supervise-daemon 8
will use for this daemon. See
.Xr supervise-daemon 8
for more information about this setting.
.It Ar retry
Retry schedule to use when stopping the daemon. It can either be a
timeout in seconds or multiple signal/timeout pairs (like SIGTERM/5).

47
man/openrc-shutdown.8 Normal file
View File

@@ -0,0 +1,47 @@
.\" Copyright (c) 2017 The OpenRC Authors.
.\" See the Authors file at the top-level directory of this distribution and
.\" https://github.com/OpenRC/openrc/blob/master/AUTHORS
.\"
.\" This file is part of OpenRC. It is subject to the license terms in
.\" the LICENSE file found in the top-level directory of this
.\" distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
.\" This file may not be copied, modified, propagated, or distributed
.\" except according to the terms contained in the LICENSE file.
.\"
.Dd April 6, 2017
.Dt openrc-shutdown 8 SMM
.Os OpenRC
.Sh NAME
.Nm openrc-shutdown
.Nd bring the system down
.Sh SYNOPSIS
.Nm
.Op Fl H , -halt
.Op Fl k , -kexec
.Op Fl p , -poweroff
.Op Fl R , -reexec
.Op Fl r , -reboot
.Sh DESCRIPTION
.Nm
is the utility that communicates with openrc-init(8) to bring down the
system or instruct openrc-init to re-execute itself. It supports the
following options:
.Bl -tag -width "poweroff"
.It Fl H , -halt
Stop all services, kill all remaining processes and halt the system.
.It Fl k , -kexec
Stop all services, kill all processes and boot directly into a new
kernel loaded via kexec(8).
.It Fl p , -poweroff
Stop all services, kill all processes and power off the system.
.It Fl R , -reexec
instruct openrc-init to re-exec itself. This should be used after an
upgrade of OpenRC if you are using openrc-init as your init process.
.It Fl r , -reboot
Stop all services, kill all processes and reboot the system.
.El
.Sh SEE ALSO
.Xr openrc-init 8 ,
.Xr kexec 8 ,
.Sh AUTHORS
.An William Hubbs <w.d.hubbs@gmail.com>

View File

@@ -25,6 +25,12 @@ in different runlevels. The default behavior is to show information
about the current runlevel and any unassigned services that are not stopped,
but any runlevel can be quickly examined.
.Pp
If an active service is being supervised by
.Xr supervise-daemon 8,
the amount of time the daemon has been active along with the number of
times it has been respawned in the current respawn period will be
displayed.
.Pp
The options are as follows:
.Bl -tag -width ".Fl test , test string"
.It Fl a , -all
@@ -57,5 +63,6 @@ dependency order if the dependency tree is available.
.Sh SEE ALSO
.Xr openrc 8 ,
.Xr rc-update 8
.Xr supervise-daemon 8
.Sh AUTHORS
.An Roy Marples <roy@marples.name>

View File

@@ -55,7 +55,7 @@ is used.
.It Fl p , -pidfile Ar pidfile
When starting, we expect the daemon to create a valid
.Ar pidfile
within a reasonable amount of time. When stopping we only stop the pid(s)
within a reasonable amount of time. When stopping we only stop the first pid
listed in the
.Ar pidfile .
.It Fl n , -name Ar name

View File

@@ -16,6 +16,8 @@
.Nd starts a daemon and restarts it if it crashes
.Sh SYNOPSIS
.Nm
.Fl D , -respawn-delay
.Ar seconds
.Fl d , -chdir
.Ar path
.Fl e , -env
@@ -26,14 +28,18 @@
.Ar arg
.Fl k , -umask
.Ar value
.Fl m , -respawn-max
.Ar count
.Fl N , -nicelevel
.Ar level
.Fl p , -pidfile
.Ar pidfile
.Fl u , -user
.Ar user
.Fl P , -respawn-period
.Ar seconds
.Fl r , -chroot
.Ar chrootpath
.Fl u , -user
.Ar user
.Fl 1 , -stdout
.Ar logfile
.Fl 2 , -stderr
@@ -82,6 +88,9 @@ Print the action(s) that are taken just before doing them.
.Pp
The options are as follows:
.Bl -tag -width indent
.It Fl D , -respawn-delay Ar seconds
wait this number of seconds before restarting a daemon after it crashes.
The default is 0.
.It Fl d , -chdir Ar path
chdir to this directory before starting the daemon.
.It Fl e , -env Ar VAR=VALUE
@@ -94,8 +103,18 @@ Class can be 0 for none, 1 for real time, 2 for best effort and 3 for idle.
Data can be from 0 to 7 inclusive.
.It Fl k , -umask Ar mode
Set the umask of the daemon.
.It Fl m , -respawn-max Ar count
Sets the maximum number of times a daemon will be respawned during a
respawn period. If a daemon dies more than this number of times during a
respawn period,
.Nm
will give up trying to respawn it and exit. The default is 10, and 0
means unlimited.
.It Fl N , -nicelevel Ar level
Modifies the scheduling priority of the daemon.
.It Fl P , -respawn-period Ar seconds
Sets the length of a respawn period. The default is 10 seconds. See the
description of --respawn-max for more information.
.It Fl r , -chroot Ar path
chroot to this directory before starting the daemon. All other paths, such
as the path to the daemon, chdir and pidfile, should be relative to the chroot.
@@ -123,6 +142,15 @@ to parse its options, which allows it to accept the `--' option which will
cause it to stop processing options at that point. Any subsequent arguments
are passed as arguments to the daemon to start and used when finding a daemon
to stop or signal.
.Sh NOTE
If respawn-delay, respawn-max and respawn-period are not set correctly,
it is possible to trigger a situation in which the supervisor will
infinitely try to respawn a daemon. To avoid this, if you change the
values of --respawn-delay, --respawn-max or --respawn-period, always
make sure the settings mmake sense. For example, a respawn period of 5
seconds with a respawn max of 10 and a respawn delay of 1 second leads
to infinite respawning since there can never be 10 respawns within 5
seconds.
.Sh SEE ALSO
.Xr chdir 2 ,
.Xr chroot 2 ,

View File

@@ -11,5 +11,5 @@
SFX= .GNU.in
PKG_PREFIX?= /usr
CPPFLAGS+= -D_BSD_SOURCE -D_XOPEN_SOURCE=700 -DMAXPATHLEN=4096 -DPATH_MAX=4096
CPPFLAGS+= -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=700 -DMAXPATHLEN=4096 -DPATH_MAX=4096
LIBDL= -Wl,-Bdynamic -ldl

View File

@@ -11,7 +11,7 @@
SFX= .Linux.in
PKG_PREFIX?= /usr
CPPFLAGS+= -D_BSD_SOURCE -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=700
CPPFLAGS+= -D_DEFAULT_SOURCE -D_XOPEN_SOURCE=700
LIBDL= -Wl,-Bdynamic -ldl
ifeq (${MKSELINUX},yes)

View File

@@ -59,6 +59,9 @@ MANPREFIX?= ${UPREFIX}/share
MANDIR?= ${MANPREFIX}/man
MANMODE?= 0444
DATADIR?= ${UPREFIX}/share/openrc
DATAMODE?= 0644
DOCDIR?= ${UPREFIX}/share/doc
DOCMODE?= 0644

View File

@@ -36,10 +36,9 @@ BOOT-FreeBSD+= hostid modules newsyslog savecore syslogd
# FreeBSD specific stuff
BOOT-FreeBSD+= adjkerntz dumpon syscons
BOOT-Linux+= binfmt hwclock keymaps modules mtab procfs termencoding \
tmpfiles.setup
BOOT-Linux+= binfmt hwclock keymaps modules mtab procfs termencoding
SHUTDOWN-Linux= killprocs mount-ro
SYSINIT-Linux= devfs dmesg sysfs tmpfiles.dev
SYSINIT-Linux= devfs dmesg sysfs
# Generic BSD stuff
BOOT-NetBSD+= hostid newsyslog savecore syslogd

View File

@@ -13,7 +13,7 @@ endif
_installafter:
ifeq (${OS},Linux)
${INSTALL} -d ${DESTDIR}${SBINDIR}
ln -s ${DIR}/rc-sstat ${DESTDIR}/${SBINDIR}/rc-sstat
ln -sf ${DIR}/rc-sstat ${DESTDIR}/${SBINDIR}/rc-sstat
endif
include ${MK}/scripts.mk

1
sh/.gitignore vendored
View File

@@ -6,6 +6,5 @@ cgroup-release-agent.sh
init.sh
init-early.sh
rc-cgroup.sh
tmpfiles.sh
migrate-to-run.sh
binfmt.sh

View File

@@ -1,9 +1,9 @@
DIR= ${LIBEXECDIR}/sh
SRCS= init.sh.in functions.sh.in gendepends.sh.in \
openrc-run.sh.in rc-functions.sh.in tmpfiles.sh.in ${SRCS-${OS}}
openrc-run.sh.in rc-functions.sh.in ${SRCS-${OS}}
INC= rc-mount.sh functions.sh rc-functions.sh runit.sh s6.sh \
start-stop-daemon.sh supervise-daemon.sh
BIN= gendepends.sh init.sh openrc-run.sh tmpfiles.sh ${BIN-${OS}}
BIN= gendepends.sh init.sh openrc-run.sh ${BIN-${OS}}
INSTALLAFTER= _installafter

View File

@@ -74,11 +74,22 @@ do
# Only generate dependencies for OpenRC scripts
read one two three <"$RC_SERVICE"
[ "$one" = "#!@SBINDIR@/runscript" ] || \
[ "$one" = "#!@SBINDIR@/openrc-run" ] || \
[ "$one" = "#!" -a "$two" = "@SBINDIR@/runscript" ] || \
[ "$one" = "#!" -a "$two" = "@SBINDIR@/openrc-run" ] || \
continue
case "$one" in
\#*/openrc-run) ;;
\#*/runscript) ;;
\#!)
case "$two" in
*/openrc-run) ;;
*/runscript) ;;
*)
continue
;;
esac
;;
*)
continue
;;
esac
unset one two three
RC_SVCNAME=${RC_SERVICE##*/} ; export RC_SVCNAME

View File

@@ -11,6 +11,16 @@ if [ -d "@SYSCONFDIR@/rc.conf.d" ]; then
done
fi
# check for md5sum, and probably /usr too
if command -v md5sum >/dev/null; then
got_md5sum=true
else
eerror "md5sum is missing, which suggests /usr is not mounted"
eerror "If you have separate /usr, it must be mounted by initramfs"
eerror "If not, you should check coreutils is installed correctly"
got_md5sum=false
fi
# By default VServer already has /proc mounted, but OpenVZ does not!
# However, some of our users have an old proc image in /proc
# NFC how they managed that, but the end result means we have to test if
@@ -21,9 +31,12 @@ fi
mountproc=true
f=/proc/self/environ
if [ -e $f ]; then
if [ "$(VAR=a md5sum $f)" = "$(VAR=b md5sum $f)" ]; then
if $got_md5sum && [ "$(VAR=a md5sum $f)" = "$(VAR=b md5sum $f)" ]; then
eerror "You have cruft in /proc that should be deleted"
else
# If they don't have md5sum, this will fail in pretty ways if
# /proc isn't really mounted. Oh well, their system is busted
# anyway, and they get to keep the pieces.
einfo "/proc is already mounted"
mountproc=false
fi
@@ -31,11 +44,9 @@ fi
unset f
if $mountproc; then
procfs="proc"
[ "$RC_UNAME" = "GNU/kFreeBSD" ] && proc="linprocfs"
ebegin "Mounting /proc"
if ! fstabinfo --mount /proc; then
mount -n -t "$procfs" -o noexec,nosuid,nodev proc /proc
mount -n -t proc -o noexec,nosuid,nodev proc /proc
fi
eend $?
fi

View File

@@ -146,10 +146,9 @@ _status()
fi
}
# Template start / stop / status functions
# These functions select the appropriate function to call from the
# supervisor modules
start()
default_start()
{
local func=ssd_start
case "$supervisor" in
@@ -163,7 +162,7 @@ start()
$func
}
stop()
default_stop()
{
local func=ssd_stop
case "$supervisor" in
@@ -177,7 +176,7 @@ stop()
$func
}
status()
default_status()
{
local func=ssd_status
case "$supervisor" in
@@ -191,6 +190,26 @@ status()
$func
}
# Template start / stop / status functions
# package init scripts may override these, but the bodies are as minimal as
# possible, so that the init scripts can creatively wrap default_*
# functions.
start()
{
default_start
}
stop()
{
default_stop
}
status()
{
default_status
}
# Start debug output
yesno $RC_DEBUG && set -x
# Load configuration settings. First the global ones, then any

View File

@@ -85,6 +85,40 @@ get_bootparam()
return 1
}
get_bootparam_value()
{
local match="$1" which_value="$2" sep="$3" result value
if [ -n "$match" -a -r /proc/cmdline ]; then
set -- $(cat /proc/cmdline)
while [ -n "$1" ]; do
case "$1" in
$match=*)
value="${1##*=}"
case "$which_value" in
all)
[ -z "$sep" ] && sep=' '
if [ -z "$result" ]; then
result="$value"
else
result="${result}${sep}${value}"
fi
;;
last)
result="$value"
;;
*)
result="$value"
break
;;
esac
;;
esac
shift
done
fi
echo $result
}
# Called from openrc-run.sh or gendepends.sh
_get_containers() {
local c

View File

@@ -25,6 +25,9 @@ supervise_start()
eval supervise-daemon --start \
${chroot:+--chroot} $chroot \
${pidfile:+--pidfile} $pidfile \
${respawn_delay:+--respawn-delay} $respawn_delay \
${respawn_max:+--respawn-max} $respawn_max \
${respawn_period:+--respawn-period} $respawn_period \
${command_user+--user} $command_user \
$supervise_daemon_args \
$command \

View File

@@ -1,457 +0,0 @@
#!/bin/sh
# This is a reimplementation of the systemd tmpfiles.d code
# Control creation, deletion, and cleaning of volatile and temporary files
#
# Copyright (c) 2012 Gentoo Foundation
# Released under the 2-clause BSD license.
#
# This instance is a pure-POSIX sh version, written by Robin H Johnson
# <robbat2@gentoo.org>, based on the Arch Linux version as of 2012/01/01:
# http://projects.archlinux.org/initscripts.git/tree/arch-tmpfiles
#
# See the tmpfiles.d manpage as well:
# https://www.freedesktop.org/software/systemd/man/tmpfiles.d.html
# This script should match the old manpage
# http://0pointer.de/public/systemd-man/tmpfiles.d.html
# as of 2012/03/12 and also implements some more recent features
#
DRYRUN=0
CHECKPATH="@LIBEXECDIR@/bin/checkpath"
checkprefix() {
n=$1
shift
for x in $@; do
case $n in
${x}*) return 0 ;;
esac
done
return 1
}
warninvalid() {
printf "tmpfiles: ignoring invalid entry on line %d of \`%s'\n" "$LINENUM" "$FILE"
error=$(( error+1 ))
} >&2
invalid_option() {
printf "tmpfiles: invalid option '%s'\n" "$1" >&2
exit 1
}
dryrun_or_real() {
local dryrun=
[ $DRYRUN -eq 1 ] && dryrun=echo
$dryrun "$@"
}
_chattr() {
local attr="$2"
case $attr in
[+-=]*) : ;;
'') return ;;
*) attr="+$attr" ;;
esac
local IFS=
dryrun_or_real chattr $1 "$attr" -- $3
}
relabel() {
local path
local paths=$1 mode=$2 uid=$3 gid=$4
for path in ${paths}; do
if [ -e "$path" ]; then
[ -x /sbin/restorecon ] && dryrun_or_real restorecon $CHOPTS "$path"
[ $uid != '-' ] && dryrun_or_real chown $CHOPTS "$uid" "$path"
[ $gid != '-' ] && dryrun_or_real chgrp $CHOPTS "$gid" "$path"
[ $mode != '-' ] && dryrun_or_real chmod $CHOPTS "$mode" "$path"
fi
done
}
splitpath() {
local path=$1
while [ -n "$path" ]; do
echo $path
path=${path%/*}
done
}
_restorecon() {
local path=$1
if [ -x /sbin/restorecon ]; then
dryrun_or_real restorecon -F $(splitpath "$path")
fi
}
_b() {
# Create a block device node if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
if [ ! -e "$path" ]; then
dryrun_or_real mknod -m $mode $path b ${arg%:*} ${arg#*:}
_restorecon "$path"
dryrun_or_real chown $uid:$gid $path
fi
}
_c() {
# Create a character device node if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
if [ ! -e "$path" ]; then
dryrun_or_real mknod -m $mode $path c ${arg%:*} ${arg#*:}
_restorecon "$path"
dryrun_or_real chown $uid:$gid $path
fi
}
_C() {
# recursively copy a file or directory
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
if [ ! -e "$path" ]; then
dryrun_or_real cp -r "$arg" "$path"
_restorecon "$path"
[ $uid != '-' ] && dryrun_or_real chown "$uid" "$path"
[ $gid != '-' ] && dryrun_or_real chgrp "$gid" "$path"
[ $mode != '-' ] && dryrun_or_real chmod "$mode" "$path"
fi
}
_f() {
# Create a file if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
[ $CREATE -gt 0 ] || return 0
if [ ! -e "$path" ]; then
dryrun_or_real $CHECKPATH -fq -m "$mode" -o "$uid:$gid" "$path"
[ -z "$arg" ] || _w "$@"
fi
}
_F() {
# Create or truncate a file
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
[ $CREATE -gt 0 ] || return 0
dryrun_or_real $CHECKPATH -Fq -m "$mode" -o "$uid:$gid" "$path"
[ -z "$arg" ] || _w "$@"
}
_d() {
# Create a directory if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4
[ $CREATE -gt 0 ] || return 0
if [ ! -d "$path" ]; then
dryrun_or_real mkdir -p "$path" 2>/dev/null
_restorecon "$path"
dryrun_or_real $CHECKPATH -dq -m "$mode" -o "$uid:$gid" "$path"
fi
}
_D() {
# Create or empty a directory
local path=$1 mode=$2 uid=$3 gid=$4
if [ -d "$path" ] && [ $REMOVE -gt 0 ]; then
dryrun_or_real find "$path" -mindepth 1 -maxdepth 1 -xdev -exec rm -rf {} +
_restorecon "$path"
fi
if [ $CREATE -gt 0 ]; then
dryrun_or_real mkdir -p "$path" 2>/dev/null
_restorecon "$path"
dryrun_or_real $CHECKPATH -Dq -m "$mode" -o "$uid:$gid" "$path"
fi
}
_v() {
# Create a subvolume if the path does not exist yet and the file system
# supports this (btrfs). Otherwise create a normal directory.
# TODO: Implement btrfs subvol creation.
_d "$@"
}
_q() {
# Similar to _v. However, make sure that the subvolume will be assigned
# to the same higher-level quota groups as the subvolume it has
# been created in.
# TODO: Implement btrfs subvol creation.
_d "$@"
}
_Q() {
# Similar to q. However, instead of copying the higher-level quota
# group assignments from the parent as-is, the lowest quota group
# of the parent subvolume is determined that is not the
# leaf quota group.
# TODO: Implement btrfs subvol creation.
_d "$@"
}
_h() {
# Set file/directory attributes. Lines of this type accept
# shell-style globs in place of normal path names.
# The format of the argument field matches chattr
_chattr '' "$6" "$1"
}
_H() {
# Recursively set file/directory attributes. Lines of this type accept
# shell-syle globs in place of normal path names.
# Does not follow symlinks
_chattr -R "$6" "$1"
}
_L() {
# Create a symlink if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
[ ! -e "$path" ] && dryrun_or_real ln -s "$arg" "$path"
_restorecon "$path"
}
_p() {
# Create a named pipe (FIFO) if it doesn't exist yet
local path=$1 mode=$2 uid=$3 gid=$4
[ $CREATE -gt 0 ] || return 0
if [ ! -p "$path" ]; then
dryrun_or_real $CHECKPATH -pq -m $mode -o "$uid:$gid" "$path"
fi
}
_x() {
# Ignore a path during cleaning. Use this type to exclude paths from clean-up as
# controlled with the Age parameter. Note that lines of this type do not
# influence the effect of r or R lines. Lines of this type accept shell-style
# globs in place of of normal path names.
:
# XXX: we don't implement this
}
_X() {
# Ignore a path during cleanup. Use this type to prevent path
# removal as controled with the age parameter. Note that if path is
# a directory, the content of the directory is not excluded from
# clean-up, only the directory itself.
# Lines of this type accept shell-style globs in place of normal path names.
:
# XXX: we don't implement this
}
_r() {
# Remove a file or directory if it exists. This may not be used to remove
# non-empty directories, use R for that. Lines of this type accept shell-style
# globs in place of normal path names.
local path
local paths=$1
[ $REMOVE -gt 0 ] || return 0
for path in ${paths}; do
if [ -f "$path" ]; then
dryrun_or_real rm -f "$path"
elif [ -d "$path" ]; then
dryrun_or_real rmdir "$path"
fi
done
}
_R() {
# Recursively remove a path and all its subdirectories (if it is a directory).
# Lines of this type accept shell-style globs in place of normal path names.
local path
local paths=$1
[ $REMOVE -gt 0 ] || return 0
for path in ${paths}; do
[ -d "$path" ] && dryrun_or_real rm -rf --one-file-system "$path"
done
}
_w() {
# Write the argument parameter to a file, if it exists.
local path=$1 mode=$2 uid=$3 gid=$4 age=$5 arg=$6
if [ -f "$path" ]; then
if [ $DRYRUN -eq 1 ]; then
echo "echo \"$arg\" >>\"$path\""
else
echo "$arg" >>"$path"
fi
fi
}
_z() {
# Set ownership, access mode and relabel security context of a file or
# directory if it exists. Lines of this type accept shell-style globs in
# place of normal path names.
[ $CREATE -gt 0 ] || return 0
relabel "$@"
}
_Z() {
# Recursively set ownership, access mode and relabel security context of a
# path and all its subdirectories (if it is a directory). Lines of this type
# accept shell-style globs in place of normal path names.
[ $CREATE -gt 0 ] || return 0
CHOPTS=-R relabel "$@"
}
BOOT=0 CREATE=0 REMOVE=0 CLEAN=0 VERBOSE=0 DRYRUN=0 error=0 LINENO=0
EXCLUDE=
PREFIX=
FILES=
while [ $# -gt 0 ]; do
case $1 in
--boot) BOOT=1 ;;
--create) CREATE=1 ;;
--remove) REMOVE=1 ;;
--clean) CLEAN=1 ;; # TODO: Not implemented
--verbose) VERBOSE=1 ;;
--dryrun|--dry-run) DRYRUN=1 ;;
--exclude-prefix=*) EXCLUDE="${EXCLUDE}${1##--exclude-prefix=} " ;;
--prefix=*) PREFIX="${PREFIX}${1##--prefix=} " ;;
-*) invalid_option "$1" ;;
*) FILES="${FILES} $1"
esac
shift
done
if [ $(( CLEAN )) -eq 1 ] ; then
printf '%s clean mode is not implemented\n' "${0##*/}"
exit 1
fi
if [ "$CREATE$REMOVE" = '00' ]; then
printf 'usage: %s [--exclude-prefix=path] [--prefix=path] [--boot] [--create] [--remove] [--clean] [--verbose] [--dry-run]\n' "${0##*/}"
exit 1
fi
# XXX: The harcoding of /usr/lib/ is an explicit choice by upstream
tmpfiles_dirs='/usr/lib/tmpfiles.d /run/tmpfiles.d /etc/tmpfiles.d'
tmpfiles_basenames=''
if [ -z "${FILES}" ]; then
# Build a list of sorted unique basenames
# directories declared later in the tmpfiles_d array will override earlier
# directories, on a per file basename basis.
# `/etc/tmpfiles.d/foo.conf' supersedes `/usr/lib/tmpfiles.d/foo.conf'.
# `/run/tmpfiles/foo.conf' will always be read after `/etc/tmpfiles.d/bar.conf'
for d in ${tmpfiles_dirs} ; do
[ -d $d ] && for f in ${d}/*.conf ; do
case "${f##*/}" in
systemd.conf|systemd-*.conf) continue;;
esac
[ -f $f ] && tmpfiles_basenames="${tmpfiles_basenames}\n${f##*/}"
done # for f in ${d}
done # for d in ${tmpfiles_dirs}
FILES="$(printf "${tmpfiles_basenames}\n" | sort -u )"
fi
tmpfiles_d=''
for b in ${FILES} ; do
if [ "${b##*/}" != "${b}" ]; then
# The user specified a path on the command line
# Just pass it through unaltered
tmpfiles_d="${tmpfiles_d} ${b}"
else
real_f=''
for d in $tmpfiles_dirs ; do
f=${d}/${b}
[ -f "${f}" ] && real_f=$f
done
[ -f "${real_f}" ] && tmpfiles_d="${tmpfiles_d} ${real_f}"
fi
done
error=0
# loop through the gathered fragments, sorted globally by filename.
# `/run/tmpfiles/foo.conf' will always be read after `/etc/tmpfiles.d/bar.conf'
FILE=
for FILE in $tmpfiles_d ; do
LINENUM=0
### FILE FORMAT ###
# XXX: We ignore the 'Age' parameter
# 1 2 3 4 5 6 7
# Cmd Path Mode UID GID Age Argument
# d /run/user 0755 root root 10d -
# Mode, UID, GID, Age, Argument may be omitted!
# If Cmd ends with !, the line is only processed if --boot is passed
# XXX: Upstream says whitespace is NOT permitted in the Path argument.
# But IS allowed when globs are expanded for the x/r/R/z/Z types.
while read cmd path mode uid gid age arg; do
LINENUM=$(( LINENUM+1 ))
FORCE=0
# Unless we have both command and path, skip this line.
if [ -z "$cmd" -o -z "$path" ]; then
continue
fi
case $cmd in
\#*) continue ;;
esac
while [ ${#cmd} -gt 1 ]; do
case $cmd in
*!) cmd=${cmd%!}; [ "$BOOT" -eq "1" ] || continue 2 ;;
*+) cmd=${cmd%+}; FORCE=1; ;;
*) warninvalid ; continue 2 ;;
esac
done
# whine about invalid entries
case $cmd in
f|F|w|d|D|v|p|L|c|C|b|x|X|r|R|z|Z|q|Q|h|H) ;;
*) warninvalid ; continue ;;
esac
# fall back on defaults when parameters are passed as '-'
if [ "$mode" = '-' -o "$mode" = '' ]; then
case "$cmd" in
p|f|F) mode=0644 ;;
d|D|v) mode=0755 ;;
C|z|Z|x|r|R|L) ;;
esac
fi
[ "$uid" = '-' -o "$uid" = '' ] && uid=0
[ "$gid" = '-' -o "$gid" = '' ] && gid=0
[ "$age" = '-' -o "$age" = '' ] && age=0
[ "$arg" = '-' -o "$arg" = '' ] && arg=''
set -- "$path" "$mode" "$uid" "$gid" "$age" "$arg"
[ -n "$EXCLUDE" ] && checkprefix $path $EXCLUDE && continue
[ -n "$PREFIX" ] && ! checkprefix $path $PREFIX && continue
if [ $FORCE -gt 0 ]; then
case $cmd in
p|L|c|b) [ -f "$path" ] && dryrun_or_real rm -f "$path"
esac
fi
[ "$VERBOSE" -eq "1" ] && echo _$cmd "$@"
_$cmd "$@"
rc=$?
if [ "${DRYRUN}" -eq "0" ]; then
[ $rc -ne 0 ] && error=$((error + 1))
fi
done <$FILE
done
exit $error
# vim: set ts=2 sw=2 sts=2 noet ft=sh:

View File

@@ -3,9 +3,5 @@
SUBDIR= test libeinfo librc rc
ifeq (${MKTOOLS},yes)
SUBDIR+= tools
endif
MK= ../mk
include ${MK}/subdir.mk

View File

@@ -23,6 +23,7 @@
#include <stdbool.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <unistd.h>
#include "helpers.h"
@@ -68,5 +69,7 @@ RC_DEPTREE *_rc_deptree_load (int, int *);
bool _rc_can_find_pids(void);
RC_SERVICE lookup_service_state(const char *service);
void from_time_t(char *time_string, time_t tv);
time_t to_time_t(char *timestring);
#endif

View File

@@ -19,6 +19,7 @@
#include "queue.h"
#include "librc.h"
#include "helpers.h"
bool
rc_yesno(const char *value)
@@ -118,7 +119,7 @@ rc_getline(char **line, size_t *len, FILE *fp)
librc_hidden_def(rc_getline)
char *
rc_proc_getent(const char *ent)
rc_proc_getent(const char *ent _unused)
{
#ifdef __linux__
FILE *fp;

View File

@@ -19,6 +19,7 @@ const char librc_copyright[] = "Copyright (c) 2007-2008 Roy Marples";
#include "queue.h"
#include "librc.h"
#include <helpers.h>
#ifdef __FreeBSD__
# include <sys/sysctl.h>
#endif
@@ -232,7 +233,7 @@ detect_prefix(const char *systype)
}
static const char *
detect_container(const char *systype)
detect_container(const char *systype _unused)
{
#ifdef __FreeBSD__
if (systype) {
@@ -296,7 +297,7 @@ detect_container(const char *systype)
}
static const char *
detect_vm(const char *systype)
detect_vm(const char *systype _unused)
{
#ifdef __NetBSD__
if (systype) {
@@ -367,11 +368,12 @@ rc_parse_service_state(RC_SERVICE state)
* specified runlevel in dependency order, including the
* specified runlevel. */
static void
get_runlevel_chain(const char *runlevel, RC_STRINGLIST *level_list)
get_runlevel_chain(const char *runlevel, RC_STRINGLIST *level_list, RC_STRINGLIST *ancestor_list)
{
char path[PATH_MAX];
RC_STRINGLIST *dirs;
RC_STRING *d, *dn;
RC_STRING *d, *parent;
const char *nextlevel;
/*
* If we haven't been passed a runlevel or a level list, or
@@ -395,8 +397,27 @@ get_runlevel_chain(const char *runlevel, RC_STRINGLIST *level_list)
*/
snprintf(path, sizeof(path), "%s/%s", RC_RUNLEVELDIR, runlevel);
dirs = ls_dir(path, LS_DIR);
TAILQ_FOREACH_SAFE(d, dirs, entries, dn)
get_runlevel_chain(d->value, level_list);
TAILQ_FOREACH(d, dirs, entries) {
nextlevel = d->value;
/* Check for loop */
if (rc_stringlist_find(ancestor_list, nextlevel)) {
fprintf(stderr, "Loop detected in stacked runlevels attempting to enter runlevel %s!\n",
nextlevel);
fprintf(stderr, "Ancestors:\n");
TAILQ_FOREACH(parent, ancestor_list, entries)
fprintf(stderr, "\t%s\n", parent->value);
exit(1);
}
/* Add new ancestor */
rc_stringlist_add(ancestor_list, nextlevel);
get_runlevel_chain(nextlevel, level_list, ancestor_list);
rc_stringlist_delete(ancestor_list, nextlevel);
}
rc_stringlist_free(dirs);
}
bool
@@ -500,9 +521,12 @@ librc_hidden_def(rc_runlevel_unstack)
RC_STRINGLIST *
rc_runlevel_stacks(const char *runlevel)
{
RC_STRINGLIST *stack;
RC_STRINGLIST *stack, *ancestor_list;
stack = rc_stringlist_new();
get_runlevel_chain(runlevel, stack);
ancestor_list = rc_stringlist_new();
rc_stringlist_add(ancestor_list, runlevel);
get_runlevel_chain(runlevel, stack, ancestor_list);
rc_stringlist_free(ancestor_list);
return stack;
}
librc_hidden_def(rc_runlevel_stacks)

View File

@@ -39,6 +39,7 @@ extern "C" {
#define RC_CONFDIR RC_SYSCONFDIR "/conf.d"
#define RC_PLUGINDIR RC_LIBDIR "/plugins"
#define RC_INIT_FIFO RC_SVCDIR"/init.ctl"
#define RC_PROFILE_ENV RC_SYSCONFDIR "/profile.env"
#define RC_SYS_WHITELIST RC_LIBEXECDIR "/conf.d/env_whitelist"
#define RC_USR_WHITELIST RC_SYSCONFDIR "/conf.d/env_whitelist"

2
src/rc/.gitignore vendored
View File

@@ -59,4 +59,6 @@ mark_service_failed
rc-abort
rc
openrc
openrc-init
openrc-run
openrc-shutdown

View File

@@ -1,3 +1,7 @@
include ../../Makefile.inc
MK= ../../mk
include ${MK}/os.mk
SRCS= checkpath.c do_e.c do_mark_service.c do_service.c \
do_value.c fstabinfo.c is_newer_than.c is_older_than.c \
mountinfo.c openrc-run.c rc-abort.c rc.c \
@@ -9,6 +13,10 @@ ifeq (${MKSELINUX},yes)
SRCS+= rc-selinux.c
endif
ifeq (${OS},Linux)
SRCS+= openrc-init.c openrc-shutdown.c
endif
CLEANFILES= version.h rc-selinux.o
BINDIR= ${PREFIX}/bin
@@ -34,6 +42,11 @@ RC_SBINPROGS= mark_service_starting mark_service_started \
mark_service_inactive mark_service_wasinactive \
mark_service_hotplugged mark_service_failed \
rc-abort swclock
ifeq (${OS},Linux)
SBINPROGS+= openrc-init openrc-shutdown
endif
ALL_PROGS= ${BINPROGS} ${SBINPROGS} ${RC_BINPROGS} ${RC_SBINPROGS}
CLEANFILES+= ${ALL_PROGS}
@@ -41,8 +54,6 @@ LOCAL_CPPFLAGS=-I../includes -I../librc -I../libeinfo
LOCAL_LDFLAGS=-L../librc -L../libeinfo
LDADD+= -lutil -lrc -leinfo
include ../../Makefile.inc
MK= ../../mk
include ${MK}/prog.mk
include ${MK}/gitver.mk
include ${MK}/cc.mk
@@ -96,6 +107,9 @@ veinfo vewarn vebegin veend vewend veindent veoutdent: do_e.o rc-misc.o
fstabinfo: fstabinfo.o _usage.o rc-misc.o
${CC} ${LOCAL_CFLAGS} ${LOCAL_LDFLAGS} ${CFLAGS} ${LDFLAGS} -o $@ $^ ${LDADD}
openrc-init: openrc-init.o
${CC} ${LOCAL_CFLAGS} ${LOCAL_LDFLAGS} ${CFLAGS} ${LDFLAGS} -o $@ $^ ${LDADD}
is_newer_than: is_newer_than.o rc-misc.o
${CC} ${LOCAL_CFLAGS} ${LOCAL_LDFLAGS} ${CFLAGS} ${LDFLAGS} -o $@ $^ ${LDADD}
@@ -114,6 +128,9 @@ mountinfo: mountinfo.o _usage.o rc-misc.o
openrc rc: rc.o rc-logger.o rc-misc.o rc-plugin.o _usage.o
${CC} ${LOCAL_CFLAGS} ${LOCAL_LDFLAGS} ${CFLAGS} ${LDFLAGS} -o $@ $^ ${LDADD}
openrc-shutdown: openrc-shutdown.o _usage.o
${CC} ${LOCAL_CFLAGS} ${LOCAL_LDFLAGS} ${CFLAGS} ${LDFLAGS} -o $@ $^ ${LDADD}
openrc-run runscript: openrc-run.o _usage.o rc-misc.o rc-plugin.o
ifeq (${MKSELINUX},yes)
openrc-run runscript: rc-selinux.o

View File

@@ -46,6 +46,7 @@
#include "_usage.h"
const char *applet = NULL;
const char *procmounts = "/proc/mounts";
const char *extraopts = "[mount1] [mount2] ...";
const char *getoptstring = "f:F:n:N:o:O:p:P:iste:E:" getoptstring_COMMON;
const struct option longopts[] = {
@@ -323,7 +324,7 @@ find_mounts(struct args *args)
int netdev;
RC_STRINGLIST *list;
if ((fp = fopen("/proc/self/mounts", "r")) == NULL)
if ((fp = fopen(procmounts, "r")) == NULL)
eerrorx("getmntinfo: %s", strerror(errno));
list = rc_stringlist_new();

206
src/rc/openrc-init.c Normal file
View File

@@ -0,0 +1,206 @@
/*
* openrc-init.c
* This is the init process (pid 1) for OpenRC.
*
* This is based on code written by James Hammons <jlhamm@acm.org>, so
* I would like to publically thank him for his work.
*/
/*
* Copyright (c) 2017 The OpenRC Authors.
* See the Authors file at the top-level directory of this distribution and
* https://github.com/OpenRC/openrc/blob/master/AUTHORS
*
* This file is part of OpenRC. It is subject to the license terms in
* the LICENSE file found in the top-level directory of this
* distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
* This file may not be copied, modified, propagated, or distributed
* except according to the terms contained in the LICENSE file.
*/
#include <errno.h>
#include <signal.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/reboot.h>
#include <sys/wait.h>
#include "helpers.h"
#include "rc.h"
#include "version.h"
static const char *rc_default_runlevel = "default";
static pid_t do_openrc(const char *runlevel)
{
pid_t pid;
sigset_t signals;
pid = fork();
switch(pid) {
case -1:
perror("fork");
break;
case 0:
setsid();
/* unblock all signals */
sigemptyset(&signals);
sigprocmask(SIG_SETMASK, &signals, NULL);
printf("Starting %s runlevel\n", runlevel);
execl("/sbin/openrc", "/sbin/openrc", runlevel, NULL);
perror("exec");
break;
default:
break;
}
return pid;
}
static void init(const char *default_runlevel)
{
const char *runlevel = NULL;
pid_t pid;
pid = do_openrc("sysinit");
waitpid(pid, NULL, 0);
pid = do_openrc("boot");
waitpid(pid, NULL, 0);
if (default_runlevel)
runlevel = default_runlevel;
else
runlevel = rc_conf_value("rc_default_runlevel");
if (!runlevel)
runlevel = rc_default_runlevel;
if (!rc_runlevel_exists(runlevel)) {
printf("%s is an invalid runlevel\n", runlevel);
runlevel = rc_default_runlevel;
}
pid = do_openrc(runlevel);
waitpid(pid, NULL, 0);
}
static void handle_reexec(char *my_name)
{
execl(my_name, my_name, "reexec", NULL);
return;
}
static void handle_shutdown(const char *runlevel, int cmd)
{
pid_t pid;
pid = do_openrc(runlevel);
while (waitpid(pid, NULL, 0) != pid);
printf("Sending the final term signal\n");
kill(-1, SIGTERM);
sleep(3);
printf("Sending the final kill signal\n");
kill(-1, SIGKILL);
sync();
reboot(cmd);
}
static void reap_zombies(void)
{
pid_t pid;
for (;;) {
pid = waitpid(-1, NULL, WNOHANG);
if (pid == 0)
break;
else if (pid == -1) {
if (errno == ECHILD)
break;
perror("waitpid");
continue;
}
}
}
static void signal_handler(int sig)
{
switch(sig) {
case SIGINT:
handle_shutdown("reboot", RB_AUTOBOOT);
break;
case SIGCHLD:
reap_zombies();
break;
default:
printf("Unknown signal received, %d\n", sig);
break;
}
}
int main(int argc, char **argv)
{
char *default_runlevel;
char buf[2048];
int count;
FILE *fifo;
bool reexec = false;
sigset_t signals;
struct sigaction sa;
if (getpid() != 1)
return 1;
printf("OpenRC init version %s starting\n", VERSION);
if (argc > 1)
default_runlevel = argv[1];
else
default_runlevel = NULL;
if (default_runlevel && strcmp(default_runlevel, "reexec") == 0)
reexec = true;
/* block all signals we do not handle */
sigfillset(&signals);
sigdelset(&signals, SIGCHLD);
sigdelset(&signals, SIGINT);
sigprocmask(SIG_SETMASK, &signals, NULL);
/* install signal handler */
memset(&sa, 0, sizeof(sa));
sa.sa_handler = signal_handler;
sigaction(SIGCHLD, &sa, NULL);
sigaction(SIGINT, &sa, NULL);
reboot(RB_DISABLE_CAD);
if (! reexec)
init(default_runlevel);
if (mkfifo(RC_INIT_FIFO, 0600) == -1 && errno != EEXIST)
perror("mkfifo");
for (;;) {
/* This will block until a command is sent down the pipe... */
fifo = fopen(RC_INIT_FIFO, "r");
if (!fifo) {
if (errno != EINTR)
perror("fopen");
continue;
}
count = fread(buf, 1, 2048, fifo);
buf[count] = 0;
fclose(fifo);
printf("PID1: Received \"%s\" from FIFO...\n", buf);
if (strcmp(buf, "halt") == 0)
handle_shutdown("shutdown", RB_HALT_SYSTEM);
else if (strcmp(buf, "kexec") == 0)
handle_shutdown("reboot", RB_KEXEC);
else if (strcmp(buf, "poweroff") == 0)
handle_shutdown("shutdown", RB_POWER_OFF);
else if (strcmp(buf, "reboot") == 0)
handle_shutdown("reboot", RB_AUTOBOOT);
else if (strcmp(buf, "reexec") == 0)
handle_reexec(argv[0]);
}
return 0;
}

132
src/rc/openrc-shutdown.c Normal file
View File

@@ -0,0 +1,132 @@
/*
* openrc-shutdown.c
* If you are using OpenRC's provided init, this will shut down or
* reboot your system.
*
* This is based on code written by James Hammons <jlhamm@acm.org>, so
* I would like to publically thank him for his work.
*/
/*
* Copyright 2017 The OpenRC Authors.
* See the Authors file at the top-level directory of this distribution and
* https://github.com/OpenRC/openrc/blob/master/AUTHORS
*
* This file is part of OpenRC. It is subject to the license terms in
* the LICENSE file found in the top-level directory of this
* distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
* This file may not be copied, modified, propagated, or distributed
* except according to the terms contained in the LICENSE file.
*/
#include <getopt.h>
#include <signal.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/types.h>
#include "einfo.h"
#include "rc.h"
#include "helpers.h"
#include "_usage.h"
const char *applet = NULL;
const char *extraopts = NULL;
const char *getoptstring = "HkpRr" getoptstring_COMMON;
const struct option longopts[] = {
{ "halt", no_argument, NULL, 'H'},
{ "kexec", no_argument, NULL, 'k'},
{ "poweroff", no_argument, NULL, 'p'},
{ "reexec", no_argument, NULL, 'R'},
{ "reboot", no_argument, NULL, 'r'},
longopts_COMMON
};
const char * const longopts_help[] = {
"halt the system",
"reboot the system using kexec",
"power off the system",
"re-execute init (use after upgrading)",
"reboot the system",
longopts_help_COMMON
};
const char *usagestring = NULL;
const char *exclusive = "Select one of "
"--halt, --kexec, --poweroff, --reexec or --reboot";
static void send_cmd(const char *cmd)
{
FILE *fifo;
size_t ignored;
fifo = fopen(RC_INIT_FIFO, "w");
if (!fifo) {
perror("fopen");
return;
}
ignored = fwrite(cmd, 1, strlen(cmd), fifo);
if (ignored != strlen(cmd))
printf("Error writing to init fifo\n");
fclose(fifo);
}
int main(int argc, char **argv)
{
int opt;
int cmd_count = 0;
bool do_halt = false;
bool do_kexec = false;
bool do_poweroff = false;
bool do_reboot = false;
bool do_reexec = false;
applet = basename_c(argv[0]);
if (geteuid() != 0)
eerrorx("%s: you must be root\n", applet);
while ((opt = getopt_long(argc, argv, getoptstring,
longopts, (int *) 0)) != -1)
{
switch (opt) {
case 'H':
do_halt = true;
cmd_count++;
break;
case 'k':
do_kexec = true;
cmd_count++;
break;
case 'p':
do_poweroff = true;
cmd_count++;
break;
case 'R':
do_reexec = true;
cmd_count++;
break;
case 'r':
do_reboot = true;
cmd_count++;
break;
case_RC_COMMON_GETOPT
}
}
if (cmd_count != 1) {
eerror("%s: %s\n", applet, exclusive);
usage(EXIT_FAILURE);
}
if (do_halt)
send_cmd("halt");
else if (do_kexec)
send_cmd("kexec");
else if (do_poweroff)
send_cmd("poweroff");
else if (do_reboot)
send_cmd("reboot");
else if (do_reexec)
send_cmd("reexec");
return 0;
}

View File

@@ -442,3 +442,35 @@ RC_SERVICE lookup_service_state(const char *service)
return service_bits[i].bit;
return 0;
}
void from_time_t(char *time_string, time_t tv)
{
strftime(time_string, 20, "%Y-%m-%d %H:%M:%S", localtime(&tv));
}
time_t to_time_t(char *timestring)
{
int check = 0;
int year = 0;
int month = 0;
int day = 0;
int hour = 0;
int min = 0;
int sec = 0;
struct tm breakdown = {0};
time_t result = -1;
check = sscanf(timestring, "%4d-%2d-%2d %2d:%2d:%2d",
&year, &month, &day, &hour, &min, &sec);
if (check == 6) {
breakdown.tm_year = year - 1900; /* years since 1900 */
breakdown.tm_mon = month - 1;
breakdown.tm_mday = day;
breakdown.tm_hour = hour;
breakdown.tm_min = min;
breakdown.tm_sec = sec;
breakdown.tm_isdst = -1;
result = mktime(&breakdown);
}
return result;
}

View File

@@ -334,7 +334,19 @@ void selinux_setup(char **argv)
/* extract the type from the context */
curr_con = context_new(curr_context);
curr_t = xstrdup(context_type_get(curr_con));
if (!curr_con) {
free(curr_context);
goto out;
}
curr_t = context_type_get(curr_con);
if (!curr_t) {
context_free(curr_con);
free(curr_context);
goto out;
}
curr_t = xstrdup(curr_t);
/* dont need them anymore so free() now */
context_free(curr_con);
free(curr_context);

View File

@@ -76,10 +76,55 @@ print_level(const char *prefix, const char *level)
printf("%s\n", level);
}
static void get_uptime(const char *service, char *uptime, int uptime_size)
{
RC_SERVICE state = rc_service_state(service);
char *start_count;
time_t now;
char *start_time_string;
time_t start_time;
double time_diff;
double diff_tmp;
double diff_days;
double diff_hours;
double diff_mins;
uptime[0] = '\0';
if (state & RC_SERVICE_STARTED) {
start_count = rc_service_value_get(service, "start_count");
start_time_string = rc_service_value_get(service, "start_time");
if (start_count && start_time_string) {
start_time = to_time_t(start_time_string);
now = time(NULL);
time_diff = difftime(now, start_time);
diff_tmp = time_diff;
if (diff_tmp > 86400.0) {
diff_days = diff_tmp / 86400.0;
diff_tmp -= diff_days * 86400.0;
}
if (diff_tmp > 3600.0) {
diff_hours = diff_tmp / 3600.0;
diff_tmp -= diff_hours * 3600.0;
}
if (diff_tmp > 60.0) {
diff_mins = diff_tmp / 60.0;
diff_tmp -= diff_mins * 60.0;
}
if ((int) diff_days > 0)
snprintf(uptime, uptime_size, "%.0f days %02.0f:%02.0f (%s)",
diff_days, diff_hours, diff_mins, start_count);
else
snprintf(uptime, uptime_size, "%02.0f:%02.0f (%s)",
diff_hours, diff_mins, start_count);
}
}
}
static void
print_service(const char *service)
{
char status[10];
char status[60];
char uptime [40];
int cols = printf(" %s", service);
const char *c = ecolor(ECOLOR_GOOD);
RC_SERVICE state = rc_service_state(service);
@@ -101,7 +146,8 @@ print_service(const char *service)
{
snprintf(status, sizeof(status), " crashed ");
} else {
snprintf(status, sizeof(status), " started ");
get_uptime(service, uptime, 40);
snprintf(status, sizeof(status), " started %s", uptime);
color = ECOLOR_GOOD;
}
} else if (state & RC_SERVICE_SCHEDULED) {

View File

@@ -64,6 +64,7 @@ static struct pam_conv conv = { NULL, NULL};
#include "rc.h"
#include "rc-misc.h"
#include "_usage.h"
#include "helpers.h"
const char *applet = NULL;
const char *extraopts = NULL;
@@ -153,7 +154,9 @@ extern char **environ;
# define SYS_ioprio_set __NR_ioprio_set
#endif
#if !defined(__DragonFly__)
static inline int ioprio_set(int which, int who, int ioprio)
static inline int ioprio_set(int which _unused,
int who _unused,
int ioprio _unused)
{
#ifdef SYS_ioprio_set
return syscall(SYS_ioprio_set, which, who, ioprio);
@@ -194,26 +197,45 @@ parse_signal(const char *sig)
int signal;
} SIGNALPAIR;
#define signalpair_item(name) { #name, SIG##name },
static const SIGNALPAIR signallist[] = {
{ "ABRT", SIGABRT },
{ "ALRM", SIGALRM },
{ "FPE", SIGFPE },
{ "HUP", SIGHUP },
{ "ILL", SIGILL },
{ "INT", SIGINT },
{ "KILL", SIGKILL },
{ "PIPE", SIGPIPE },
{ "QUIT", SIGQUIT },
{ "SEGV", SIGSEGV },
{ "TERM", SIGTERM },
{ "USR1", SIGUSR1 },
{ "USR2", SIGUSR2 },
{ "CHLD", SIGCHLD },
{ "CONT", SIGCONT },
{ "STOP", SIGSTOP },
{ "TSTP", SIGTSTP },
{ "TTIN", SIGTTIN },
{ "TTOU", SIGTTOU },
signalpair_item(HUP)
signalpair_item(INT)
signalpair_item(QUIT)
signalpair_item(ILL)
signalpair_item(TRAP)
signalpair_item(ABRT)
signalpair_item(BUS)
signalpair_item(FPE)
signalpair_item(KILL)
signalpair_item(USR1)
signalpair_item(SEGV)
signalpair_item(USR2)
signalpair_item(PIPE)
signalpair_item(ALRM)
signalpair_item(TERM)
signalpair_item(CHLD)
signalpair_item(CONT)
signalpair_item(STOP)
signalpair_item(TSTP)
signalpair_item(TTIN)
signalpair_item(TTOU)
signalpair_item(URG)
signalpair_item(XCPU)
signalpair_item(XFSZ)
signalpair_item(VTALRM)
signalpair_item(PROF)
#ifdef SIGWINCH
signalpair_item(WINCH)
#endif
#ifdef SIGIO
signalpair_item(IO)
#endif
#ifdef SIGPWR
signalpair_item(PWR)
#endif
signalpair_item(SYS)
{ "NULL", 0 },
};
@@ -468,7 +490,7 @@ run_stop_schedule(const char *exec, const char *const *argv,
if (tkilled == 0) {
if (progressed)
printf("\n");
eerror("%s: no matching processes found", applet);
eerror("%s: no matching processes found", applet);
}
return tkilled;
}
@@ -696,17 +718,17 @@ int main(int argc, char **argv)
if (sscanf(tmp, "%d", &nicelevel) != 1)
eerror("%s: invalid nice level `%s' (SSD_NICELEVEL)",
applet, tmp);
if ((tmp = getenv("SSD_IONICELEVEL"))) {
int n = sscanf(tmp, "%d:%d", &ionicec, &ioniced);
if (n != 1 && n != 2)
eerror("%s: invalid ionice level `%s' (SSD_IONICELEVEL)",
applet, tmp);
if (ionicec == 0)
ioniced = 0;
else if (ionicec == 3)
ioniced = 7;
ionicec <<= 13; /* class shift */
}
if ((tmp = getenv("SSD_IONICELEVEL"))) {
int n = sscanf(tmp, "%d:%d", &ionicec, &ioniced);
if (n != 1 && n != 2)
eerror("%s: invalid ionice level `%s' (SSD_IONICELEVEL)",
applet, tmp);
if (ionicec == 0)
ioniced = 0;
else if (ionicec == 3)
ioniced = 7;
ionicec <<= 13; /* class shift */
}
/* Get our user name and initial dir */
p = getenv("USER");
@@ -938,6 +960,9 @@ int main(int argc, char **argv)
if (redirect_stdout || redirect_stderr)
eerrorx("%s: --stdout and --stderr are only relevant"
" with --start", applet);
if (start_wait)
ewarn("using --wait with --stop has no effect,"
" use --retry instead");
} else {
if (!exec)
eerrorx("%s: nothing to start", applet);
@@ -990,7 +1015,11 @@ int main(int argc, char **argv)
eerror("%s: %s does not exist", applet,
*exec_file ? exec_file : exec);
exit(EXIT_FAILURE);
}
if (start && retry)
ewarn("using --retry with --start has no effect,"
" use --wait instead");
/* If we don't have a pidfile we should check if it's interpreted
* or not. If it we, we need to pass the interpreter through

View File

@@ -62,39 +62,46 @@ static struct pam_conv conv = { NULL, NULL};
#include "rc.h"
#include "rc-misc.h"
#include "_usage.h"
#include "helpers.h"
const char *applet = NULL;
const char *extraopts = NULL;
const char *getoptstring = "d:e:g:I:Kk:N:p:r:Su:1:2:" \
const char *getoptstring = "D:d:e:g:I:Kk:m:N:p:r:Su:1:2:" \
getoptstring_COMMON;
const struct option longopts[] = {
{ "respawn-delay", 1, NULL, 'D'},
{ "chdir", 1, NULL, 'd'},
{ "env", 1, NULL, 'e'},
{ "group", 1, NULL, 'g'},
{ "ionice", 1, NULL, 'I'},
{ "stop", 0, NULL, 'K'},
{ "umask", 1, NULL, 'k'},
{ "respawn-max", 1, NULL, 'm'},
{ "nicelevel", 1, NULL, 'N'},
{ "pidfile", 1, NULL, 'p'},
{ "user", 1, NULL, 'u'},
{ "respawn-period", 1, NULL, 'P'},
{ "chroot", 1, NULL, 'r'},
{ "start", 0, NULL, 'S'},
{ "user", 1, NULL, 'u'},
{ "stdout", 1, NULL, '1'},
{ "stderr", 1, NULL, '2'},
longopts_COMMON
};
const char * const longopts_help[] = {
"Set a respawn delay",
"Change the PWD",
"Set an environment string",
"Change the process group",
"Set an ionice class:data when starting",
"Stop daemon",
"Set the umask for the daemon",
"set maximum number of respawn attempts",
"Set a nicelevel when starting",
"Match pid found in this file",
"Change the process user",
"Set respawn time period",
"Chroot to this directory",
"Start daemon",
"Change the process user",
"Redirect stdout to file",
"Redirect stderr to file",
longopts_help_COMMON
@@ -124,7 +131,8 @@ extern char **environ;
# define SYS_ioprio_set __NR_ioprio_set
#endif
#if !defined(__DragonFly__)
static inline int ioprio_set(int which, int who, int ioprio)
static inline int ioprio_set(int which _unused, int who _unused,
int ioprio _unused)
{
#ifdef SYS_ioprio_set
return syscall(SYS_ioprio_set, which, who, ioprio);
@@ -163,7 +171,8 @@ static pid_t get_pid(const char *pidfile)
return pid;
}
static void child_process(char *exec, char **argv)
static void child_process(char *exec, char **argv, char *svcname,
int start_count)
{
RC_STRINGLIST *env_list;
RC_STRING *env;
@@ -175,6 +184,9 @@ static void child_process(char *exec, char **argv)
char *np;
char **c;
char cmdline[PATH_MAX];
time_t start_time;
char start_count_string[20];
char start_time_string[20];
#ifdef HAVE_PAM
pam_handle_t *pamh = NULL;
@@ -184,6 +196,14 @@ static void child_process(char *exec, char **argv)
setsid();
if (svcname) {
start_time = time(NULL);
from_time_t(start_time_string, start_time);
rc_service_value_set(svcname, "start_time", start_time_string);
sprintf(start_count_string, "%i", start_count);
rc_service_value_set(svcname, "start_count", start_count_string);
}
if (nicelevel) {
if (setpriority(PRIO_PROCESS, getpid(), nicelevel) == -1)
eerrorx("%s: setpriority %d: %s", applet, nicelevel,
@@ -224,6 +244,7 @@ static void child_process(char *exec, char **argv)
/* Close any fd's to the passwd database */
endpwent();
/* remove the controlling tty */
#ifdef TIOCNOTTY
ioctl(tty_fd, TIOCNOTTY, 0);
close(tty_fd);
@@ -319,7 +340,7 @@ static void child_process(char *exec, char **argv)
dup2(stderr_fd, STDERR_FILENO);
for (i = getdtablesize() - 1; i >= 3; --i)
close(i);
fcntl(i, F_SETFD, FD_CLOEXEC);
*cmdline = '\0';
c = argv;
@@ -421,7 +442,14 @@ int main(int argc, char **argv)
char *p;
char *token;
int i;
int n;
char exec_file[PATH_MAX];
int respawn_count = 0;
int respawn_delay = 0;
int respawn_max = 10;
int respawn_period = 5;
time_t respawn_now= 0;
time_t first_spawn= 0;
struct passwd *pw;
struct group *gr;
FILE *fp;
@@ -458,6 +486,12 @@ int main(int argc, char **argv)
while ((opt = getopt_long(argc, argv, getoptstring, longopts,
(int *) 0)) != -1)
switch (opt) {
case 'D': /* --respawn-delay time */
n = sscanf(optarg, "%d", &respawn_delay);
if (n != 1 || respawn_delay < 1)
eerrorx("Invalid respawn-delay value '%s'", optarg);
break;
case 'I': /* --ionice */
if (sscanf(optarg, "%d:%d", &ionicec, &ioniced) == 0)
eerrorx("%s: invalid ionice `%s'",
@@ -479,6 +513,12 @@ int main(int argc, char **argv)
applet, optarg);
break;
case 'P': /* --respawn-period time */
n = sscanf(optarg, "%d", &respawn_period);
if (n != 1 || respawn_delay < 1)
eerrorx("Invalid respawn-delay value '%s'", optarg);
break;
case 'S': /* --start */
start = true;
break;
@@ -508,6 +548,12 @@ int main(int argc, char **argv)
applet, optarg);
break;
case 'm': /* --respawn-max count */
n = sscanf(optarg, "%d", &respawn_max);
if (n != 1 || respawn_max < 1)
eerrorx("Invalid respawn-max value '%s'", optarg);
break;
case 'p': /* --pidfile <pid-file> */
pidfile = optarg;
break;
@@ -578,6 +624,11 @@ int main(int argc, char **argv)
if (start) {
if (!exec)
eerrorx("%s: nothing to start", applet);
if (respawn_delay * respawn_max > respawn_period) {
ewarn("%s: Please increase the value of --respawn-period to more "
"than %d to avoid infinite respawning", applet,
respawn_delay * respawn_max);
}
}
/* Expand ~ */
@@ -637,10 +688,12 @@ int main(int argc, char **argv)
* result would be the same. */
if (pidfile && exists(pidfile))
unlink(pidfile);
if (svcname)
if (svcname) {
rc_service_daemon_set(svcname, exec,
(const char *const *)argv,
pidfile, false);
rc_service_mark(svcname, RC_SERVICE_STOPPED);
}
exit(EXIT_SUCCESS);
}
@@ -662,7 +715,7 @@ int main(int argc, char **argv)
fp = fopen(pidfile, "w");
if (! fp)
eerrorx("%s: fopen `%s': %s", applet, pidfile, strerror(errno));
fclose(fp);
fclose(fp);
child_pid = fork();
if (child_pid == -1)
@@ -672,6 +725,10 @@ int main(int argc, char **argv)
if (child_pid != 0)
exit(EXIT_SUCCESS);
#ifdef TIOCNOTTY
tty_fd = open("/dev/tty", O_RDWR);
#endif
devnull_fd = open("/dev/null", O_RDWR);
child_pid = fork();
if (child_pid == -1)
eerrorx("%s: fork: %s", applet, strerror(errno));
@@ -680,18 +737,22 @@ int main(int argc, char **argv)
/* this is the supervisor */
umask(numask);
#ifdef TIOCNOTTY
tty_fd = open("/dev/tty", O_RDWR);
#endif
devnull_fd = open("/dev/null", O_RDWR);
fp = fopen(pidfile, "w");
if (! fp)
eerrorx("%s: fopen `%s': %s", applet, pidfile, strerror(errno));
fprintf(fp, "%d\n", getpid());
fclose(fp);
if (svcname)
rc_service_daemon_set(svcname, exec,
(const char * const *) argv, pidfile, true);
/* remove the controlling tty */
#ifdef TIOCNOTTY
ioctl(tty_fd, TIOCNOTTY, 0);
close(tty_fd);
#endif
/*
* Supervisor main loop
*/
@@ -702,6 +763,23 @@ int main(int argc, char **argv)
syslog(LOG_INFO, "stopping %s, pid %d", exec, child_pid);
kill(child_pid, SIGTERM);
} else {
sleep(respawn_delay);
if (respawn_max > 0 && respawn_period > 0) {
respawn_now = time(NULL);
if (first_spawn == 0)
first_spawn = respawn_now;
if (respawn_now - first_spawn > respawn_period) {
respawn_count = 0;
first_spawn = 0;
} else
respawn_count++;
if (respawn_count >= respawn_max) {
syslog(LOG_INFO, "respawned \"%s\" too many times, "
"exiting", exec);
exiting = true;
continue;
}
}
if (WIFEXITED(i))
syslog(LOG_INFO, "%s, pid %d, exited with return code %d",
exec, child_pid, WEXITSTATUS(i));
@@ -712,15 +790,19 @@ int main(int argc, char **argv)
if (child_pid == -1)
eerrorx("%s: fork: %s", applet, strerror(errno));
if (child_pid == 0)
child_process(exec, argv);
child_process(exec, argv, svcname, respawn_count);
}
}
if (svcname)
if (pidfile && exists(pidfile))
unlink(pidfile);
if (svcname) {
rc_service_daemon_set(svcname, exec,
(const char * const *) argv, pidfile, true);
(const char *const *)argv,
pidfile, false);
rc_service_mark(svcname, RC_SERVICE_STOPPED);
}
exit(EXIT_SUCCESS);
} else if (child_pid == 0)
child_process(exec, argv);
child_process(exec, argv, svcname, respawn_count);
}

View File

@@ -1,5 +0,0 @@
DIR= ${UPREFIX}/bin
BIN= deptree2dot
MK= ../../mk
include ${MK}/scripts.mk

20
support/Makefile Normal file
View File

@@ -0,0 +1,20 @@
# Copyright (c) 2017 the OpenRC Authors.
# See the Authors file at the top-level directory of this distribution and
# https://github.com/OpenRC/openrc/blob/master/AUTHORS
#
# This file is part of OpenRC. It is subject to the license terms in
# the LICENSE file found in the top-level directory of this
# distribution and at https://github.com/OpenRC/openrc/blob/master/LICENSE
# This file may not be copied, modified, propagated, or distributed
# except according to the terms contained in the LICENSE file.
MK= ../mk
include ${MK}/os.mk
SUBDIR= deptree2dot init.d.examples openvpn
ifeq (${OS},Linux)
SUBDIR+= sysvinit
endif
include ${MK}/subdir.mk

View File

@@ -0,0 +1,9 @@
MK= ../../mk
include ${MK}/os.mk
DIR= ${DATADIR}/support/deptree2dot
BIN= deptree2dot
INC= README.md
include ${MK}/scripts.mk

View File

@@ -0,0 +1,11 @@
# deptree2dot - Graph the OpenRC Dependency Tree
This utility can be used to graph the OpenRC dependency tree. It
requires perl5.x and converts the tree to a .dot file which can be
processed by graphviz.
Example usage:
$ chmod +x deptree2dot
$deptree2dot > deptree.dot
$deptree2dot | dot -Tpng -o deptree.png

View File

@@ -1,9 +1,11 @@
DIR= ${INITDIR}
DIR= ${DATADIR}/support/init.d.examples
INC= README.md
SRCS= avahi-dnsconfd.in avahid.in dhcpcd.in dbus.in \
hald.in named.in ntpd.in \
openvpn.in polkitd.in sshd.in wpa_supplicant.in
BIN= ${OBJS}
MK= ../mk
MK= ../../mk
SED_EXTRA+= -e 's:@VARBASE@:/var:g'

View File

@@ -0,0 +1,3 @@
The service scripts in this directory are meant as examples only.
They are not installed by default as the scripts will need tweaking on a
per distro basis. They are also non essential to the operation of the system.

Some files were not shown because too many files have changed in this diff Show More