2 # -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*-
3 # ex: ts=8 sw=4 sts=4 et filetype=sh
5 # Licensed under the GPLv2
7 # Copyright 2008-2010, Red Hat, Inc.
8 # Harald Hoyer <harald@redhat.com>
9 # Jeremy Katz <katzj@redhat.com>
14 [ "$RD_DEBUG" = "yes" ] ||
return
15 [ -e /run
/initramfs
/loginit.pipe
] ||
return
17 exec 0<>/dev
/console
1<>/dev
/console
2<>/dev
/console
20 while [ $i -lt 10 ]; do
21 if [ ! -e /run
/initramfs
/loginit.pipe
]; then
24 [ -z "${j##*Running*}" ] ||
break
30 if [ $i -eq 10 ]; then
31 kill %1 >/dev
/null
2>&1
32 kill $
(while read line
;do echo $line;done</run
/initramfs
/loginit.pid
)
36 rm -f /run
/initramfs
/loginit.pipe
/run
/initramfs
/loginit.pid
42 if [ "$1" = "-n" ]; then
53 [ -e /run
/initramfs
/.die
] && exit 1
54 if getargbool
1 rd.shell
-y rdshell || getarg rd.
break rdbreak
; then
55 echo "Dropping to debug shell."
57 export PS1
="$_rdshell_name:\${PWD}# "
58 [ -e /.profile
] ||
echo "exec 0<>/dev/console 1<>/dev/console 2<>/dev/console" > /.profile
61 warn
"Boot has failed. To debug this issue add \"rdshell\" to the kernel command line."
62 # cause a kernel panic
68 [ -d $NEWROOT ] || mkdir
-p -m 0755 $NEWROOT
70 trap "emergency_shell Signal caught!" 0
72 PATH
=/usr
/sbin
:/usr
/bin
:/sbin
:/bin
78 [ -c /dev
/null
] || mknod
-m 0666 /dev
/null c
1 3
80 # mount some important things
81 [ ! -d /proc
/self
] && \
82 mount
-t proc
-o nosuid
,noexec
,nodev
/proc
/proc
>/dev
/null
2>&1
84 [ ! -d /sys
/kernel
] && \
85 mount
-t sysfs
-o nosuid
,noexec
,nodev
/sys
/sys
>/dev
/null
2>&1
87 if [ -x /lib
/systemd
/systemd-timestamp
]; then
88 RD_TIMESTAMP
=$
(/lib
/systemd
/systemd-timestamp
)
90 read RD_TIMESTAMP _tmp
< /proc
/uptime
96 if [ "$RD_DEBUG" = "yes" ]; then
97 getarg quiet
&& DRACUT_QUIET
="yes"
99 [ -n "$a" ] && [ $a -ge 8 ] && unset DRACUT_QUIET
102 if ! ismounted
/dev
; then
103 # try to mount devtmpfs
104 if ! mount
-t devtmpfs
-o mode
=0755,nosuid
,noexec udev
/dev
>/dev
/null
2>&1; then
105 # if it failed fall back to normal tmpfs
106 mount
-t tmpfs
-o mode
=0755,nosuid udev
/dev
>/dev
/null
2>&1
107 # Make some basic devices first, let udev handle the rest
108 mknod
-m 0666 /dev
/null c
1 3
109 mknod
-m 0666 /dev
/ptmx c
5 2
110 mknod
-m 0600 /dev
/console c
5 1
111 mknod
-m 0660 /dev
/kmsg c
1 11
115 # prepare the /dev directory
116 [ ! -h /dev
/fd
] && ln -s /proc
/self
/fd
/dev
/fd
>/dev
/null
2>&1
117 [ ! -h /dev
/stdin
] && ln -s /proc
/self
/fd
/0 /dev
/stdin
>/dev
/null
2>&1
118 [ ! -h /dev
/stdout
] && ln -s /proc
/self
/fd
/1 /dev
/stdout
>/dev
/null
2>&1
119 [ ! -h /dev
/stderr
] && ln -s /proc
/self
/fd
/2 /dev
/stderr
>/dev
/null
2>&1
121 if ! ismounted
/dev
/pts
; then
122 mkdir
-m 0755 /dev
/pts
123 mount
-t devpts
-o gid
=5,mode
=620,noexec
,nosuid devpts
/dev
/pts
>/dev
/null
2>&1
126 if ! ismounted
/dev
/shm
; then
127 mkdir
-m 0755 /dev
/shm
128 mount
-t tmpfs
-o mode
=1777,nosuid
,nodev tmpfs
/dev
/shm
>/dev
/null
2>&1
131 if ! ismounted
/run
; then
132 mkdir
-m 0755 /newrun
133 mount
-t tmpfs
-o mode
=0755,nosuid
,nodev tmpfs
/newrun
>/dev
/null
2>&1
134 cp -a -t /newrun
/run
/*
135 mount
--move /newrun
/run
139 UDEVVERSION
=$
(udevadm
--version)
140 if [ $UDEVVERSION -gt 166 ]; then
141 # newer versions of udev use /run/udev/rules.d
142 export UDEVRULESD
=/run
/udev
/rules.d
144 mkdir
-m 0755 /dev
/.udev
/dev
/.udev
/rules.d
145 export UDEVRULESD
=/dev
/.udev
/rules.d
148 if [ "$RD_DEBUG" = "yes" ]; then
149 mkfifo /run
/initramfs
/loginit.pipe
150 loginit
$DRACUT_QUIET </run
/initramfs
/loginit.pipe
>/dev
/console
2>&1 &
151 exec >/run
/initramfs
/loginit.pipe
2>&1
153 exec 0<>/dev
/console
1<>/dev
/console
2<>/dev
/console
156 source_conf
/etc
/conf.d
158 # run scriptlets to parse the command line
159 getarg
'rd.break=cmdline' 'rdbreak=cmdline' && emergency_shell
-n cmdline
"Break before cmdline"
162 [ -z "$root" ] && die
"No or empty root= argument"
163 [ -z "$rootok" ] && die
"Don't know how to handle 'root=$root'"
165 # Network root scripts may need updated root= options,
166 # so deposit them where they can see them (udev purges the env)
169 echo "rflags='$rflags'"
170 echo "fstype='$fstype'"
171 echo "netroot='$netroot'"
172 echo "NEWROOT='$NEWROOT'"
175 # pre-udev scripts run before udev starts, and are run only once.
176 getarg
'rd.break=pre-udev' 'rdbreak=pre-udev' && emergency_shell
-n pre-udev
"Break before pre-udev"
179 # start up udev and trigger cold plugs
180 udevd
--daemon --resolve-names=never
182 UDEV_LOG_PRIO_ARG
=--log-priority
183 UDEV_QUEUE_EMPTY
="udevadm settle --timeout=0"
185 if [ $UDEVVERSION -lt 140 ]; then
186 UDEV_LOG_PRIO_ARG
=--log_priority
187 UDEV_QUEUE_EMPTY
="udevadm settle --timeout=1"
190 getargbool
0 rd.udev.info
-y rdudevinfo
&& udevproperty
"$UDEV_LOG_PRIO_ARG=info"
191 getargbool
0 rd.udev.debug
-y rdudevdebug
&& udevproperty
"$UDEV_LOG_PRIO_ARG=debug"
192 udevproperty
"hookdir=$hookdir"
194 getarg
'rd.break=pre-trigger' 'rdbreak=pre-trigger' && emergency_shell
-n pre-trigger
"Break before pre-trigger"
195 source_hook pre-trigger
198 udevadm trigger
--action=add
$udevtriggeropts >/dev
/null
2>&1
200 getarg
'rd.break=initqueue' 'rdbreak=initqueue' && emergency_shell
-n initqueue
"Break before initqueue"
202 RDRETRY
=$
(getarg rd.retry
'rd_retry=')
203 RDRETRY
=${RDRETRY:-20}
204 RDRETRY
=$
(($RDRETRY*2))
209 check_finished
&& break
213 check_finished
&& break
215 if [ -f $hookdir/initqueue
/work
]; then
216 rm $hookdir/initqueue
/work
219 for job
in $hookdir/initqueue
/*.sh
; do
220 [ -e "$job" ] ||
break
222 check_finished
&& break 2
225 $UDEV_QUEUE_EMPTY >/dev
/null
2>&1 ||
continue
227 for job
in $hookdir/initqueue
/settled
/*.sh
; do
228 [ -e "$job" ] ||
break
230 check_finished
&& break 2
233 $UDEV_QUEUE_EMPTY >/dev
/null
2>&1 ||
continue
235 # no more udev jobs and queues empty.
238 # dirty hack for some cdrom drives,
239 # which report no medium for quiet
241 for cdrom
in /sys
/block
/sr
*; do
242 [ -e "$cdrom" ] ||
continue
243 # skip, if cdrom medium was already found
244 strstr
"$(udevadm info --query=env --path=${cdrom##/sys})" \
245 ID_CDROM_MEDIA
&& continue
247 if [ -e "$cdrom"/events_poll_msecs
-a ! -e "/tmp/.poll_${cdrom##*/}" ]; then
248 msecs
=$
(while read a
; do echo $a;done < "$cdrom"/events_poll_msecs
)
249 if [ "$msecs" = "-1" ]; then
250 echo 250 > "$cdrom"/events_poll_msecs
251 > "/tmp/.poll_${cdrom##*/}"
254 echo change
> "$cdrom/uevent"
259 [ $i -gt $RDRETRY ] \
260 && { flock
-s 9 ; emergency_shell
"No root device \"$root\" found"; } 9>/.console_lock
265 # reset cdrom polling
266 for cdrom
in /sys
/block
/sr
*; do
267 [ -e "$cdrom" ] ||
continue
268 if [ -e "$cdrom"/events_poll_msecs
]; then
269 echo -1 > "$cdrom"/events_poll_msecs
273 # pre-mount happens before we try to mount the root filesystem,
275 getarg
'rd.break=pre-mount' 'rdbreak=pre-mount' && emergency_shell
-n pre-mount
"Break pre-mount"
276 source_hook pre-mount
279 getarg
'rd.break=mount' 'rdbreak=mount' && emergency_shell
-n mount
"Break mount"
280 # mount scripts actually try to mount the root filesystem, and may
281 # be sourced any number of times. As soon as one suceeds, no more are sourced.
284 [ -d "$NEWROOT/proc" ] && break;
285 for f
in $hookdir/mount
/*.sh
; do
286 [ -f "$f" ] && .
"$f"
287 [ -d "$NEWROOT/proc" ] && break;
292 && { flock
-s 9 ; emergency_shell
"Can't mount root filesystem"; } 9>/.console_lock
296 echo -n "Mounted root filesystem "
297 while read dev mp rest
; do [ "$mp" = "$NEWROOT" ] && echo $dev; done < /proc
/mounts
300 # pre pivot scripts are sourced just before we switch over to the new root.
301 getarg
'rd.break=pre-pivot' 'rdbreak=pre-pivot' && emergency_shell
-n pre-pivot
"Break pre-pivot"
302 source_hook pre-pivot
304 # by the time we get here, the root filesystem should be mounted.
306 for i
in "$(getarg real_init=)" "$(getarg init=)" /sbin
/init
/etc
/init
/init
/bin
/sh
; do
307 [ -n "$i" ] ||
continue
308 if ! [ -d "$NEWROOT$i" ] && [ -L "$NEWROOT$i" -o -x "$NEWROOT$i" ]; then
315 echo "Cannot find init!"
316 echo "Please check to make sure you passed a valid root filesystem!"
320 getarg rd.
break rdbreak
&& emergency_shell
-n switch_root
"Break before switch_root"
322 if [ $UDEVVERSION -lt 168 ]; then
323 # stop udev queue before killing it
324 udevadm control
--stop-exec-queue
327 while pidof udevd
>/dev
/null
2>&1; do
328 for pid
in $
(pidof udevd
); do
329 kill $HARD $pid >/dev
/null
2>&1
334 udevadm control
--exit
335 udevadm info
--cleanup-db
339 set +x
# Turn off debugging for this section
340 # Clean up the environment
341 for i
in $
(export -p); do
344 strstr
"$i" "=" ||
continue
346 [ -z "$i" ] && continue
348 root|PATH|HOME|TERM|PS4|RD_
*)
356 read CLINE
</proc
/cmdline
357 if getarg init
= >/dev
/null
; then
358 set +x
# Turn off debugging for this section
359 ignoreargs
="console BOOT_IMAGE"
360 # only pass arguments after init= to the init
361 CLINE
=${CLINE#*init=}
363 shift # clear out the rest of the "init=" arg
365 for s
in $ignoreargs; do
366 [ "${x%%=*}" = $s ] && continue 2
368 initargs
="$initargs $x"
372 set +x
# Turn off debugging for this section
376 [0-9]|s|S|single|emergency|auto
) \
377 initargs
="$initargs $x"
382 [ "$RD_DEBUG" = "yes" ] && set -x
384 if [ -d "$NEWROOT"/run
]; then
385 NEWRUN
="${NEWROOT}/run"
386 mount
--bind /run
"$NEWRUN"
387 NEWINITRAMFSROOT
="$NEWRUN/initramfs"
389 if [ "$NEWINITRAMFSROOT/lib" -ef "/lib" ]; then
390 for d
in bin etc lib lib64 sbin tmp usr var
; do
391 [ -h /$d ] && ln -fsn $NEWINITRAMFSROOT/$d /$d
395 NEWRUN
=/dev
/.initramfs
396 mkdir
-m 0755 "$NEWRUN"
397 mount
--bind /run
/initramfs
"$NEWRUN"
402 info
"Switching root"
408 CAPSH
=$
(command -v capsh
)
409 SWITCH_ROOT
=$
(command -v switch_root
)
413 if [ -f /etc
/capsdrop
]; then
415 info
"Calling $INIT with capabilities $CAPS_INIT_DROP dropped."
417 exec $CAPSH --drop="$CAPS_INIT_DROP" -- \
418 -c "exec switch_root \"$NEWROOT\" \"$INIT\" $initargs" || \
421 warn capsh
--drop=$CAPS_INIT_DROP -- -c exec switch_root
"$NEWROOT" "$INIT" $initargs
427 exec $SWITCH_ROOT "$NEWROOT" "$INIT" $initargs ||
{
428 warn
"Something went very badly wrong in the initramfs. Please "
429 warn
"file a bug against dracut."