56

With init scripts (or with openrc) I alway could run services from a different installation root.
but when I run chroot /somepath/to_root /usr/bin/systemctl start someservice I got:

Running in chroot, ignoring request.

Is there a way to force systemd run the service?

Update:
I forgot to say my host system run init scripts or openrc, but never systemd, and that I use chroot to troubleshot Unix systems which can't even launch a minimal shell.

4
  • 2
    I also need to run services into a chroot, it always worked before openrc2, seems impossible now ;(
    – neofutur
    Aug 3, 2014 at 1:05
  • You’re trying to solve the wrong problem. If you have OpenRC, you need to convert the systemd service into an OpenRC service. There’s really no way around that.
    – Daniel B
    Mar 10, 2015 at 21:22
  • @DanielB : NO! Did you ever heard of systemrescuecd? Mar 11, 2015 at 0:19
  • No. I also don't see how it relates to your question.
    – Daniel B
    Mar 11, 2015 at 6:34

9 Answers 9

41

A well-known problem in systemd distros (Arch Linux, OpenSUSE, Fedora).

Systemd replaces sysvinit, and provides one great advantage over this. In sysvinit, when you ask a service to start, it inherits the execution context of the person invoking the script, which includes environment variables, ulimits, and so on. Systemd improves on this at the contrary by notifying a daemon, which will start the service in a well-defined, healthy, constant environment, where of course the performances of the services are much easier to predict, since the environment is always the same.

This implies that, when I call systemctl from within the chroot, it is irrelevant that I am inside chroot, the environment that will be inherited is still that of PID 1, not my current one. But it gets worse than this: since communication sockets are placed inside /run/systemd, a process in a chroot will not even be able to talk to the init system!

So how do you go about chroot'ing in systemd distros?

  1. If all you want to do is have a Linux container, this Arch Wiki page will tell you how to set up a Linux container in less than 30 seconds, thanks to systemd-nspawn.

  2. If instead you really want a chroot environment, this beautiful and crystal clear Web page will provide you with two working solutions (the second one is a modified version of the one offered at point #1).

13
  • 3
    That I never use systemd in my host system root. In my case I can't mix systemd with openrc. Dec 16, 2013 at 18:05
  • 3
    @TwoD That won't work. Running systemd-nspawn fails with "Not running on a systemd system." unless the host is using systemd as well.
    – hvd
    Jul 15, 2015 at 11:59
  • 1
    @TwoD And I responded because it doesn't sound like that at all to me. :) "I can't run it" is an odd thing to say if you're having trouble finding the executable, which is why I suspect that the problem is what I put in my comment: running it gives that error message and doesn't do anything useful. But even if it turns out the problem really was where to find systemd-nspawn, then pointing into the new root won't help. Either the host already has it (because it's running systemd), in which case the host version can be used, or the host doesn't have it, but the new root's version won't work.
    – hvd
    Jul 15, 2015 at 12:45
  • 1
    systemd will refuse to be run in chroot Mar 11, 2017 at 14:30
  • 1
    @CraigHicks Except since you set up a jail, you can’t do things like connecting wayland apps to the host’s compositing. Plain chroot isn’t a jail, but a way to change access search paths for the binaires. Aug 8, 2020 at 10:02
13

Several years later I must admit there is only one solution to most Systemd practical problems. Because the error is Systemd itself

I am really fed up with Systemd as I had problems that I never faced with things like Upstart or Openrc :

  • The enforcing of a kernel requiring cgroups support (instead of being made optional but enabled by default inside a config file) even for embedded systems with only 24Mb of ram and no writable storage.
    While proponents argue that not being able to use it in such case is the wanted behavior since it wasn’t designed for such case, the reality is the other init systems also don’t care while in systemd such feature isn’t a separate project which highlights once again the consequences of not following kiss.
  • Despite the claim of being modular, at runtime the dependency hell makes it a strong god object : want to boot over a single reiser4 rootfs ? It’s not possible because many programs requires systemd-udevd which requires systemd-init which requires the systemd-boot package which can’t be installed at the same time than grub2 nor can read kernel images from a reiser4 partition.
  • Want to connect to the internet through Bluetooth dialup ? If it doesn’t work with your Samsung java me phone, then you aren’t able to run the scripts and command line software that previously worked manually because of networkd.
  • Though I recognize the biggest problem is if you are building and maintaining your own Linux distribution : the systemd init module itself has so many dependencies that you can’t propose to choose another init system through different install packages.
  • The default use of Google dns for systemd if no resolver is defined in terms of privacy and censorship through the example to prevent Tornado Cash domains to resolve.
  • The inability to launch a background non service process and log out as there are no simple ways to do it in a new systemd scope.
  • Good luck for viewing logs if you can’t chroot in your system or if you upgraded from libdb4.8 (whereas at least, in worst case Microsoft has it’s log files in xml format).

The only solution :

Systemd is unnecessary complex for solving problems : like alsa instead of ossv4. So if you have something that uses systemd just wipe all the data :

dd if=/dev/urandom of=/dev/dm−0 bs=1M count=1

and install something that doesn’t use it at all while solving problems of SysV Init like Gentoo with Openrc.
Concerning my question systemd makes things like the Windows® registry : if a part of it gets screwed up, then it’s over.

16
  • 12
    Please recognize that the design of something can really prevent from getting an answer so that the answer is to switch to something which works. And that this is a real answer. Nov 18, 2018 at 21:47
  • 3
    I had the same opinion, now I am on a little bit more balanced view. Systemd has the super-big advantage that it can really kill what should be killed. It is because it tracks all the forked sub-processes with the kernel cgroup feature. None of the older tools can do that. Furthermore, do you remember the crap of the scripts in /etc/init/*.sh?I too, but it is only a bad memory to me today. The systemd service files are clear and around 10 lines long configs. Not 200 line long scripts. These huge advantages has the systemd, I agree that its all other features are disadvantage.
    – peterh
    Mar 25, 2019 at 12:53
  • 1
    @peterh : unfortunately not everyone share it I mean to the point of deleting post. This is not about SysV init against Systemd but more against things like Openrc or even Upstart (which allows for short startup scripts as well as parallel service start). At least I learned one thing : Darwin is mostly the ᴏꜱ of Apple™ Windows is the ᴏꜱ of Microsoft and Linux design is mostly run by red hat. Though SysV init while being slower doesn’t restrict you at what you can do at runtime. Mar 26, 2019 at 13:08
  • 1
    After many years and at least in Debian I've found the easiest solution is to simply, in the chroot, apt purge systemd and then apt install sysvinit-core. Since in a chroot systemd is not really "running" even if it's started, uninstalling it won't cripple the chroot, and then you can operate with sysv just as you do in the outside machine. (Unfortunately, in Debian I've found no way to debootstrap chroots with sysvinit preinstalled) Apr 28, 2020 at 20:05
  • 1
    @LuisMachuca which is the problem of this question (but apt-get can work without Systemd). How do you manage to not have pid 1 based on a systemd binary because of packages dependencies? This is for that impossibility that devuan was started. Are you still running Jessie or older? Apr 28, 2020 at 22:12
11

systemd only ignores "services", so I just run the daemon commands manually.

So instead of

service sshd start

I use

/usr/sbin/sshd -D &
3
  • 2
    This doesn’t work for all services. Some require to be started as part of the system service starter like Xorg. Dec 6, 2015 at 11:15
  • startx will work for Xorg. Mar 11, 2017 at 14:26
  • 1
    @ErkinAlpGüney : not in chroot… Because of Dbus. Apr 20, 2018 at 19:02
3

No. Services are executed by systemd (pid 1), not by systemctl directly (which only sends a start request), and since systemd runs outside the chroot, so will the service.

Although technically it could be possible to implement this (by making systemctl somehow pass its root to systemd), it is somewhat unlikely to happen since there already is a tool for creating full containers (systemd-nspawn /somepath/to_root). You could always contact the mailing list though.

4
  • 1
    Nice, But I need to use systemctl since My host system use oepnrc. I want full independent solution Dec 15, 2013 at 17:55
  • 3
    I'll muddy the waters yet further by saying: Psst! Mention RootDirectory= as well since you are so dangerously short of upvotes. (-:
    – JdeBP
    Dec 16, 2013 at 19:56
  • @JdeBP : What is the difference (in term of results) beetween the variable RootDirectoryand the chrootcommand? Dec 17, 2013 at 21:35
  • @grawity : So What append if the pid 1 is init? Dec 21, 2013 at 9:41
2

Faced this problem once tried to bring up network in rescue mode using network configuration from chroot. Finally this works for me:

service --skip-redirect <service> restart

or:

SYSTEMCTL_SKIP_REDIRECT=_ /etc/init.d/<service> restart
1
  • Nice. But it works only with legacy Init compatible services (won’t work for networking in Fedora rawhide). As I said in my answer, the real solution is to screw up anything that use systemd. Dec 12, 2017 at 14:59
1

Define a service file outside chroot that execute the service inside the chroot with the options RootDirectory=/path/to/chroot in conjunction with MountAPIVFS=on, the link above contains the magic.

Run systemd script in chroot from outside the chroot

2
  • It will then be run with isolation preventing it from interacting with things like udev on the host. Sep 8, 2020 at 7:38
  • its almost a nice solution, but sadly too much of a hack to succesfully solve many problems with it. May 26, 2022 at 23:27
0

Systemd will simply not run unless it has access to cgroups, udev and a bunch of others. It will not run in a chroot or in a docker container (unless the container is give unlimited privileges).

It will run in podman, which is not a surprise seeing as the same company stands behind that and systemd. The fact systemd tries to do everything is also concerning to linux altogether. It is an init system, but wait, it also uses journald and is now a logging system. And that listens on /dev/log, so you cannot use rsyslog with local sockets. Oh, and now it's a timesyncd daemon as well, and so forth.

So anyways, I am also fed up with docker saying "that is not the docker way, one container, one service, one entrypoint". But hold on, with chroot environments, and then with LXC containers, we were able to run an init system and use containers like mini-servers if we wished so, since forever. Systemd simply doesn't let you, unless you give it a lot of permissions on docker or use podman. And docker is adamant you should not be running a multi-service init system inside containers, even though they are full linux containers.

So, anyways, this is not just a rant. I have a solution - I did a thing!

https://github.com/rglonek/docker-systemd/blob/main/QUICKSTART.md

It's a golang-written application, which allows you to put in a single binary in your docker container and run it. It loads itself and acts as systemd/journald and provides systemctl/journalctl commands. Essentially I have rewritten the important parts of systemd/journald in go :D Yes, this is a beta, yes the code is a proof-of-concept. And yes, I've been using it since I built it and it works, at least for me, without issues.

It supports most standard systemctl commands (start/stop/restart/status/etc) though output looks more basic, most standard journalctl parameters and handles the loading of services at system startup (looks up the multi-user.target). It understands and speaks systemd system files, so you can install say apache2, and do systemctl start apache2; journalctl -u apache2 -f and systemctl enable apache2 to make it start at system boot.

I needed it cause some stuff I am installing is badly packaged and tries to run systemctl commands on install (and fails) in docker. And I like running say a process and it's little other process-helper thing in the same container. It's linux, I should be allowed to if I choose so.

1
  • Question is about sharing resources with the host rootfs in order to salvage the damaged rootfs. Not performing security. Jan 13 at 20:29
-2

If you are launching an inetd-style service with socket activation, consider launching stunnel instead with a configuration file that specifies both a chroot and your binary as an inetd-style launch target.

Note that you may have SELINUX issues. On an Oracle Linux 7.1 system, I had to "chcon -v --type=stunnel_etc_t" on all files that stunnel needed to read.

You will need to use TLS encryption on the client side of the socket (i.e., another stunnel with "client=yes" in the config). Let me know if you want more details on this.

1
  • no it's about things like d-bus. I do it in order to diagnose problems on the target chroot. Sep 14, 2015 at 17:15
-3

You can use nohup command to start services in chroot. To start httpdservice for example, I do it like this.

nohup httpd /dev/null &

to stop it pkill httpd

5
  • What about services like Dbus that can only be started by the installed binary systemd script ? Apr 11, 2016 at 10:01
  • You can start such services from its directory with start command.
    – ellooku
    Apr 21, 2016 at 18:18
  • Which is a symlink against systemctl. So it doesn’t work. Apr 21, 2016 at 18:25
  • I do this all the time on Fedora running on my Android. May be I don't know what your problem is.
    – ellooku
    Apr 21, 2016 at 18:32
  • 1
    The consequence is this message :Running in chroot, ignoring request.. I don’t think you do it all the time though chroot. Indeed, the startup script requires systemd. Apr 21, 2016 at 18:35

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .