Difference between revisions of "Change root"

From ArchWiki
Jump to: navigation, search
(Undo revision 512665 by PXf (talk) - systemd-nspawn is already in the "Related articles" box)
(103 intermediate revisions by 28 users not shown)
Line 1: Line 1:
 
[[Category:System recovery]]
 
[[Category:System recovery]]
[[es:Change Root]]
+
[[es:Change root]]
 
[[fa:تغییر ریشه]]
 
[[fa:تغییر ریشه]]
 
[[fr:Chroot]]
 
[[fr:Chroot]]
 
[[ja:Change Root]]
 
[[ja:Change Root]]
 +
[[pt:Change root]]
 
[[ro:Chroot]]
 
[[ro:Chroot]]
[[zh-CN:Change Root]]
+
[[ru:Change root]]
[[ru:Change Root]]
+
[[zh-hans:Change root]]
[[Wikipedia:Chroot|Chroot]] is the process of changing of the apparent disk root directory (and the current running process and its children) to another root directory. When you change root to another directory you cannot access files and commands outside that directory. This directory is called a ''chroot jail''. Changing root is commonly done for system maintenance, such as reinstalling the bootloader or resetting a forgotten password.
+
{{Related articles start}}
 +
{{Related|PRoot}}
 +
{{Related|Linux Containers}}
 +
{{Related|systemd-nspawn}}
 +
{{Related articles end}}
 +
[[Wikipedia:Chroot|Chroot]] is an operation that changes the apparent root directory for the current running process and their children. A program that is run in such a modified environment cannot access files and commands outside that environmental directory tree. This modified environment is called a ''chroot jail''.
  
== Requirements ==
+
== Reasoning ==
  
* You'll need to boot from another working Linux environment (e.g. from a LiveCD or USB flash media, or from another installed Linux distribution).
+
Changing root is commonly done for performing system maintenance on systems where booting and/or logging in is no longer possible. Common examples are:
  
* Root privileges are required in order to chroot.
+
* Reinstalling the [[bootloader]].
 +
* Rebuilding the [[mkinitcpio|initramfs image]].
 +
* Upgrading or [[downgrading packages]].
 +
* Resetting a [[Password recovery|forgotten password]].
 +
* Building packages in a clean chroot, see [[DeveloperWiki:Building in a Clean Chroot]].
  
* Be sure that the architecture of the Linux environment you have booted into matches the architecture of the root directory you wish to enter (i.e. i686, x86_64). You can find the architecture of your current environment with:
+
See also [[Wikipedia:Chroot#Limitations]].
  
: {{bc|# uname -m}}
+
== Requirements ==
  
* If you need any kernel modules loaded in the chroot environment, load them before chrooting. It may also be useful to initialize your swap ({{ic|swapon /dev/sdxY}}) and to establish an internet connection before chrooting.
+
* Root privilege.
  
== Mount the partitions ==
+
* Another Linux environment, e.g. a LiveCD or USB flash media, or from another existing Linux distribution.
  
The root partition of the Linux system that you're trying to chroot into needs to be mounted first. To find out the device name assigned by the kernel, run:
+
* Matching architecture environments; i.e. the chroot from and chroot to. The architecture of the current environment can be discovered with: {{ic|uname -m}} (e.g. i686 or x86_64).
  
# lsblk /dev/sda
+
* Kernel modules loaded that are needed in the chroot environment.
  
You can also run the following to get an idea of your partition layout.
+
* Swap enabled if needed: {{bc|# swapon /dev/sd''xY''}}
  
# fdisk -l
+
* Internet connection established if needed.
  
Now create a directory where you would like to mount the root partition and mount it:
+
== Usage ==
  
# mkdir /mnt/arch
+
{{Note|
# mount /dev/sda3 /mnt/arch
+
*Some [[systemd]] tools such as ''localectl'' and ''timedatectl'' can not be used inside a chroot, as they require an active [[dbus]] connection. [https://github.com/systemd/systemd/issues/798#issuecomment-126568596]
 +
*The file system that will serve as the new root ({{ic|/}}) of your chroot must be accessible (i.e., decrypted, mounted).}}
  
Next, if you have separate partitions for other parts of your system (e.g. {{ic|/boot}}, {{ic|/home}}, {{ic|/var}}, etc), you should mount them, as well:
+
There are two main options for using chroot, described below.
  
# mount /dev/sda1 /mnt/arch/boot/
+
=== Using arch-chroot ===
# mount /dev/sdb5 /mnt/arch/home/
 
# mount ...
 
  
While it's possible to mount filesystems after you've chrooted, it is more convenient to do so beforehand. The reasoning for this is that you'll have to unmount the temporary filesystems after you exit the chroot, so this lets you umount all the filesystems with a single command. This also allows for a safer shutdown. Because the external Linux environment knows all mounted partitions, it can safely unmount them during shutdown.
+
The bash script {{ic|arch-chroot}} is part of the {{Pkg|arch-install-scripts}} package.  Before it runs {{ic|/usr/bin/chroot}}, the script mounts api filesystems like {{ic|/proc}} and makes {{ic|/etc/resolv.conf}} available from the chroot.
  
== Change root ==
+
==== Enter a chroot ====
  
Mount the temporary filesystems as root (note: newer install cds have the {{ic|arch-chroot /mnt/arch}} command, or if you prefer to type it:
+
Run arch-chroot with the new root directory as first argument:
  
  cd /mnt/arch
+
  # arch-chroot ''/location/of/new/root''
mount -t proc proc proc/
 
mount --rbind /sys sys/
 
mount --rbind /dev dev/
 
  
If you have established an internet connection and want to use it in the chroot environment, it may be necessary to copy over your DNS details:
+
For example, in the [[installation guide]] this directory would be {{ic|/mnt}}:
  
  cp /etc/resolv.conf etc/resolv.conf
+
  # arch-chroot /mnt
  
To root change and define the shell, do:
+
To exit the chroot simply use:
  
  chroot /mnt/arch /bin/bash
+
  # exit
  
{{Note|If you see the error {{ic|chroot: cannot run command '/usr/bin/bash': Exec format error}}, it is likely that the install-media and new-root program-architectures do not match.}}
+
==== Run a single command and exit ====
{{Note|If you see the error {{ic|chroot: '/usr/bin/bash': permission denied}}, remount with the exec permission: {{ic|mount -o remount,exec /mnt/arch}}.}}
 
Optionally, to source your Bash configuration ({{ic|~/.bashrc}} and {{ic|/etc/bash.bashrc}}), run:
 
  
source ~/.bashrc
+
To run a command from the chroot, and exit again append the command to the end of the line:
source /etc/profile
 
  
Optionally, create a unique prompt to be able to differentiate your chroot environment:
+
# arch-chroot ''/location/of/new/root'' ''mycommand''
  
export PS1="(chroot) $PS1"
+
For example, to run {{ic|mkinitcpio -p linux}} for a chroot located at {{ic|/mnt/arch}} do:
  
== Run graphical chrooted applications ==
+
# arch-chroot /mnt/arch mkinitcpio -p linux
  
If you have [[X]] running on your system, you can start graphical applications from the chroot environment.
+
=== Using chroot ===
  
To allow the chroot environment to connect to an X server, open a terminal inside the X server (i.e. inside the desktop of the user that is currently logged in), then run the [[xhost]] command, which gives permission to anyone to connect to the user's X server:
+
{{Warning|When using {{ic|--rbind}}, some subdirectories of {{ic|dev/}} and {{ic|sys/}} will not be unmountable. Attempting to unmount with {{ic|umount -l}} in this situation will break your session, requiring a reboot. If possible, use {{ic|-o bind}} instead.}}
  
$ xhost +
+
In the following example ''/location/of/new/root'' is the directory where the new root resides.
  
Then, to direct the applications to the X server from chroot, set the DISPLAY environment variable inside the chroot to match the DISPLAY variable of the user that owns the X server. So for example, run
+
First, mount the temporary api filesystems:
  
  $ echo $DISPLAY
+
  # cd ''/location/of/new/root''
 +
# mount -t proc /proc proc/
 +
# mount --rbind /sys sys/
 +
# mount --rbind /dev dev/
  
as the user that owns the X server to see the value of DISPLAY. If the value is ":0" (for example), then in the chroot environment run
+
And optionally:
  
  # export DISPLAY=:0
+
  # mount --rbind /run run/
  
Now you can launch GUI apps from the chroot command line. ;)
+
Next, in order to use an internet connection in the chroot environment copy over the DNS details:
  
== Perform system maintenance ==
+
# cp /etc/resolv.conf etc/resolv.conf
  
At this point you can perform whatever system maintenance you require inside the chroot environment. A few common examples are:
+
Finally, to change root into ''/location/of/new/root'' using a bash shell:
  
* Reinstall the bootloader.
+
# chroot ''/location/of/new/root'' /bin/bash
* Rebuild your [[mkinitcpio|initramfs]] image.
 
* Upgrade or [[Downgrading_Packages|downgrade]] packages.
 
* Reset a [[Password_Recovery|forgotten password]].
 
  
== Exit the chroot environment ==
+
{{Note|If you see the error:
 +
* {{ic|chroot: cannot run command '/usr/bin/bash': Exec format error}}, it is likely that the architectures of the host environment and chroot environment do not match.
 +
* {{ic|chroot: '/usr/bin/bash': permission denied}}, remount with the exec permission: {{ic|mount -o remount,exec /mnt/arch}}.
 +
}}
  
When you're finished with system maintenance, exit the chroot:
+
After chrooting it may be necessary to load the local bash configuration:
  
  # exit
+
  # source /etc/profile
 +
# source ~/.bashrc
  
Then unmount the temporary filesystems and any mounted devices:
+
{{Tip|Optionally, create a unique prompt to be able to differentiate your chroot environment:
 +
{{bc|1=# export PS1="(chroot) $PS1"}}
 +
}}
  
# umount {proc,sys,dev/pts,dev,boot,[...],}
+
When finished with the chroot, you can exit it via:
  
Finally, attempt to unmount your root partition:
+
# exit
  
# cd ..
+
Then unmount the temporary file systems:
# umount arch/
 
  
{{Note|If you get an error saying that {{ic|/mnt}} (or any other partition) is busy, this can mean one of two things:
+
# cd /
 +
# umount --recursive ''/location/of/new/root''
  
* A program was left running inside of the chroot.
+
{{Note|If there is an error mentioning something like: {{ic|umount: /path: device is busy}} this usually means that either: a program (even a shell) was left running in the chroot or that a sub-mount still exists. Quit the program and use {{ic|mount | grep /mnt/arch}} to find and {{ic|umount}} sub-mounts).  It may be tricky to {{ic|umount}} some things and one can hopefully have {{ic|umount --force}} work, as a last resort use {{ic|umount --lazy}} which just releases them.  In either case to be safe, {{ic|reboot}} as soon as possible if these are unresolved to avoid possible future conflicts.}}
  
* Or, more frequently, a sub-mount still exists (e.g. {{ic|/mnt/arch/boot}} within {{ic|/mnt/arch}}). Check with {{ic|lsblk}} to see if there are any mountpoints left:
+
== Run graphical applications from chroot ==
  
: {{bc|lsblk /dev/sda}}
+
If you have an [[X server]] running on your system, you can start graphical applications from the chroot environment.
  
: If you are still unable to unmount a partition, use the {{ic|--force}} option:
+
To allow the chroot environment to connect to an X server, open a virtual terminal inside the X server (i.e. inside the desktop of the user that is currently logged in), then run the [[xhost]] command, which gives permission to anyone to connect to the user's X server:
  
: {{bc|# umount -f /mnt}}}}
+
$ xhost +local:
  
After this, you will be able to safely reboot.
+
Then, to direct the applications to the X server from chroot, set the DISPLAY environment variable inside the chroot to match the DISPLAY variable of the user that owns the X server. So for example, run
  
== Example ==
+
$ echo $DISPLAY
This may protect your system from Internet attacks during browsing:
 
{{bc|1=
 
# # as root:
 
# cd /home/''user''
 
# mkdir myroot
 
# pacman -S arch-install-scripts
 
# # pacstrap must see myroot as mounted:
 
# mount --bind myroot myroot
 
# pacstrap -i myroot base base-devel
 
# mount -t proc proc myroot/proc/
 
# mount -t sysfs sys myroot/sys/
 
# mount -o bind /dev myroot/dev/
 
# mount -o gid=5 -t devpts pts myroot/dev/pts/
 
# cp -i /etc/resolv.conf myroot/etc/
 
# chroot myroot
 
# # inside chroot:
 
# passwd # set a password
 
# useradd -m -s /bin/bash ''user''
 
# passwd ''user'' # set a password
 
# # in a shell outside the chroot:
 
# pacman -S xorg-server-xnest
 
# # in a shell outside the chroot you can run this as ''user'':
 
$ Xnest -ac -geometry 1024x716+0+0 :1
 
# # continue inside the chroot:
 
# pacman -S xterm
 
# DISPLAY=:1
 
# xterm
 
# # xterm is now running in Xnest
 
# pacman -S xorg-server xorg-xinit xorg-server-utils
 
# pacman -S openbox
 
# # for java we need icedtea-web which requires some fonts:
 
# nano /etc/locale.gen
 
# # uncomment en_US.UTF-8 UTF-8, save and exit
 
# locale-gen
 
# echo LANG=en_US.UTF-8 > /etc/locale.conf
 
# export LANG=en_US.UTF-8
 
# pacman -S ttf-dejavu
 
# pacman -S icedtea-web
 
# pacman -S firefox
 
# firefox
 
# # firefox is now running in Xnest
 
# exit
 
# # outside chroot:
 
# chroot --userspec=''user'' myroot
 
# # inside chroot as ''user'':
 
$ DISPLAY=:1
 
$ openbox &
 
$ HOME="/home/''user''"
 
$ firefox
 
}}
 
See also: [https://help.ubuntu.com/community/BasicChroot Basic Chroot]
 
  
== An Alternative to chroot Using systemd-nspawn ==
+
as the user that owns the X server to see the value of DISPLAY. If the value is ":0" (for example), then in the chroot environment run
Alternatively, you can use systemd-nspawn to achieve the same thing, with added benefits (see the "systemd-nspawn" man page).
 
  
The steps are very similar:
+
# export DISPLAY=:0
  
First mount the root partition.
+
== Without root privileges ==
  
# mkdir /mnt/arch
+
Chroot requires root privileges, which may not be desirable or possible for the user to obtain in certain situations. There are, however, various ways to simulate chroot-like behavior using alternative implementations.
# mount /dev/sdx3 /mnt/arch
 
  
Then mount the boot and home partitions inside the root partition.
+
=== PRoot ===
  
# mount /dev/sdx1 /mnt/arch/boot
+
[[PRoot]] may be used to change the apparent root directory and use {{ic|mount --bind}} without root privileges. This is useful for confining applications to a single directory or running programs built for a different CPU architecture, but it has limitations due to the fact that all files are owned by the user on the host system. PRoot provides a {{ic|--root-id}} argument that can be used as a workaround for some of these limitations in a similar (albeit more limited) manner to ''fakeroot''.
# mount /dev/sdx4 /mnt/arch/home
 
  
Then, simply cd into the root partition and run systemd-nspawn.
+
=== Fakechroot ===
  
# cd /mnt/arch
+
{{Pkg|fakechroot}} is a library shim which intercepts the chroot call and fakes the results. It can be used in conjunction with {{Pkg|fakeroot}} to simulate a chroot as a regular user.
# systemd-nspawn
 
  
As you can see, there's no need to worry about mounting proc, sys, dev, or dev/pts. systemd-nspawn starts a new init process in the contained environment which takes care of everything. It's like booting up a second Linux OS on the same machine, but it's not a virtual machine.
+
# fakechroot fakeroot chroot ~/my-chroot bash
  
To quit, just log out or issue the poweroff command. You can then unmount the partitions like described above (except without having to worry about proc, sys, etc).
+
== See also ==
  
{{Expansion|Describe the steps to run an X server inside the systemd-nspawn container.}}
+
* [https://help.ubuntu.com/community/BasicChroot Basic Chroot]
 
 
Related: See [[Arch systemd container]].
 
 
 
== Without root privileges ==
 
Chroot requires root privileges, which may not be desirable or possible for the user to obtain in certain situations. There are, however, various ways to simulate chroot-like behavior using alternative implementations.
 
=== Proot ===
 
[[Proot]] may be used to change the apparent root directory and use {{ic|mount --bind}} without root privileges. This is useful for confining applications to a single directory or running programs built for a different CPU architecture, but it has limitations due to the fact that all files are owned by the user on the host system. Proot provides a {{ic|--root-id}} argument that can be used as a workaround for some of these limitations in a similar (albeit more limited) manner to [[fakeroot]].
 

Revision as of 12:26, 4 March 2018

ro:Chroot

Chroot is an operation that changes the apparent root directory for the current running process and their children. A program that is run in such a modified environment cannot access files and commands outside that environmental directory tree. This modified environment is called a chroot jail.

Reasoning

Changing root is commonly done for performing system maintenance on systems where booting and/or logging in is no longer possible. Common examples are:

See also Wikipedia:Chroot#Limitations.

Requirements

  • Root privilege.
  • Another Linux environment, e.g. a LiveCD or USB flash media, or from another existing Linux distribution.
  • Matching architecture environments; i.e. the chroot from and chroot to. The architecture of the current environment can be discovered with: uname -m (e.g. i686 or x86_64).
  • Kernel modules loaded that are needed in the chroot environment.
  • Swap enabled if needed:
    # swapon /dev/sdxY
  • Internet connection established if needed.

Usage

Note:
  • Some systemd tools such as localectl and timedatectl can not be used inside a chroot, as they require an active dbus connection. [1]
  • The file system that will serve as the new root (/) of your chroot must be accessible (i.e., decrypted, mounted).

There are two main options for using chroot, described below.

Using arch-chroot

The bash script arch-chroot is part of the arch-install-scripts package. Before it runs /usr/bin/chroot, the script mounts api filesystems like /proc and makes /etc/resolv.conf available from the chroot.

Enter a chroot

Run arch-chroot with the new root directory as first argument:

# arch-chroot /location/of/new/root

For example, in the installation guide this directory would be /mnt:

# arch-chroot /mnt

To exit the chroot simply use:

# exit

Run a single command and exit

To run a command from the chroot, and exit again append the command to the end of the line:

# arch-chroot /location/of/new/root mycommand

For example, to run mkinitcpio -p linux for a chroot located at /mnt/arch do:

# arch-chroot /mnt/arch mkinitcpio -p linux

Using chroot

Warning: When using --rbind, some subdirectories of dev/ and sys/ will not be unmountable. Attempting to unmount with umount -l in this situation will break your session, requiring a reboot. If possible, use -o bind instead.

In the following example /location/of/new/root is the directory where the new root resides.

First, mount the temporary api filesystems:

# cd /location/of/new/root
# mount -t proc /proc proc/
# mount --rbind /sys sys/
# mount --rbind /dev dev/

And optionally:

# mount --rbind /run run/

Next, in order to use an internet connection in the chroot environment copy over the DNS details:

# cp /etc/resolv.conf etc/resolv.conf

Finally, to change root into /location/of/new/root using a bash shell:

# chroot /location/of/new/root /bin/bash
Note: If you see the error:
  • chroot: cannot run command '/usr/bin/bash': Exec format error, it is likely that the architectures of the host environment and chroot environment do not match.
  • chroot: '/usr/bin/bash': permission denied, remount with the exec permission: mount -o remount,exec /mnt/arch.

After chrooting it may be necessary to load the local bash configuration:

# source /etc/profile
# source ~/.bashrc
Tip: Optionally, create a unique prompt to be able to differentiate your chroot environment:
# export PS1="(chroot) $PS1"

When finished with the chroot, you can exit it via:

# exit

Then unmount the temporary file systems:

# cd /
# umount --recursive /location/of/new/root
Note: If there is an error mentioning something like: umount: /path: device is busy this usually means that either: a program (even a shell) was left running in the chroot or that a sub-mount still exists. Quit the program and use mount to find and umount sub-mounts). It may be tricky to umount some things and one can hopefully have umount --force work, as a last resort use umount --lazy which just releases them. In either case to be safe, reboot as soon as possible if these are unresolved to avoid possible future conflicts.

Run graphical applications from chroot

If you have an X server running on your system, you can start graphical applications from the chroot environment.

To allow the chroot environment to connect to an X server, open a virtual terminal inside the X server (i.e. inside the desktop of the user that is currently logged in), then run the xhost command, which gives permission to anyone to connect to the user's X server:

$ xhost +local:

Then, to direct the applications to the X server from chroot, set the DISPLAY environment variable inside the chroot to match the DISPLAY variable of the user that owns the X server. So for example, run

$ echo $DISPLAY

as the user that owns the X server to see the value of DISPLAY. If the value is ":0" (for example), then in the chroot environment run

# export DISPLAY=:0

Without root privileges

Chroot requires root privileges, which may not be desirable or possible for the user to obtain in certain situations. There are, however, various ways to simulate chroot-like behavior using alternative implementations.

PRoot

PRoot may be used to change the apparent root directory and use mount --bind without root privileges. This is useful for confining applications to a single directory or running programs built for a different CPU architecture, but it has limitations due to the fact that all files are owned by the user on the host system. PRoot provides a --root-id argument that can be used as a workaround for some of these limitations in a similar (albeit more limited) manner to fakeroot.

Fakechroot

fakechroot is a library shim which intercepts the chroot call and fakes the results. It can be used in conjunction with fakeroot to simulate a chroot as a regular user.

# fakechroot fakeroot chroot ~/my-chroot bash

See also