Drop config_debug, not working under systemd as intended
[grml-autoconfig.git] / autoconfig.functions
1 #!/bin/zsh
2 # Filename:      autoconfig.functions
3 # Purpose:       basic system configuration and hardware setup for grml system
4 # Authors:       grml-team (grml.org), (c) Michael Prokop <mika@grml.org>
5 # Bug-Reports:   see http://grml.org/bugs/
6 # License:       This file is licensed under the GPL v2.
7 ################################################################################
8
9 # {{{ path, variables, signals, umask, zsh
10 export PATH="/bin:/sbin:/usr/bin:/usr/sbin"
11 DEBUG="/dev/null"
12 KERNEL="$(uname -r)"
13 ARCH="$(uname -m)"
14 umask 022
15
16 # old linuxrc version:
17 [ -d /cdrom ]      && export LIVECD_PATH=/cdrom
18 # initramfs layout until around December 2012:
19 [ -d /live/image ] && export LIVECD_PATH=/live/image
20 # initramfs layout since around December 2012:
21 [ -d /lib/live/mount/medium ] && export LIVECD_PATH=/lib/live/mount/medium
22
23 # Ignore these signals in non-interactive mode: INT, TERM, SEGV
24 [ -z "$PS1" ] && trap "" 2 3 11
25
26 if [ "$(cat /proc/1/comm 2>/dev/null)" = "systemd" ] ; then
27   SYSTEMD=true
28 else
29   SYSTEMD=false
30 fi
31
32 service_wrapper() {
33   if [ "$#" -lt 2 ] ; then
34     echo "Usage: service_wrapper <service> <action>" >&2
35     return 1
36   fi
37
38   local service="$1"
39   local action="$2"
40
41   if $SYSTEMD ; then
42     systemctl "$action" "$service"
43   else
44     /etc/init.d/"$service" "$action"
45   fi
46 }
47
48 # zsh stuff
49 iszsh(){
50 if [ -n "$ZSH_VERSION" ] ; then
51   return 0
52 else
53   return 1
54 fi
55 }
56 # avoid 'no matches found: ...'
57 iszsh && setopt no_nomatch # || echo "Warning: not running under zsh!"
58 # }}}
59
60 # {{{ Read in boot parameters
61 if [ -z "$CMDLINE" ]; then
62   # if CMDLINE was set from the outside, we're debugging.
63   # otherwise, take CMDLINE from Kernel and config files.
64   CMDLINE="$(cat /proc/cmdline)"
65   [ -d ${LIVECD_PATH}/bootparams/ ] && CMDLINE="$CMDLINE $(cat ${LIVECD_PATH}/bootparams/* | tr '\n' ' ')"
66   modprobe 9p 2>/dev/null || true
67   if grep -q 9p /proc/filesystems ; then
68       TAG="grml-parameters"
69       if grep -q "$TAG" /sys/bus/virtio/devices/*/mount_tag 2>/dev/null ; then
70           MOUNTDIR="$(mktemp -d)"
71           mount -t 9p -o trans=virtio,ro "$TAG" "$MOUNTDIR"
72           CMDLINE="$CMDLINE $(cat "$MOUNTDIR"/* 2>/dev/null | tr '\n' ' ')"
73           umount "$MOUNTDIR"
74           rmdir "$MOUNTDIR"
75       fi
76   fi
77 fi
78 # }}}
79
80 ### {{{ Utility Functions
81
82 # Get a bootoption's parameter: read boot command line and either
83 # echo last parameter's argument or return false.
84 getbootparam(){
85   local line
86   local ws
87   ws='   '
88   line=" $CMDLINE "
89   case "$line" in
90     *[${ws}]"$1="*)
91       result="${line##*[$ws]$1=}"
92       result="${result%%[$ws]*}"
93       echo "$result"
94       return 0 ;;
95     *) # no match?
96       return 1 ;;
97   esac
98 }
99
100 # Check boot commandline for specified option
101 checkbootparam(){
102   [ -n "$1" ] || ( echo "Error: missing argument to checkbootparam()" ; return 1 )
103   local line
104   local ws
105   ws='   '
106   line=" $CMDLINE "
107   case "$line" in
108     *[${ws}]"$1"=*|*[${ws}]"$1"[${ws}]*)
109       return 0 ;;
110     *)
111       return 1 ;;
112   esac
113 }
114
115 # Check if currently using a framebuffer
116 hasfb() {
117     [ -e /dev/fb0 ] && return 0 || return 1
118 }
119
120 # Check wheter a configuration variable (like $CONFIG_TOHD) is
121 # enabled or not
122 checkvalue(){
123   case "$1" in
124     [yY][eE][sS])     return 0 ;; # it's set to 'yes'
125     [tT][rR][uU][eE]) return 0 ;; # it's set to 'true'
126                    *) return 1 ;; # default
127   esac
128 }
129
130 # Are we using grml-small?
131 checkgrmlsmall(){
132   grep -q small /etc/grml_version 2>>$DEBUG && return 0 || return 1
133 }
134
135 # if no password is set return a random password
136 set_passwd() {
137   [ -n "$PASSWD" ] && return 0
138
139   if [ -x /usr/bin/apg ] ; then
140     PASSWD="$(apg -M NL -a 0 -m 8 -x 12 -n 1)"
141   elif [ -x /usr/bin/gpw ] ; then
142     PASSWD="$(gpw 1)"
143   elif [ -x /usr/bin/pwgen ] ; then
144     PASSWD="$(pwgen -1 8)"
145   elif [ -x /usr/bin/hexdump ] ; then
146     PASSWD="$(dd if=/dev/urandom bs=14 count=1 2>/dev/null | hexdump | awk '{print $3 $4}')"
147   elif [ -n "$RANDOM" ] ; then
148     PASSWD="grml${RANDOM}"
149   else
150     PASSWD=''
151     eerror "Empty passphrase and neither apg, gpw, pwgen, hexdump nor \$RANDOM available. Skipping."
152     eend 1
153     return 1
154   fi
155 }
156
157 ### }}}
158
159 # {{{ filesystems (proc, pts, sys) and fixes
160 mount_proc(){
161   [ -f /proc/version ] || mount -t proc /proc /proc 2>/dev/null
162 }
163
164 mount_pts(){
165   grep -q "/dev/pts" /proc/mounts || mount -t devpts /dev/pts /dev/pts 2>/dev/null
166 }
167
168 mount_sys(){
169   [ -d /sys/devices ] || mount -t sysfs /sys /sys 2>/dev/null
170 }
171 # }}}
172
173 # {{{ Check if we are running in live mode or from HD
174 INSTALLED=""
175 [ -e /etc/grml_cd ] || INSTALLED="yes"
176 # }}}
177
178 # {{{ provide information about virtual environments
179 VIRTUAL=false # assume physical system by default
180 KVM=false
181 VIRTUALBOX=false
182 VMWARE=false
183
184 if vmware-detect &>/dev/null; then
185   VIRTUAL=true; VMWARE=true; VIRTUAL_ENV='VMware'
186 elif [ "$(virt-what 2>/dev/null)" = "kvm" ] || \
187    [ "$(imvirt 2>/dev/null)" = "KVM" ] ; then
188   VIRTUAL=true; KVM=true; VIRTUAL_ENV='KVM'
189 elif [ "$(virt-what 2>/dev/null)" = "virtualbox" ] || \
190    [ "$(imvirt 2>/dev/null)" = "VirtualBox" ] ; then
191   VIRTUAL=true; VIRTUALBOX=true; VIRTUAL_ENV='VirtualBox'
192 fi
193 # }}}
194
195 # {{{ source lsb-functions , color handling
196 if checkbootparam 'nocolor'; then
197   . /etc/grml/lsb-functions
198   einfo "Disabling colors in bootsequence as requested on commandline." ; eend 0
199 else
200   . /etc/grml/lsb-functions
201 fi
202 # }}}
203
204 # {{{ log
205 config_log(){
206 if checkbootparam 'log' || checkbootparam 'debug' ; then
207    export DEBUG="/tmp/grml.log.`date +%Y%m%d`"
208    touch $DEBUG
209    einfo "Bootparameter log found. Log files: ${DEBUG} and /var/log/boot"
210    eindent
211      einfo "Starting bootlogd." # known to be *very* unreliable :(
212      bootlogd -r -c >>$DEBUG 2>&1 ; eend $?
213    eoutdent
214 else
215    DEBUG="/dev/null"
216 fi
217 }
218 # }}}
219
220 ### {{{ language configuration / localization
221 config_language(){
222
223  einfo "Activating language settings:"
224  eindent
225
226  # people can specify $LANGUAGE and $CONSOLEFONT in a config file
227  [ -r /etc/grml/autoconfig ] && . /etc/grml/autoconfig
228
229  # check for bootoption which overrides config from /etc/grml/autoconfig
230  BOOT_LANGUAGE="$(getbootparam 'lang' 2>>$DEBUG)"
231  [ -n "$BOOT_LANGUAGE" ] && LANGUAGE="$BOOT_LANGUAGE"
232
233  # set default to 'en' in live-cd mode iff $LANGUAGE is not set yet
234  if [ -z "$INSTALLED" ] ; then
235     [ -n "$LANGUAGE" ] || LANGUAGE='en'
236  fi
237
238  if [ -x /usr/sbin/grml-setlang ] ; then
239    # if bootoption lang is used update /etc/default/locale accordingly
240    if [ -n "$BOOT_LANGUAGE" ] ; then
241      /usr/sbin/grml-setlang "$LANGUAGE"
242    # otherwise default to lang=en
243    else
244      /usr/sbin/grml-setlang "en"
245    fi
246  fi
247
248  # set console font
249  if [ -z "$CONSOLEFONT" ] ; then
250     if ! checkbootparam 'nodefaultfont' >>$DEBUG 2>&1 ; then
251        if [ -r /usr/share/consolefonts/Uni3-Terminus16.psf.gz ] ; then
252           CONSOLEFONT='Uni3-Terminus16'
253        else
254           ewarn "/usr/share/consolefonts/Uni3-Terminus16.psf.gz not available. Please upgrade package console-terminus." ; eend 1
255        fi
256        if ! hasfb ; then
257           CONSOLEFONT='Lat15-Terminus16'
258        fi
259     fi
260  fi
261
262  # export it now, so error messages get translated, too
263  [ -r /etc/default/locale ] && . /etc/default/locale
264  export LANG LANGUAGE
265
266  # configure keyboard layout, read in already set values first:
267  [ -r /etc/sysconfig/keyboard ] && . /etc/sysconfig/keyboard
268
269  # now allow keyboard override by boot commandline for later use:
270  KKEYBOARD="$(getbootparam 'keyboard' 2>>$DEBUG)"
271  [ -n "$KKEYBOARD" ] && KEYTABLE="$KKEYBOARD"
272  # notce: de/at is a bad choice, so take de-latin1-nodeadkeys instead:
273  [[ "$KKEYBOARD" == 'de' ]] && KEYTABLE=de-latin1-nodeadkeys
274  [[ "$KKEYBOARD" == 'at' ]] && KEYTABLE=de-latin1-nodeadkeys
275
276  # modify /etc/sysconfig/keyboard only in live-cd mode:
277  if [ -z "$INSTALLED" ] ; then
278
279    local LANGUAGE="$BOOT_LANGUAGE"
280    . /etc/grml/language-functions
281    # allow setting xkeyboard explicitly different than console keyboard
282    KXKEYBOARD="$(getbootparam 'xkeyboard' 2>>$DEBUG)"
283    if [ -n "$KXKEYBOARD" ]; then
284       XKEYBOARD="$KXKEYBOARD"
285       KDEKEYBOARD="$KXKEYBOARD"
286    elif [ -n "$KKEYBOARD" ]; then
287       XKEYBOARD="$KKEYBOARD"
288       KDEKEYBOARD="$KKEYBOARD"
289    fi
290
291    # duplicate of previous code to make sure /etc/grml/language-functions
292    # does not overwrite our values....
293    # now allow keyboard override by boot commandline for later use:
294    KKEYBOARD="$(getbootparam 'keyboard' 2>>$DEBUG)"
295    [ -n "$KKEYBOARD" ] && KEYTABLE="$KKEYBOARD"
296    # notce: de/at is a bad choice, so take de-latin1-nodeadkeys instead:
297    [[ "$KKEYBOARD" == 'de' ]] && KEYTABLE=de-latin1-nodeadkeys
298    [[ "$KKEYBOARD" == 'at' ]] && KEYTABLE=de-latin1-nodeadkeys
299
300    # write keyboard related variables to file for later use
301    [ -d /etc/sysconfig ] || mkdir /etc/sysconfig
302    if ! [ -e /etc/sysconfig/keyboard ] ; then
303       echo "KEYTABLE=\"$KEYTABLE\""          > /etc/sysconfig/keyboard
304       echo "XKEYBOARD=\"$XKEYBOARD\""       >> /etc/sysconfig/keyboard
305       echo "KDEKEYBOARD=\"$KDEKEYBOARD\""   >> /etc/sysconfig/keyboard
306       echo "KDEKEYBOARDS=\"$KDEKEYBOARDS\"" >> /etc/sysconfig/keyboard
307    fi
308  fi
309
310  [ -r /etc/sysconfig/keyboard ] && . /etc/sysconfig/keyboard
311
312  # activate unicode console if running within utf8 environment
313  if [ -r /etc/default/locale ] ; then
314     if grep -q "LANG=.*UTF" /etc/default/locale ; then
315        einfo "Setting up unicode environment."
316        unicode_start >>$DEBUG 2>&1 ; eend $?
317     fi
318  fi
319
320  # Set default keyboard before interactive setup
321  if [ -n "$KEYTABLE" ] ; then
322     einfo "Running loadkeys for ${WHITE}${KEYTABLE}${NORMAL} in background"
323     loadkeys -q $KEYTABLE &
324     eend $?
325  fi
326
327  # we have to set up all consoles, therefore loop it over all ttys:
328  NUM_CONSOLES=$(fgconsole --next-available 2>/dev/null)
329  if [ -n "$NUM_CONSOLES" ] ; then
330     NUM_CONSOLES=$(expr ${NUM_CONSOLES} - 1)
331     [ ${NUM_CONSOLES} -eq 1 ] && NUM_CONSOLES=6
332  fi
333  CUR_CONSOLE=$(fgconsole 2>/dev/null)
334
335  if [ -x "$(which setfont)" ] ; then
336     use_setfont=true
337  elif [ -x "$(which consolechars)" ] ; then
338     use_consolechars=true
339  else
340     eerror "Neither setfont nor consolechars tool present, can not set font."
341     eend 1
342     return 1
343  fi
344
345  if [ -n "$CHARMAP" ] ; then
346     einfo "Setting font to ${CHARMAP}"
347     RC=0
348     for vc in $(seq 0 ${NUM_CONSOLES}) ; do
349         if $use_setfont ; then
350           setfont -C /dev/tty${vc} $CHARMAP ; RC=$?
351         elif $use_consolechars ; then
352           consolechars --tty=/dev/tty${vc} -m ${CHARMAP} ; RC=$?
353         fi
354     done
355     if [ -n "$CUR_CONSOLE" ] ; then
356        [ "$CUR_CONSOLE" != "serial" ] && chvt $CUR_CONSOLE
357     fi
358     eend $RC
359  fi
360
361  if checkbootparam 'noconsolefont' ; then
362     ewarn "Skipping setting console font as requested on boot commandline." ; eend 0
363  else
364     if [ -n "$CONSOLEFONT" ] ; then
365        einfo "Setting font to ${CONSOLEFONT}"
366        RC=0
367        for vc in $(seq 0 ${NUM_CONSOLES}) ; do
368            if $use_setfont ; then
369              setfont -C /dev/tty${vc} ${CONSOLEFONT} ; RC=$?
370            elif $use_consolechars ; then
371              consolechars --tty=/dev/tty${vc} -f ${CONSOLEFONT} ; RC=$?
372            fi
373        done
374        if [ -n "$CUR_CONSOLE" ] ; then
375           [ "$CUR_CONSOLE" != "serial" ] && chvt $CUR_CONSOLE
376        fi
377        eend $RC
378     fi
379  fi
380
381  eoutdent
382 }
383 # }}}
384
385 # {{{ Set hostname
386 config_hostname(){
387   if ! checkbootparam 'hostname' ; then
388     return 0
389   fi
390
391   HOSTNAME="$(getbootparam 'hostname' 2>>$DEBUG)"
392   if [ -z "$HOSTNAME" ] && [ -x /usr/bin/random-hostname ] ; then
393     einfo "Generating random hostname as no hostname was specified."
394     HOSTNAME="$(/usr/bin/random-hostname)"
395     eend $?
396   fi
397
398   einfo "Setting hostname to $HOSTNAME as requested."
399   grml-hostname $HOSTNAME >>$DEBUG
400   eend $?
401 }
402 # }}}
403
404 # fstabuser (needed when running from harddisk with username != grml {{{
405 config_userfstab(){
406   # force load of build-in and local config
407   [ -r /etc/grml/autoconfig ] && . /etc/grml/autoconfig
408   [ -r /etc/grml/autoconfig ] && . /etc/grml/autoconfig.local
409
410   # 1st. try configured fstab user
411   if [ -n "$CONFIG_FSTAB_USER" ] ; then
412      fstabuser=$(getent passwd $CONFIG_FSTAB_USER | cut -d: -f1)
413   fi
414
415   # 2nd. use standard user id
416   [ -n "$fstabuser" ] || fstabuser=$(getent passwd 1000 | cut -d: -f1)
417
418   # 3rd. use standard user name
419   [ -n "$fstabuser" ] || fstabuser=$(getent passwd grml | cut -d: -f1)
420
421   # if not yet set fall back to 'root' user, avoid bad /etc/fstab
422   [ -n "$fstabuser" ] || fstabuser='root'
423 }
424 # }}}
425
426 # local_user (needed when running with username != grml {{{
427 config_userlocal() {
428
429   # force load of build-in and local config
430   [ -r /etc/grml/autoconfig ] && . /etc/grml/autoconfig
431   [ -r /etc/grml/autoconfig ] && . /etc/grml/autoconfig.local
432
433   # 1st. try id of primary user
434   localuser=$(getent passwd 1000 | cut -d: -f1)
435
436   # 2nd. use name standard user
437   [ -n "$localuser" ] || localuser=$(getent passwd grml | cut -d: -f1)
438 }
439 # }}}
440
441 # {{{ Set clock (Local time is more often used than GMT, so it is default)
442 config_time(){
443  # don't touch the files if running from harddisk:
444  if [ -z "$INSTALLED" ]; then
445     # The default hardware clock timezone is stated as representing local time.
446     UTC="--localtime"
447
448     if [ -f /etc/default/rcS ] ; then
449       grep -q "^UTC=" /etc/default/rcS || echo "UTC=no" >> /etc/default/rcS
450       checkbootparam 'utc'       >>$DEBUG 2>&1 && sed -i "s|^UTC=.*$|UTC=yes|" /etc/default/rcS
451       checkbootparam 'gmt'       >>$DEBUG 2>&1 && sed -i "s|^UTC=.*$|UTC=yes|" /etc/default/rcS
452       checkbootparam 'localtime' >>$DEBUG 2>&1 && sed -i "s|^UTC=.*$|UTC=no|"  /etc/default/rcS
453       grep -q -i "^UTC=yes" /etc/default/rcS && UTC="-u"
454     # recent initscripts package versions don't ship /etc/default/rcS anymore, instead rely on /etc/adjtime
455     elif [ -f /etc/adjtime ] ; then
456       checkbootparam 'utc'       >>$DEBUG 2>&1 && sed -i "s/^LOCAL/UTC/" /etc/adjtime
457       checkbootparam 'gmt'       >>$DEBUG 2>&1 && sed -i "s/^LOCAL/UTC/" /etc/adjtime
458       checkbootparam 'localtime' >>$DEBUG 2>&1 && sed -i "s/^UTC$/LOCAL/" /etc/adjtime
459       grep -q "^UTC$" /etc/adjtime && UTC="-u"
460     fi
461
462     # hwclock uses the TZ variable
463     KTZ="$(getbootparam 'tz' 2>>$DEBUG)"
464     [ -z "$KTZ" ] && [ -r /etc/timezone ] && KTZ=$(cat /etc/timezone)
465     if [ ! -f "/usr/share/zoneinfo/$KTZ" ] ; then
466        ewarn "Warning: unknown timezone $KTZ" ; eend 1
467        KTZ="UTC"
468        ewarn "Falling back to timezone $KTZ" ; eend 0
469     fi
470
471     if ! [ -r /dev/rtc ] ; then
472       ewarn "Warning: realtime clock not available, trying to execute hwclock anyway." ; eend 0
473     fi
474
475     ERROR=$(TZ="$KTZ" hwclock $UTC -s 2>&1 | head -1) ; RC=$?
476     if [ -n "$ERROR" ] ; then
477        eindent
478        ERROR=$(TZ="$KTZ" hwclock $UTC -s --directisa 2>&1 | head -1)
479        if [ -n "$ERROR" ] ; then
480           eerror "Problem running hwclock: $ERROR" ; eend 1
481        fi
482        eoutdent
483     fi
484
485  fi
486 }
487 # }}}
488
489 # {{{ print kernel info
490 config_kernel(){
491   if $VIRTUAL && [ -n "$VIRTUAL_ENV" ] ; then
492     einfo "Running Linux Kernel $KERNEL inside $VIRTUAL_ENV" ; eend 0
493   else
494     einfo "Running Linux Kernel $KERNEL" ; eend 0
495   fi
496
497   if [ -r /proc/cpuinfo ] ; then
498     if egrep -q '^flags.*(vmx|svm)' /proc/cpuinfo ; then
499       eindent
500       einfo 'CPU(s) featuring virtualization technology detected' ; eend 0
501       eoutdent
502     fi
503   fi
504
505   if [ -d /proc/xen ] ; then
506     eindent
507     einfo 'Running kernel featuring support for Xen detected' ; eend 0
508     eoutdent
509   fi
510 }
511 # }}}
512
513 # {{{ secure boot
514 config_secureboot(){
515   if [ -x /usr/bin/mokutil ] ; then
516     local secstate=$(mokutil --sb-state 2>/dev/null) # "SecureBoot enabled"
517     if [ -n "$secstate" ] ; then
518       einfo "SecureBoot is enabled" ; eend 0
519     else
520       einfo "SecureBoot not detected" ; eend 0
521     fi
522   else
523     if modprobe efivars &>/dev/null ; then
524       if od -An -t u1 /sys/firmware/efi/vars/SecureBoot-*/data 2>/dev/null | grep -q 1 ; then
525         einfo "SecureBoot is enabled" ; eend 0
526       else
527         einfo "SecureBoot not detected" ; eend 0
528       fi
529     fi
530   fi
531 }
532 # }}}
533
534 # {{{ timezone
535 config_timezone(){
536  # don't touch the files if running from harddisk:
537  if [ -z "$INSTALLED" ]; then
538     KTZ="$(getbootparam 'tz' 2>>$DEBUG)"
539     if [ -n "$KTZ" ] ; then
540        if [ ! -f "/usr/share/zoneinfo/$KTZ" ]
541        then
542           ewarn "Warning: unknown timezone $KTZ"; eend 0
543        else
544           einfo "Setting timezone."
545           # update debconf
546           area=$(echo $KTZ | cut -d '/' -f1)
547           zone=$(echo $KTZ | cut -d '/' -f2)
548           echo "tzdata tzdata/Areas       select $area" | debconf-set-selections
549           echo "tzdata tzdata/Zones/$area select $zone" | debconf-set-selections
550           # update files
551           echo $KTZ > /etc/timezone
552           rm -f /etc/localtime
553           cp "/usr/share/zoneinfo/$KTZ" /etc/localtime ; eend $?
554        fi
555     fi
556  fi
557 }
558 # }}}
559
560 # activate serial console {{{
561 config_console(){
562 if checkbootparam 'console'; then
563   # this hack is no longer necessary with systemd
564   if $SYSTEMD ; then
565     return
566   fi
567
568   local line
569   local ws
570   ws='   '
571
572   einfo "Bootoption for serial console detected:"
573
574   line="$CMDLINE x "
575   this=""
576   line="${line#*[$ws]}"
577   local telinitq=""
578   while [ -n "$line" ]; do
579     case "$this" in
580       console=*)
581         local serial="$this"
582         local device="${this%%,*}"
583         local device="${device##*=}"
584         if echo $serial | grep -q ttyS ; then
585           local option="${serial##*,}"
586           # default (works for kvm & CO):
587           local speed="115200,57600,38400,19200,9600,4800,2400,1200";
588           # ... unless overriden by command line:
589           case "$option" in
590             115200*) speed=115200 ;;
591              57600*) speed=57600 ;;
592              38400*) speed=38400 ;;
593              19200*) speed=19200 ;;
594               9600*) speed=9600 ;;
595               4800*) speed=4800 ;;
596               2400*) speed=2400 ;;
597               1200*) speed=1200 ;;
598           esac
599           eindent
600             einfo "Activating console login on device ${device} with speed ${speed}."
601             local number="${device#ttyS}"
602             sed -i "/^T$number:/d;/^#grmlserial#/iT$number:23:respawn:/bin/bash -c \"/sbin/getty -L $device -l /usr/share/grml-scripts/run-welcome $speed vt100 || sleep 30\"" /etc/inittab
603             eend $?
604             telinitq="1"
605           eoutdent
606         fi
607         ;;
608     esac
609     this="${line%%[$ws]*}"
610     line="${line#*[$ws]}"
611   done
612
613   if [ -n "$telinitq" ]; then
614     /sbin/telinit q
615   fi
616   eend $?
617 fi
618 }
619 # }}}
620
621 # {{{ CD Checker
622 config_testcd(){
623 if checkbootparam 'testcd' ; then
624   einfo "Checking CD data integrity as requested by '${WHITE}testcd${NORMAL}' boot option."
625   eindent
626
627   local ERROR=true
628   local FOUND_FILE=false
629   local logfile='/tmp/md5sum.log'
630
631   rm -f "$logfile"
632
633   for md5 in $(find "${LIVECD_PATH}" -name md5sums) ; do
634     einfo "Checking files against $md5, this may take a while..."
635
636     FOUND_FILE=true
637     OLD_PWD=$(pwd)
638     cd $(dirname "$md5")
639     md5sum -c $(basename "$md5") |& tee -a "${logfile}"
640     if [ $pipestatus[1] -eq 0 ] ; then
641       ERROR=false
642     fi
643     cd "${OLD_PWD}"
644   done
645
646   if ! $FOUND_FILE ; then
647     eerror 'Error: Could not find md5sum file' ; eend 1
648     return
649   fi
650
651   if ! $ERROR ; then
652     einfo "Everything looks OK" ; eend 0
653   else
654     eerror 'Checksum failed for theses files:' ; eend 1
655     egrep -v '(^md5sum:|OK$)' "${logfile}"
656     eerror 'Data on the medium is possibly incomplete/damaged or RAM of your system is broken.' ; eend 1
657     einfon "Hit return to continue, or press the power button to shut down system."
658     read a
659   fi
660
661   eoutdent
662 fi
663 }
664 # }}}
665
666 # {{{ blacklist specific module [ used in /etc/init.d/udev ]
667 config_blacklist(){
668 if checkbootparam 'blacklist' ; then
669  if [ -z "$INSTALLED" ]; then
670   einfo "Bootoption blacklist found."
671   BLACK="$(getbootparam 'blacklist' 2>>$DEBUG)"
672   BLACKLIST_FILE='/etc/modprobe.d/grml.conf'
673   if [ -n "$BLACK" ] ; then
674     for module in $(echo ${BLACK//,/ }) ; do
675         einfo "Blacklisting module ${module} via ${BLACKLIST_FILE}."
676         echo "# begin entry generated by config_blacklist of grml-autoconfig" >> "$BLACKLIST_FILE"
677         echo "blacklist $module"     >> "$BLACKLIST_FILE"
678         echo "alias     $module off" >> "$BLACKLIST_FILE"
679         echo "# end   entry generated by config_blacklist of grml-autoconfig" >> "$BLACKLIST_FILE" ; eend $?
680     done
681   else
682    eerror "No given module for blacklist found. Blacklisting will not work therefore."
683   fi
684  else
685   ewarn "Backlisting via bootoption is not intended for use on harddisk installations." ; eend 1
686   eindent
687    einfo "Please blacklist the module(s) manually using the 'blacklist' script."
688   eoutdent
689  fi
690 fi
691 }
692 # }}}
693
694 # {{{ ACPI
695 config_acpi(){
696   if $SYSTEMD ; then
697     echo "systemd detected, no acpi(d) stuff needed." >>"$DEBUG"
698     return
699   fi
700
701   if checkbootparam 'noacpi'; then
702     ewarn "ACPI: Not loading modules as requested by boot option \"noacpi\"." ; eend 0
703   elif checkbootparam 'nogrmlacpi' ; then
704     ewarn "ACPI: Not loading modules as requested by boot option \"nogrmlacpi\"." ; eend 0
705   elif [ ! -d /proc/acpi ] ; then
706     ewarn "ACPI: Kernel support not present." ; eend 0
707   else
708     einfo "ACPI: Loading modules (disable with boot option noacpi / nogrmlacpi): "
709     eindent
710     found=""
711     for a in /lib/modules/$KERNEL/kernel/drivers/acpi/*; do
712       basename="${a##*/}"
713       basename="${basename%%.*}"
714       case "$basename" in *_acpi)
715         egrep -qi "${basename%%_acpi}" /proc/acpi/dsdt 2>>$DEBUG || continue ;;
716     esac
717     modprobe $basename >>$DEBUG 2>&1 && found="yes"
718     local BASE="$BASE $basename"
719   done
720   if [ -n "$found" ] ; then
721     einfo "$BASE"  ; eend 0
722   else
723     ewarn "(none)" ; eend 1
724   fi
725   if ! pgrep acpid >/dev/null ; then
726     einfo "Starting acpi daemon."
727     service_wrapper acpid.socket start >>$DEBUG 2>&1 ; eend $?
728     service_wrapper acpid start >>$DEBUG 2>&1 ; eend $?
729   else
730     ewarn "acpi daemon already running."
731     eend 0
732   fi
733   eoutdent
734 fi
735 }
736 # }}}
737
738 # {{{ Start brltty
739 config_brltty() {
740   if checkbootparam 'brltty' ; then
741     [ -x /lib/brltty/brltty.sh ] && /lib/brltty/brltty.sh
742   fi
743 }
744 # }}}
745
746 # {{{ Start creating /etc/fstab with HD partitions and USB SCSI devices now
747 config_fstab(){
748
749 NOSWAP="yes" # we do not use swap by default!
750 if checkbootparam 'swap' || checkbootparam 'anyswap' ; then
751    NOSWAP=''
752    checkbootparam 'anyswap' && export ANYSWAP='yes' || export ANYSWAP=""
753 fi
754
755 # Scan for swap, config, homedir - but only in live-mode
756 if [ -z "$INSTALLED" ] ; then
757    [ -z "$NOSWAP" ] && einfo "Searching for swap partition(s) as requested."
758    GRML_IMG=""
759    GRML_SWP=""
760    HOMEDIR="$(getbootparam 'home')"
761    if [ -n "$partitions" ]; then
762       while read p m f relax; do
763         case "$p" in *fd0*|*proc*|*sys*|*\#*) continue;; esac
764         partoptions="users,exec"
765         fnew=""
766         # it's a swap partition?
767         case "$f" in swap)
768           eindent
769           if [ -n "$NOSWAP" ]; then
770              ewarn "Ignoring swap partition ${WHITE}$p${NORMAL}. (Force usage via boot option 'swap', or execute grml-swapon)"
771              eend 0
772           else
773              case "$(dd if=$p bs=1 count=6 skip=4086 2>/dev/null)" in
774                    S1SUSP|S2SUSP|pmdisk|[zZ]*)
775                      if [ -n "$ANYSWAP" ] ; then
776                         einfo "Using swap partition ${WHITE}${p}${NORMAL} [bootoption anyswap found]."
777                         swapon $p 2>>$DEBUG ; eend $?
778                      else
779                         ewarn "Suspend signature on ${WHITE}${p}${NORMAL} found, not using as swap. (Force usage via boot option: anyswap)"
780                      fi
781                      ;;
782                    *)
783                      if [[ "$p" == LABEL* ]] ; then
784                         p=$(blkid -t $p | awk -F: '{print $1}')
785                      fi
786                      if grep -q $p /proc/swaps ; then
787                         ewarn "Not using swap partition ${WHITE}${p}${NORMAL} as it is already in use." ; eend 0
788                      else
789                         if [ -b "$p" ] ; then
790                         einfo "Using swap partition ${WHITE}${p}${NORMAL}."
791                         swapon $p 2>>$DEBUG ; eend $?
792                         else
793                         ewarn "$p is not a valid block device - not using it therefore." ; eend 0
794                         fi
795                      fi
796                      ;;
797              esac # dd-check
798           fi # -n "$NOSWAP
799           eoutdent
800           continue
801           ;;
802         esac # it's a swap partition?
803
804         # mount read-only
805         MOUNTOPTS="ro"
806         case "$f" in
807           vfat|msdos|ntfs) MOUNTOPTS="$MOUNTOPTS,uid=${fstabuser},gid=${fstabuser}" ;;
808           ext2|ext3|reiserfs|jfs|reiser4|xfs) MOUNTOPTS="$MOUNTOPTS,noatime" ;;
809           *) continue ;;
810           # *) NONEFOUND='1'; continue ;;
811         esac
812
813         # use a swapfile
814         if [ -z "$NOSWAP" ] ; then
815            mount -o "$MOUNTOPTS" -t $f $p $m 2>>$DEBUG && MOUNTED=1 || continue
816            # Activate swapfile, if exists
817            SWAPFILE="$(/bin/ls -1d $m/[Gg][Rr][Mm][Ll].[Ss][Ww][Pp] 2>/dev/null)"
818         fi
819         if [ -z "$NOSWAP" -a -n "$SWAPFILE" -a -f "$SWAPFILE" ]; then
820            mount -o remount,rw $m && MOUNTED=1
821            if swapon "$SWAPFILE" 2>>$DEBUG ; then
822               eindent
823                 einfo "Using GRML swapfile ${WHITE}${SWAPFILE}${NORMAL}."
824               eoutdent
825               fnew="$SWAPFILE swap swap defaults 0 0"
826               grep -q "$fnew" "/etc/fstab" || echo "$fnew" >> /etc/fstab
827               GRML_SWP="$GRML_SWP $SWAPFILE"
828               eend 0
829            fi
830            mount -o remount,ro $m 2>>$DEBUG && MOUNTED=1
831         fi
832
833         # use a image as home
834         IMAGE="$(/bin/ls -1d $m/[Gg][Rr][Mm][Ll].[Ii][Mm][Gg] 2>/dev/null)"
835         if [ -z "$GRML_IMG" -a -n "$IMAGE" -a -f "$IMAGE" ]; then
836            if [ -n "$HOMEDIR" ]; then
837               if [ "$HOMEDIR" != "scan" -a "$HOMEDIR" != "$IMAGE" -a "$HOMEDIR" != "${IMAGE%/*.*}" ]; then
838                  continue
839               fi
840            fi
841            if type -a grml-image >/dev/null 2>&1 && grml-image "$IMAGE" </dev/console >/dev/console 2>&1; then
842               GRML_IMG="$IMAGE"
843               mount -o remount,ro $m 2>>$DEBUG && MOUNTED=1
844            fi
845         fi
846         eend 0
847
848         # Umount, if not in use
849         [ -n "$MOUNTED" ] && umount -r $m 2>/dev/null
850
851       done <<EOT
852       $(cat /etc/fstab)
853 EOT
854    fi # -n $partitions
855 fi # -z $INSTALLED
856 }
857 # }}}
858
859 # {{{ CPU-detection
860 config_cpu(){
861 if checkbootparam 'nocpu'; then
862   ewarn "Skipping CPU detection as requested on boot commandline." ; eend 0
863   return 0
864 fi
865
866 if [[ $(grep -c processor /proc/cpuinfo) -gt 1 ]] ; then
867    einfo "Found CPU:"
868    CPU=$(awk -F: '/^processor/{printf " Processor"$2" is"};/^model name/{printf $2};/^vendor_id/{printf vendor};/^cpu MHz/{printf " %dMHz",int($2)};/^cache size/{printf ","$2" Cache"};/^$/{print ""}' /proc/cpuinfo 2>>$DEBUG)
869    echo $CPU | sed 's/ \{1,\}/ /g'
870    eend 0
871 else
872    einfo "Found CPU: `awk -F: '/^processor/{printf " Processor"$2" is"};/^model name/{printf $2};/^vendor_id/{printf vendor};/^cpu MHz/{printf " %dMHz",int($2)};/^cache size/{printf ","$2" Cache"};/^$/{print ""}' /proc/cpuinfo 2>>$DEBUG` " ; eend 0
873 fi
874
875 # no cpufreq setup inside VirtualBox
876 if $VIRTUALBOX ; then
877    einfo 'Virtual Box detected, skipping cpufreq setup.' ; eend 0
878    return 0
879 fi
880
881 if ! [ -x /etc/init.d/loadcpufreq ] ; then
882   ewarn "loadcpufreq init script not available, ignoring cpu frequency scaling."
883   eend 0
884   return 0
885 else
886    einfo "Trying to set up cpu frequency scaling:"
887    eindent
888    SKIP_CPU_GOVERNOR=''
889    LOADCPUFREQ=$(mktemp)
890    /etc/init.d/loadcpufreq start >"$LOADCPUFREQ" 2>&1 ; RC=$?
891    if grep -q FATAL "$LOADCPUFREQ" ; then
892       eindent
893         SKIP_CPU_GOVERNOR=1
894         oldIFS="$IFS"
895         IFS="
896 "
897          for line in $(grep FATAL "$LOADCPUFREQ" | sed 's/.*FATAL: //; s/ (.*)//') ; do
898              eerror "$line" ; eend $RC
899          done
900          IFS="$oldIFS"
901       eoutdent
902    elif grep -q done "$LOADCPUFREQ" ; then
903       MODULE=$(grep done "$LOADCPUFREQ" | sed 's/.*done (\(.*\))./\1/')
904       if [ -n "$MODULE" -a "$MODULE" != none ]; then
905          einfo "Loading cpufreq kernel module $MODULE" ; eend 0
906       else
907          SKIP_CPU_GOVERNOR=1
908          ewarn "Could not find an appropriate kernel module for cpu frequency scaling." ; eend 1
909       fi
910    fi
911
912    rm -f "$LOADCPUFREQ"
913
914    if [ -z "$SKIP_CPU_GOVERNOR" ] ; then
915      if [ -r /sys/devices/system/cpu/cpu0/cpufreq/scaling_available_governors ] ; then
916        if ! grep -q ondemand /sys/devices/system/cpu/cpu0/cpufreq/scaling_available_governors ; then
917          einfo "Ondemand governor not available for CPU(s), not modifying governor configuration"
918        else
919          einfo "Setting ondemand governor"
920          RC=0
921          for file in $(find /sys/devices/system/cpu/ -name scaling_governor 2>/dev/null) ; do
922            echo ondemand > $file || RC=1
923          done
924          eend $RC
925        fi
926      fi
927    fi
928
929    eoutdent
930 fi
931 }
932 # }}}
933
934 # {{{ autostart of ssh
935 config_ssh(){
936 if checkbootparam 'ssh' ; then
937    local PASSWD
938    PASSWD="$(getbootparam 'ssh' 2>>$DEBUG)"
939
940    config_userlocal
941    einfo "Bootoption ssh found, trying to set password for root and user $localuser"
942    [ -z "$localuser" ] && eend 1
943
944    eindent
945    if [ -z "$PASSWD" ] ; then
946      set_passwd && ewarn "No given password for found. Using random password: $PASSWD" && eend 0
947    fi
948    eoutdent
949
950    if [ -n "$PASSWD" ] ; then
951       chpass_options=""
952       if chpasswd --help 2>&1 | grep -q -- '-m,' ; then
953         chpass_options="-m"
954       fi
955
956       echo "$localuser:$PASSWD" | chpasswd $chpass_options
957       echo "root:$PASSWD" | chpasswd $chpass_options
958
959       eindent
960       ewarn "Warning: please change the password for root and user $localuser as soon as possible!"
961       eoutdent
962    fi
963
964    einfo "Starting secure shell server in background for root and user $localuser"
965    service_wrapper rmnologin start >>$DEBUG 2>>$DEBUG
966    service_wrapper ssh start >>$DEBUG 2>>$DEBUG &
967    eend $?
968
969 fi
970 }
971
972 # }}}
973
974 # {{{ display hostkeys of SSH server
975 config_display_ssh_fingerprints() {
976   if ! ls /etc/ssh/ssh_host_\*_key >/dev/null 2>&1 ; then
977     return 0 # no SSH host keys present
978   fi
979
980   einfo "SSH key fingerprints:"
981   for file in /etc/ssh/ssh_host_*_key ; do
982     einfon
983     ssh-keygen -l -f $file
984   done | column -t
985   eend $?
986 }
987 # }}}
988
989 # {{{ autostart of x11vnc
990 config_vnc(){
991 if checkbootparam 'vnc' ; then
992    config_userlocal
993    VNC_PASSWD=''
994    VNC_PASSWD="$(getbootparam 'vnc' 2>>$DEBUG)"
995    einfo "Bootoption vnc found, trying to set password for user $localuser."
996    eindent
997    if [ -z "$VNC_PASSWD" ] ; then
998       if [ -x /usr/bin/apg ] ; then
999          VNC_PASSWD="$(apg -M NL -a 0 -m 8 -x 12 -n 1)"
1000       elif [ -x /usr/bin/gpw ] ; then
1001          VNC_PASSWD="$(gpw 1)"
1002       elif [ -x /usr/bin/pwgen ] ; then
1003          VNC_PASSWD="$(pwgen -1 8)"
1004       elif [ -x /usr/bin/hexdump ] ; then
1005          VNC_PASSWD="$(dd if=/dev/urandom bs=14 count=1 2>/dev/null | hexdump | awk '{print $3 $4}')"
1006       elif [ -n "$RANDOM" ] ; then
1007          VNC_PASSWD="${localuser}${RANDOM}"
1008       else
1009          VNC_PASSWD=''
1010          eerror "Empty passphrase and neither pwgen nor hexdump nor \$RANDOM found. Skipping."
1011          eend 1
1012       fi
1013
1014       if [ -n "$VNC_PASSWD" ] ; then
1015          ewarn "No given password for vnc found. Using random password: $VNC_PASSWD" ; eend 0
1016       fi
1017    fi
1018    eoutdent
1019
1020    # finally check if we have a password we can use:
1021    if [ -n "$VNC_PASSWD" ] ; then
1022
1023       VNCDIR="/home/${localuser}/.vnc"
1024       [ -d "$VNCDIR" ] || mkdir "$VNCDIR"
1025
1026       if [ ! -x /usr/bin/x11vnc ] ; then
1027          eerror "Error: x11vnc not found - can not set up vnc. Please make sure to install the x11vnc package."
1028          eend 1
1029       else
1030          /usr/bin/x11vnc -storepasswd "$VNC_PASSWD" "$VNCDIR"/passwd ; eend $?
1031          /bin/chown -R "$localuser": "$VNCDIR"
1032       fi
1033    fi
1034    if checkbootparam 'vnc_connect' ; then
1035       VNC_CONNECT=''
1036       VNC_CONNECT="$(getbootparam 'vnc_connect' 2>>$DEBUG)"
1037       einfo "Bootoption vnc_connect found, will start vnc with connect to $VNC_CONNECT."
1038       #store the options in a file
1039       VNCDIR="/home/${localuser}/.vnc"
1040       [ -d "$VNCDIR" ] || mkdir "$VNCDIR"
1041       echo " --connect $VNC_CONNECT " >> $VNCDIR/options
1042    fi
1043 fi
1044 }
1045 # }}}
1046
1047 # {{{ set password for root and default user
1048 config_passwd(){
1049 if checkbootparam 'passwd' >>$DEBUG 2>&1; then
1050   local PASSWD
1051   PASSWD="$(getbootparam 'passwd' 2>>$DEBUG)"
1052
1053   config_userlocal
1054   einfo "Bootoption passwd found, trying to set password for root and user $localuser"
1055   [ -z "$localuser" ] && eend 1
1056
1057   eindent
1058   if [ -z "$PASSWD" ] ; then
1059     set_passwd && ewarn "No given password for found. Using random password: $PASSWD" && eend 0
1060   fi
1061   eoutdent
1062
1063   if [ -n "$PASSWD" ] ; then
1064     chpass_options=""
1065     if chpasswd --help 2>&1 | grep -q -- '-m,' ; then
1066       chpass_options="-m"
1067     fi
1068
1069     echo "$localuser:$PASSWD" | chpasswd $chpass_options
1070     echo "root:$PASSWD" | chpasswd $chpass_options
1071
1072     eindent
1073     ewarn "Warning: please change the password for root and user $localuser as soon as possible!"
1074     eoutdent
1075   fi
1076
1077 fi
1078
1079 if checkbootparam 'encpasswd' >>$DEBUG 2>&1; then
1080   local PASSWD
1081   PASSWD="$(getbootparam 'encpasswd' 2>>$DEBUG)"
1082
1083   if [ -z "$PASSWD" ] ; then
1084     eerror "No hashed password found, can not set password."
1085     eend 1
1086     return
1087   fi
1088
1089   config_userlocal
1090   einfo "Bootoption encpasswd found, trying to set hashed password for root and user $localuser"
1091   [ -z "$localuser" ] && eend 1
1092
1093   if [ -n "$PASSWD" ] ; then
1094     chpass_options="-e"
1095
1096     echo "$localuser:$PASSWD" | chpasswd $chpass_options
1097     echo "root:$PASSWD" | chpasswd $chpass_options
1098
1099     eindent
1100     ewarn "Warning: please change the password for root and user $localuser as soon as possible!"
1101     eoutdent
1102   fi
1103
1104 fi
1105 }
1106 # }}}
1107
1108 # {{{ Sound
1109 config_mixer () {
1110   if ! [ -x /usr/bin/amixer ] ; then
1111     logger -t grml-autoconfig "amixer binary not available"
1112     return
1113   fi
1114
1115   if ! [ -r /proc/asound/cards ] ; then
1116     ewarn "No soundcard present, skipping mixer settings therefore."
1117     eend 0
1118     return
1119   fi
1120
1121   for card in $(cat /proc/asound/cards| grep -e '^\s*[0-9]' | awk '{print $1}') ; do
1122     einfo "Configuring soundcard \"$(awk -F\[ '/^ *'$card' \[/{ FS=" "; $0=$2; print $1}' < /proc/asound/cards)\""
1123     eindent
1124
1125     if checkbootparam 'vol' ; then
1126       VOL="$(getbootparam 'vol' 2>>$DEBUG)"
1127       if [ -z "$VOL" ] ; then
1128         eerror "Bootoption vol found but no volume level/parameter given. Using defaults (75%)."
1129         VOL='75'
1130         eend 1
1131       fi
1132     else
1133       VOL='75'
1134     fi
1135
1136     if checkbootparam 'nosound' ; then
1137       einfo "Muting sound devices on request."
1138       ERROR=$(amixer -q set Master mute)
1139       RC=$?
1140       if [ -n "$ERROR" ] ; then
1141         eindent
1142         eerror "Problem muting sound devices: $ERROR"
1143         eoutdent
1144       fi
1145       eend $RC
1146     elif [ -z "$INSTALLED" ] ; then
1147       einfo "Setting mixer volumes to level ${WHITE}${VOL}${NORMAL}."
1148
1149       if checkbootparam 'micvol' ; then
1150         MICVOL="$(getbootparam 'micvol' 2>>$DEBUG)"
1151         einfo "Setting microphone to ${WHITE}${MICVOL}${NORMAL}."
1152       else
1153         MICVOL=0
1154       fi
1155
1156       CONTROLS=$(amixer -c $card scontrols | awk -F"Simple mixer control " '{print $2}')
1157       IFSOLD=${IFS:-}
1158       IFS='
1159       '
1160       for CONTROL in ${=CONTROLS} ; do
1161         # such devices can not be controlled with amixer ... unmute
1162         [[ "$CONTROL" == *Console* ]] && continue
1163
1164         if ! echo "${CONTROL}" | grep -q -i "mic" ; then
1165           if amixer -c $card sget "${CONTROL}" | grep -q 'Capabilities:.*pswitch' ; then
1166             amixer -c $card -q set "${CONTROL}" unmute
1167           fi
1168           if amixer -c $card sget "${CONTROL}" | grep -q -P 'Capabilities:.*(pvolume| volume)' ; then
1169             amixer -c $card -q set "${CONTROL}" "${VOL}"%
1170           fi
1171         fi
1172
1173         if [ ${MICVOL} -ne 0 ] ; then
1174           if amixer -c $card sget "${CONTROL}" | grep -q 'Capabilities:.*cswitch' ; then
1175             amixer -c $card -q set "${CONTROL}" unmute
1176           fi
1177           if amixer -c $card sget "${CONTROL}" | grep -q 'Capabilities:.*cvolume' ; then
1178             amixer -c $card -q set "${CONTROL}" $MICVOL%
1179           fi
1180           eend $?
1181         fi
1182       done
1183       IFS=$IFSOLD
1184     fi # checkbootparam 'nosound'
1185     eoutdent
1186   done
1187 }
1188 # }}}
1189
1190 # {{{ syslog service
1191 config_syslog(){
1192  if checkbootparam 'nosyslog'; then
1193     ewarn "Not starting syslog daemon as requested on boot commandline." ; eend 0
1194  else
1195     einfo "Starting rsyslog in background."
1196     service_wrapper rsyslog start >>$DEBUG &
1197     eend 0
1198  fi
1199 }
1200 # }}}
1201
1202 # {{{ gpm
1203 config_gpm(){
1204   if checkbootparam 'nogpm'; then
1205     ewarn "Not starting GPM as requested on boot commandline." ; eend 0
1206   else
1207     if ! [ -r /dev/input/mice ] ; then
1208       eerror "No mouse found - not starting GPM." ; eend 1
1209     else
1210       einfo "Starting gpm in background."
1211       service_wrapper gpm start >>$DEBUG &
1212       # ( while [ ! -e /dev/psaux ]; do sleep 5; done; /etc/init.d/gpm start >>$DEBUG ) &
1213       eend 0
1214     fi
1215   fi
1216 }
1217 # }}}
1218
1219 # {{{ services
1220 config_services(){
1221  if checkbootparam 'services' ; then
1222     SERVICE="$(getbootparam 'services' 2>>$DEBUG)"
1223     SERVICELIST=$(echo "$SERVICE" | sed 's/,/\\n/g')
1224     SERVICENL=$(echo "$SERVICE" | sed 's/,/ /g')
1225     for service in $(echo -e $SERVICELIST) ; do
1226       # support running (custom) init scripts in non-blocking mode
1227       # if they contain the keyword "DO_NO_RUN_IN_BACKGROUND".
1228       if grep -q 'DO_NO_RUN_IN_BACKGROUND' "/etc/init.d/${service}" 2>>$DEBUG ; then
1229         einfo "Starting service ${service}."
1230         service_wrapper "${service}" start >>$DEBUG
1231       else
1232         einfo "Starting service ${service} in background."
1233         service_wrapper "${service}" start >>$DEBUG &
1234       fi
1235     done
1236     eend $?
1237  fi
1238 }
1239 # }}}
1240
1241 # {{{ remote files
1242 get_remote_file() {
1243   [ "$#" -eq 2 ] || ( echo "Error: wrong parameter for get_remote_file()" ; return 1 )
1244   SOURCE=$(eval echo "$1")
1245   TARGET="$2"
1246   getconfig() {
1247   wget --timeout=10 --dns-timeout=10  --connect-timeout=10 --tries=1 \
1248        --read-timeout=10 ${SOURCE} -O ${TARGET} && return 0 || return 1
1249   }
1250   einfo "Trying to get ${WHITE}${TARGET}${NORMAL}"
1251
1252   if checkbootparam 'getfile.retries' ; then
1253     local counter="$(getbootparam 'getfile.retries' 2>>$DEBUG)"
1254   else
1255     local counter=10
1256   fi
1257
1258   while ! getconfig && [[ "$counter" != 0 ]] ; do
1259     echo -n "Sleeping for 1 second and trying to get config again... "
1260     counter=$(( counter-1 ))
1261     echo "$counter tries left" ; sleep 1
1262   done
1263   if [ -s "$TARGET" ] ; then
1264     einfo "Downloading was successfull." ; eend 0
1265     einfo "md5sum of ${WHITE}${TARGET}${NORMAL}: "
1266     md5sum ${TARGET} ; eend 0
1267     return 0;
1268   else
1269     einfo "Sorry, could not fetch ${SOURCE}" ; eend 1
1270     return 1;
1271  fi
1272 }
1273 # }}}
1274
1275 # {{{ config files
1276 config_netconfig(){
1277  if checkbootparam 'netconfig' ; then
1278   CONFIG="$(getbootparam 'netconfig' 2>>$DEBUG)"
1279   CONFIGFILE='/tmp/netconfig.grml'
1280
1281   if get_remote_file ${CONFIG} ${CONFIGFILE} ; then
1282     cd / && einfo "Unpacking ${WHITE}${CONFIGFILE}${NORMAL}:" && /usr/bin/unp $CONFIGFILE $EXTRACTOPTIONS ; eend $?
1283   fi
1284
1285  fi
1286 }
1287 # }}}
1288
1289 # {{{ remote scripts
1290 config_netscript() {
1291  if checkbootparam 'netscript' ; then
1292   CONFIG="$(getbootparam 'netscript' 2>>$DEBUG)"
1293   SCRIPTFILE='/tmp/netscript.grml'
1294
1295   if get_remote_file ${CONFIG} ${SCRIPTFILE} ; then
1296     chmod +x ${SCRIPTFILE}
1297     einfo "Running ${WHITE}${SCRIPTFILE}${NORMAL}:" && NETSCRIPT=${CONFIG} ${SCRIPTFILE} ; eend $?
1298   fi
1299
1300  fi
1301 }
1302 # }}}
1303
1304 # {{{ start X window system via grml-x
1305 config_x_startup(){
1306
1307
1308 # make sure we start X only if startx is used *before* a nostartx option
1309 # so it's possible to disable automatic X startup using nostart
1310 if checkbootparam 'startx' && ! echo "$CMDLINE" | grep -q 'startx.*nostartx' ; then
1311  if [ -x "$(which X)" ] ; then
1312   if [ -z "$INSTALLED" ] ; then
1313    WINDOWMANAGER="$(getbootparam 'startx' 2>>$DEBUG)"
1314    if [ -z "$WINDOWMANAGER" ] ; then
1315      einfo "No window manager specified. Using default one." && eend 0
1316    else
1317      einfo "Window manager ${WHITE}${WINDOWMANAGER}${NORMAL} found as bootoption." && eend 0
1318    fi
1319    einfo "Setting up and invoking grml-x ${WINDOWMANAGER}. Just exit X windows system to get full featured consoles."
1320    config_userlocal
1321    if $SYSTEMD ; then
1322      cat>|/etc/init.d/startx<<EOF
1323 #!/bin/sh
1324 chgrp tty \${TTY}
1325 chmod g=rw \${TTY}
1326 sudo -u "${localuser}" /usr/bin/grml-x ${WINDOWMANAGER}
1327 EOF
1328      chmod 755 /etc/init.d/startx
1329      chvt 6
1330      return
1331    fi
1332    cat>|/etc/init.d/startx<<EOF
1333 #!/bin/sh
1334 su "${localuser}" -c "/usr/bin/grml-x ${WINDOWMANAGER}"
1335 EOF
1336    chmod 755 /etc/init.d/startx
1337
1338    # adjust inittab for startx
1339    if grep -q '^6:' /etc/inittab ; then
1340       sed -i 's|^6:.*|6:2345:respawn:/bin/zsh --login -c "/etc/init.d/startx ; /usr/share/grml-scripts/run-welcome" >/dev/tty6 2>\&1 </dev/tty6|' /etc/inittab
1341    else # just append tty6 to inittab if no definition is present:
1342       echo '6:2345:respawn:/bin/zsh --login -c "/etc/init.d/startx ; /usr/share/grml-scripts/run-welcome" >/dev/tty6 2>&1 < /dev/tty6' >> /etc/inittab
1343    fi
1344
1345    /sbin/telinit q ; eend $?
1346
1347    if grep -q '^allowed_users=' /etc/X11/Xwrapper.config ; then
1348       sed -i 's/^allowed_users=.*/allowed_users=anybody/' /etc/X11/Xwrapper.config
1349    else
1350       echo 'allowed_users=anybody' >> /etc/X11/Xwrapper.config
1351    fi
1352
1353   else
1354     eerror "We are not running in live mode - startx will not work, skipping it."
1355     eerror " -> Please use something like xdm, gdm or kdm for starting X on a harddisk system!" ; eend 1
1356   fi
1357  else
1358    eerror "/usr/bin/X is not present on this grml flavour."
1359    eerror "  -> Boot parameter startx does not work therefore." ; eend 1
1360  fi
1361 fi
1362 }
1363 # }}}
1364
1365 # {{{ configuration framework
1366 config_extract(){
1367 if checkbootparam 'extract' ; then
1368  EXTRACT="$(getbootparam 'extract' 2>>$DEBUG)"
1369  EXTRACTOPTIONS="-- -x $EXTRACT"
1370 fi
1371 }
1372
1373 config_finddcsdir() {
1374 #  - If no GRMLCFG partition is found and noautoconfig is _not_ given
1375 #    on the command line, nothing is changed and the dcs files are
1376 #    searched within the .iso, $dcs-dir is set to the root directory
1377 #    within the .iso
1378 #  - If a GRMLCFG partition is found, $dcs-dir is set to the root of
1379 #    the GRMLCFG partition unless noautoconfig is set. If noautoconfig is
1380 #    set, $dcs-dir is set to the root directory within the .iso.
1381 #  - If myconfig=foo is set on the command line, $dcs-dir is set to
1382 #    foo, even if a GRMLCFG partition is present.
1383 DCSDIR=""
1384 DCSMP="/mnt/grml"
1385 # autoconfig, see issue673
1386 GRMLCFG="$(getbootparam 'autoconfig' 2>>$DEBUG)"
1387 [ -n "$GRMLCFG" ] || GRMLCFG="GRMLCFG"
1388 if checkbootparam 'noautoconfig' ; then
1389   DCSDIR="${LIVECD_PATH}" # set default so it works for "scripts" boot option as expected
1390   ewarn "Skipping running automount of device(s) labeled $GRMLCFG as requested." ; eend 0
1391 else
1392   if [ -z "$INSTALLED" ] ; then
1393     if checkbootparam 'myconfig' ; then
1394       DCSDEVICE="$(getbootparam 'myconfig' 2>>$DEBUG)"
1395       if [ -z "$DCSDEVICE" ]; then
1396         eerror "Error: No device for bootoption myconfig provided." ; eend 1
1397       fi # [ -z "$DCSDEVICE" ]
1398     elif checkvalue $CONFIG_MYCONFIG; then # checkbootparam myconfig
1399       einfo "Searching for device(s) labeled with $GRMLCFG. (Disable this via boot option: noautoconfig)" ; eend 0
1400       eindent
1401       DCSDEVICE=$(blkid -t LABEL=$GRMLCFG | head -1 | awk -F: '{print $1}')
1402
1403       modprobe 9p 2>/dev/null || true
1404       if [ -z "$DCSDEVICE" ] && grep -q 9p /proc/filesystems ; then
1405           if grep -q "$GRMLCFG" /sys/bus/virtio/devices/*/mount_tag 2>/dev/null ; then
1406             einfo "Found 9p-virtio fs with mount_tag $GRMLCFG"
1407             DCSDEVICE="$GRMLCFG"
1408             MOUNTOPTIONS="ro,trans=virtio"
1409             DCSFS="9p"
1410           fi
1411       fi
1412
1413       if [ -n "$DCSDEVICE" ]; then
1414         DCSMP="/mnt/grmlcfg"
1415       fi
1416       eoutdent
1417     fi
1418
1419     # if not specified/present then assume default:
1420     if [ -z "$DCSDEVICE" ]; then
1421       DCSDIR="${LIVECD_PATH}"
1422     else
1423       eindent
1424       einfo "debs, config, scripts are read from $DCSDEVICE." ; eend 0
1425       DCSDIR="$(< /proc/mounts awk -v DCSDEV=$DCSDEVICE '{if ($1 == DCSDEV) { print $2 }}')"
1426       if [ -n "$DCSDIR" ]; then
1427         ewarn "$DCSDEVICE already mounted on $DCSDIR"; eend 0
1428       else
1429         [ -d $DCSMP ] || mkdir $DCSMP
1430         umount $DCSMP >>$DEBUG 2>&1 # make sure it is not mounted
1431         mount -o ${MOUNTOPTIONS:-ro} -t ${DCSFS:-auto} $DCSDEVICE  $DCSMP ; RC="$?"
1432         if [[ $RC == 0 ]]; then
1433           einfo "Successfully mounted $DCSDEVICE to $DCSMP (readonly)." ; eend 0
1434         else
1435           eerror "Error: mounting $DCSDEVICE to $DCSMP (readonly) failed." ; eend 1
1436         fi
1437         DCSDIR="$DCSMP"
1438       fi
1439       eoutdent
1440     fi
1441   fi
1442 fi
1443
1444 if [ -n "$DCSDIR" -a "$DCSDIR" != "${LIVECD_PATH}" ] ; then
1445   einfo "Debs, config, scripts (if present) will be read from $DCSDIR." ; eend 0
1446 elif checkbootparam 'debs' || checkbootparam 'config' || checkbootparam 'scripts'; then
1447   einfo "Debs, config, scripts will be read from the live image directly." ; eend 0
1448 fi
1449 }
1450
1451
1452 config_partconf() {
1453 if checkbootparam 'partconf' ; then
1454  MOUNTDEVICE="$(getbootparam 'partconf' 2>>$DEBUG)"
1455  if [ -n "$MOUNTDEVICE" ]; then
1456    [ -d /mnt/grml ] || mkdir /mnt/grml
1457    mount -o ro -t auto $MOUNTDEVICE /mnt/grml ; RC="$?"
1458     if [[ $RC == 0 ]]; then
1459       einfo "Successfully mounted $MOUNTDEVICE to /mnt/grml (readonly)." ; eend 0
1460       einfo "Copying files from $MOUNTDEVICE over grml system."
1461       for file in `cat /etc/grml/partconf` ; do
1462         [ -d /mnt/grml/$file ] && cp -a /mnt/grml/${file}* ${file} && echo "copied: $file"
1463         [ -f /mnt/grml/$file ] && cp -a /mnt/grml/${file}  ${file} && echo "copied: $file"
1464       done && eend 0
1465     else
1466       einfo "Could not mount $MOUNTDEVICE to /mnt/grml - sorry." ; eend 1
1467     fi # mount $MOUNTDEVICE
1468    grep -q '/mnt/grml' /proc/mounts && umount /mnt/grml
1469  else
1470    einfo "Sorry, no device for bootoption partconf provided. Skipping." ; eend 1
1471  fi # [ -n "$MOUNTDEVICE" ]
1472 fi
1473 }
1474 # }}}
1475
1476 # {{{ /cdrom/.*-options
1477 config_debs(){
1478 if checkbootparam 'debs' ; then
1479    iszsh && setopt localoptions shwordsplit
1480    DEBS="$(getbootparam 'debs' 2>>$DEBUG)"
1481    if [ -z "$DEBS" ] ; then
1482       DEBS="*.deb"
1483    fi
1484    if ! echo $DEBS | grep -q '/'; then
1485      # backwards compatibility: if no path is given get debs from debs/
1486      DEBS="debs/$DEBS"
1487    fi
1488    einfo "Trying to install Debian package(s) ${DEBS}"
1489    DEBS="$(eval echo ${DCSDIR}/$DEBS)"
1490    dpkg -i $DEBS ; eend $?
1491 fi
1492 }
1493
1494 config_scripts(){
1495 if checkbootparam 'scripts' || [ "$DCSMP" = "/mnt/grmlcfg" ]; then
1496    SCRIPTS="$(getbootparam 'scripts' 2>>$DEBUG)"
1497    if [ -d ${DCSDIR}/scripts ] && [ -z "$SCRIPTS" ]; then
1498      SCRIPTS="$(cd ${DCSDIR}/scripts; /bin/ls -1d [Gg][Rr][Mm][Ll].[Ss][Hh] 2>>$DEBUG)"
1499    fi
1500    if ! echo $SCRIPTS | grep -q '/'; then
1501      # backwards compatibility: if no path is given get scripts from scripts/
1502      SCRIPTS="scripts/$SCRIPTS"
1503    fi
1504    if [ -n "$SCRIPTS" ]; then
1505      SCRIPTS="${DCSDIR}/$SCRIPTS"
1506      if [ "$DCSMP" = "/mnt/grmlcfg" ]; then
1507        einfo "Trying to execute ${SCRIPTS}"
1508        sh -c $SCRIPTS
1509        eend $?
1510      elif [ -d "$SCRIPTS" ]; then
1511        einfo "Bootparameter scripts found. Trying to execute from directory ${SCRIPTS}:"
1512        run-parts --regex '.*' $SCRIPTS
1513        eend $?
1514      else
1515        einfo "Bootparameter scripts found. Trying to execute ${SCRIPTS}:"
1516        sh -c $SCRIPTS
1517        eend $?
1518      fi
1519    fi
1520 fi
1521 }
1522
1523 config_config(){
1524 if checkbootparam 'config' || [ "$DCSMP" = "/mnt/grmlcfg" ]; then
1525   CONFIG="$(getbootparam 'config' 2>>$DEBUG)"
1526   if [ -z "$CONFIG" ]; then
1527     CONFIG="$(cd ${DCSDIR}; ls -1d [Cc][Oo][Nn][Ff][Ii][Gg].[Tt][Bb][Zz] 2>>$DEBUG)"
1528   fi
1529   if [ -n "$CONFIG" ]; then
1530     if [ -d "${DCSDIR}/${CONFIG}" ] ; then
1531       einfo "Taking configuration from directory ${DCSDIR}/${CONFIG}"
1532
1533       cp -a ${DCSDIR}/${CONFIG}/* /
1534     elif [ -f "${DCSDIR}/${CONFIG}" ]; then
1535       einfo "Extracting configuration from file ${DCSDIR}/${CONFIG}"
1536
1537       cd /
1538       unp ${DCSDIR}/${CONFIG} $EXTRACTOPTIONS ; eend $?
1539     else
1540       ewarn "Sorry, could not find configuration file or directory ${DCSDIR}/${FILENAME}." ; eend 1
1541     fi
1542   fi
1543 fi
1544 }
1545 # }}}
1546
1547 # {{{ confing_umount_dcsdir
1548 config_umount_dcsdir(){
1549    # umount $DCSMP if it was mounted by finddcsdir
1550    grep -q "$DCSMP" /proc/mounts && umount "$DCSMP"
1551 }
1552 # }}}
1553
1554 # {{{ mypath
1555 config_mypath(){
1556 if checkbootparam 'mypath' ; then
1557    MY_PATH="$(getbootparam 'mypath' 2>>$DEBUG)"
1558    einfo "Bootparameter mypath found, adding ${MY_PATH} to /etc/grml/my_path"
1559    touch /etc/grml/my_path
1560    chmod 644 /etc/grml/my_path
1561    # make sure the directories exist:
1562    eindent
1563    for i in $(echo $MY_PATH | sed 's/:/\n/g') ; do
1564        if ! [ -d "$i" ] ; then
1565           einfo "Creating directory $i"
1566           mkdir -p "$i" ; eend $?
1567        fi
1568    done
1569    grep -q "${MY_PATH}" /etc/grml/my_path || echo "${MY_PATH}" >> /etc/grml/my_path ; eend $?
1570    eoutdent
1571 fi
1572 }
1573 # }}}
1574
1575 # {{{ SW-RAID
1576 config_swraid(){
1577   [ -n "$INSTALLED" ] && return 0
1578
1579   if checkbootparam 'noraid'   || checkbootparam 'noswraid' || \
1580      checkbootparam 'raid=noautodetect' ; then
1581      ewarn "Skipping SW-RAID code as requested on boot commandline." ; eend 0
1582   else
1583     [ -e /proc/mdstat ] || modprobe md_mod
1584     if ! [ -x /sbin/mdadm ] ; then
1585        eerror "mdadm not available, can not execute it." ; eend 1
1586     else
1587
1588        # if ! egrep -qv '^(MAILADDR.*|#.*|)$' /etc/mdadm/mdadm.conf 2>>$DEBUG ; then
1589        # find out whether we have a valid configuration file already
1590        if ! grep -q ARRAY /etc/mdadm/mdadm.conf 2>>$DEBUG ; then
1591           einfo "Creating /etc/mdadm/mdadm.conf for use with mdadm."
1592           [ -r /etc/mdadm/mdadm.conf ] && mv /etc/mdadm/mdadm.conf /etc/mdadm/mdadm.conf.old
1593           MDADM_MAILADDR__='root' /usr/share/mdadm/mkconf > /etc/mdadm/mdadm.conf ; eend $?
1594         else
1595           ewarn "/etc/mdadm/mdadm.conf looks like a configured mdadm setup, will not touch it." ; eend 0
1596        fi
1597
1598        if ! checkbootparam 'swraid' ; then
1599           eindent
1600           if $SYSTEMD ; then
1601             einfo "Just run 'Start mdmonitor' to assemble md arrays or boot using 'swraid' as bootoption for autostart."
1602           else
1603             einfo "Just run 'Start mdadm-raid' to assemble md arrays or boot using 'swraid' as bootoption for autostart."
1604           fi
1605           eoutdent
1606        else
1607           einfo "Bootoption swraid found. Searching for software RAID arrays:"
1608           eindent
1609            IFSOLD=${IFS:-}
1610            IFS='
1611 '
1612            for line in $(mdadm --assemble --scan --auto=yes --symlink=no 2>&1) ; do
1613                case $line in
1614                  *'No arrays found'*)
1615                    ewarn "$line" ; eend 0
1616                    ;;
1617                  *)
1618                    einfo "$line" ; eend 0
1619                    ;;
1620                esac
1621            done
1622            IFS=$IFSOLD
1623          eoutdent
1624
1625          if [ -r /proc/mdstat ] ; then
1626             eindent
1627             MDSTAT=$(grep '^md[0-9]' /proc/mdstat)
1628             if [ -z "$MDSTAT" ] ; then
1629                ewarn "No active arrays found" ; eend 0
1630             else
1631                IFSOLD=${IFS:-}
1632                IFS='
1633 '
1634                for line in $(grep '^md[0-9]' /proc/mdstat) ; do
1635                    einfo "active arrays: $line" ; eend 0
1636                done
1637                IFS=$IFSOLD
1638             fi
1639             eoutdent
1640          fi # /proc/mdstat
1641        fi # bootoption swraid
1642
1643      fi # is /sbin/mdadm executable?
1644   fi # check for bootoptions
1645 }
1646 # }}}
1647
1648 # {{{ dmraid
1649 config_dmraid(){
1650   [ -n "$INSTALLED" ] && return 0
1651
1652   if checkbootparam 'nodmraid' ; then
1653     ewarn "Skipping dmraid code as requested on boot commandline." ; eend 0
1654     return 0
1655   fi
1656
1657   if ! [ -x /sbin/dmraid ] ; then
1658     eerror "dmraid not available, can not execute it." ; eend 1
1659     return
1660   fi
1661
1662   dmraid_wrapper() {
1663     # usage: dmraid_wrapper <dmraid_option>
1664     [ -n "$1" ] || return 1
1665
1666     IFSOLD=${IFS:-}
1667     IFS='
1668 '
1669     eindent
1670
1671     for line in $(dmraid $1 ; echo errcode:$?); do
1672       case $line in
1673         *'no block devices found'*)
1674           einfo "No block devices found" ; eend 0
1675           break
1676           ;;
1677         *'no raid disks'*)
1678           einfo "No active dmraid devices found" ; eend 0
1679           break
1680           ;;
1681         errcode:0)
1682           eend 0;
1683           ;;
1684         errcode:1)
1685           eend 1
1686           ;;
1687         *)
1688           einfo "$line"
1689           ;;
1690       esac
1691     done
1692
1693     eoutdent
1694     IFS=$IFSOLD
1695   }
1696
1697   if checkbootparam 'dmraid' ; then
1698     local ACTION="$(getbootparam 'dmraid' 2>>$DEBUG)"
1699     if [ "$ACTION" = "off" ] ; then
1700       # Deactivates all active software RAID sets:
1701       einfo "Deactivating present dmraid sets (as requested via dmraid=off):"
1702       dmraid_wrapper -an
1703     else
1704       # Activate all software RAID sets discovered:
1705       einfo "Activating present dmraid sets (as requested via dmraid):"
1706       dmraid_wrapper -ay
1707     fi
1708
1709     return
1710   fi
1711
1712   # by default (no special bootoptions) discover all software RAID devices:
1713   einfo "Searching for any present dmraid sets:"
1714   dmraid_wrapper -r
1715 }
1716 # }}}
1717
1718 # {{{ LVM (Logical Volumes)
1719 config_lvm(){
1720   [ -n "$INSTALLED" ] && return 0
1721
1722   if checkbootparam 'nolvm' ; then
1723      ewarn "Skipping LVM code as requested on boot commandline." ; eend 0
1724   else
1725     if ! [ -x /sbin/lvm ] ; then
1726        eerror "LVM not available, can not execute it." ; eend 1
1727     else
1728        if lvdisplay 2>&1 | grep -v 'No volume groups found' >/dev/null 2>&1 ; then
1729           einfo "You seem to have logical volumes (LVM) on your system."
1730           eindent
1731           if $SYSTEMD ; then
1732             einfo "Just run 'Start lvm2-lvmetad' to activate them or boot using 'lvm' as bootoption for autostart."
1733           else
1734             einfo "Just run 'Start lvm2' to activate them or boot using 'lvm' as bootoption for autostart."
1735           fi
1736           eend 0
1737           if checkbootparam 'lvm' ; then
1738              einfo "Bootoption LVM found. Searching for logical volumes:"
1739              if $SYSTEMD ; then
1740                service_wrapper lvm2-lvmetad start ; eend $?
1741              else
1742                service_wrapper lvm2 start ; eend $?
1743              fi
1744           fi
1745           eoutdent
1746        fi
1747     fi # check for lvm binary
1748   fi # check for bootoption nolvm
1749 }
1750 # }}}
1751
1752 # {{{ debnet: setup network based on an existing one found on a partition
1753 config_debnet(){
1754 if checkbootparam 'debnet' ; then
1755  einfo "Bootoption 'debnet' found. Searching for Debian network configuration: "
1756  /usr/sbin/debnet
1757 fi
1758 }
1759 # }}}
1760
1761 # {{{ disable console blanking
1762 config_blanking(){
1763 if checkbootparam 'noblank' ; then
1764   einfo "Bootoption noblank found. Disabling monitor blanking."
1765   setterm -blank 0 ; eend $?
1766 fi
1767 }
1768 # }}}
1769
1770 # {{{ debootstrap: automatic installation
1771 config_debootstrap(){
1772
1773 if checkbootparam "BOOT_IMAGE=debian2hd" || checkbootparam "debian2hd" ; then
1774
1775 einfo "Bootoption debian2hd found. Setting up environment for automatic installation via grml-debootstrap." ; eend 0
1776
1777 if ! [ -x /usr/sbin/grml-debootstrap ] ; then
1778    eindent
1779    eerror "Bootoption debian2hd found, but grml-debootstrap is not available." ; eend 1
1780    eoutdent
1781    exit 1
1782 fi
1783
1784 if checkbootparam 'target' ; then
1785   TARGET=''
1786   TARGET="$(getbootparam 'target' 2>>$DEBUG)"
1787   # notice: the following checks whether the given partition is available, if not the skip
1788   # execution of grml-debootstrap as it might result in data loss...
1789   if ! [ -r "$TARGET" ] ; then
1790      eerror "Target $TARGET does not exist. Skipping execution of grml-debootstrap therefore." ; eend 1
1791   fi
1792 else
1793   eindent
1794   eerror "No bootoption named target found, can not continue execution of grml-debootstrap." ; eend 1
1795   eoutdent
1796   exit 1
1797 fi
1798
1799 if checkbootparam 'grub' ; then
1800   GRUB=''
1801   GRUB="$(getbootparam 'grub' 2>>$DEBUG)"
1802 fi
1803
1804 if checkbootparam 'groot' ; then
1805   GROOT=''
1806   GROOT="$(getbootparam 'groot' 2>>$DEBUG)"
1807 fi
1808
1809 if checkbootparam 'release' ; then
1810   RELEASE=''
1811   RELEASE="$(getbootparam 'release' 2>>$DEBUG)"
1812 fi
1813
1814 if checkbootparam 'mirror' ; then
1815   MIRROR=''
1816   MIRROR="$(getbootparam 'mirror' 2>>$DEBUG)"
1817 fi
1818
1819 if checkbootparam 'boot_append' ; then
1820   BOOT_APPEND=''
1821   BOOT_APPEND="$(getbootparam 'boot_append' 2>>$DEBUG)"
1822 fi
1823
1824 if checkbootparam 'password' ; then
1825   PASSWORD=''
1826   PASSWORD="$(getbootparam 'password' 2>>$DEBUG)"
1827 fi
1828
1829 # now check which options are available
1830 if [ -n "TARGET" ] ; then
1831    TARGETCMD="--target $TARGET"
1832 else
1833    TARGETCMD=''
1834    eindent
1835    eerror "Target not set via bootoption. Skipping execution of grml-debootstrap therefore."; eend 1
1836    eoutdent
1837    exit 1
1838 fi
1839 [ -n "$GRUB" ]     && GRUBCMD="--grub $GRUB"               || GRUBCMD=''
1840 [ -n "$GROOT" ]    && GROOTCMD="--groot $GROOT"            || GROOTCMD=''
1841 [ -n "$RELEASE" ]  && RELEASECMD="--release $RELEASE"      || RELEASECMD=''
1842 [ -n "$MIRROR" ]   && MIRRORCMD="--mirror $MIRROR"         || MIRRORCMD=''
1843 [ -n "$PASSWORD" ] && PASSWORDCMD="--password $PASSWORD"   || PASSWORDCMD=''
1844 [ -n "$BOOT_APPEND" ] && BOOT_APPEND="--boot_append $BOOT_APPEND" || BOOT_APPEND=''
1845
1846 # and finally write script and execute it
1847 cat>|/usr/bin/grml-debootstrap_noninteractive<<EOF
1848 #!/bin/sh
1849 AUTOINSTALL='yes' grml-debootstrap $TARGETCMD $GRUBCMD $GROOTCMD $RELEASECMD $MIRRORCMD $PASSWORDCMD $BOOT_APPEND
1850 EOF
1851
1852 chmod 750  /usr/bin/grml-debootstrap_noninteractive
1853
1854 screen /usr/bin/grml-debootstrap_noninteractive
1855 einfo "Invoking a shell, just exit to continue booting..."
1856 /bin/zsh
1857
1858 fi # checkbootparam "BOOT_IMAGE=debian2hd
1859 }
1860 # }}}
1861
1862 # {{{ virtualbox shared folders
1863 config_virtualbox_shared_folders() {
1864 if $VIRTUALBOX ; then
1865   einfo "VirtualBox detected, trying to set up Shared Folders."
1866   if ! modinfo vboxsf &>/dev/null ; then
1867     ewarn "vboxsf driver not present, not setting up VirtualBox Shared Folders."
1868     eend 0
1869   elif ! [ -x /usr/sbin/VBoxService ] ; then
1870     ewarn "virtualbox-guest-utils not installed, not setting up VirtualBox Shared Folders."
1871     eend 0
1872   else
1873     eindent
1874
1875       einfo "Loading vboxsf driver."
1876       lsmod | grep -q vboxsf || modprobe vboxsf
1877       eend $?
1878
1879       einfo "Adjusting /dev/vboxguest."
1880       chown root:vboxsf /dev/vboxguest
1881       chmod 660 /dev/vboxguest
1882       eend $?
1883
1884       config_userfstab
1885
1886       einfo "Adding $fstabuser to group vboxsf."
1887       adduser grml vboxsf &>/dev/null
1888       eend $?
1889
1890       einfo "Starting VBoxService."
1891       VBoxService >/dev/null
1892       eend $?
1893
1894       local vbautomation='automation'
1895       if checkbootparam 'vbautomation'; then
1896         vbautomation="$(getbootparam 'vbautomation' 2>>$DEBUG)"
1897       fi
1898
1899       if ! VBoxControl sharedfolder list | egrep -q "^[0-9]+ - ${vbautomation}$" ; then
1900         ewarn "No automount shared folder '$vbautomation' available"
1901         eend 0
1902       else
1903         einfo "Found automount shared folder '$vbautomation'"
1904         eend 0
1905
1906         local distri="$(getbootparam 'distri' 2>>$DEBUG)"
1907         [ -n "$distri" ] || distri='grml'
1908
1909         local vbox_auto_sf="/media/sf_${vbautomation}"
1910
1911         sleep 1 # ugly but necessary
1912
1913         counter=10
1914         eindent
1915         while ! [ -d "${vbox_auto_sf}" ] && [[ "$counter" != 0 ]]; do
1916           einfo "Waiting another second to retry access to ${vbox_auto_sf}"
1917           sleep 1
1918           counter=$(( counter-1 ))
1919           eend 0
1920         done
1921         eoutdent
1922
1923         if ! [ -d "${vbox_auto_sf}" ] ; then
1924           eerror "Giving up trying to access folder ${vbox_auto_sf} which doesn't seem to exist"
1925           eend 1
1926         else
1927           einfo "Found shared folders automation directory $vbox_auto_sf"
1928           eend 0
1929
1930           eindent
1931           if checkbootparam 'novbautomation' ; then
1932             einfo "Bootoption novbautomation found. Disabling automation script execution."
1933             eend 0
1934           else
1935             if ! [ -x "${vbox_auto_sf}/${distri}" ] ; then
1936               ewarn "Couldn't find an automation script named ${vbox_auto_sf}/${distri}"
1937               eend 1
1938             else
1939               einfo "Executing '${vbox_auto_sf}/${distri}' now:"
1940               "${vbox_auto_sf}/${distri}"
1941               eend $?
1942             fi
1943           fi
1944           eoutdent
1945         fi
1946       fi
1947
1948     eoutdent
1949   fi
1950 fi
1951 }
1952 # }}}
1953
1954 # {{{ Support customization
1955 config_distri(){
1956 if checkbootparam 'distri'; then
1957   DISTRI="$(getbootparam 'distri' 2>>$DEBUG)"
1958   if [ -r "${LIVECD_PATH}"/desktop/"$DISTRI".jpg ] ; then
1959      # make sure the desktop.jpg file is not a symlink, so copying does not file then
1960      [ -L /usr/share/grml/desktop.jpg ] && rm /usr/share/grml/desktop.jpg
1961      cp "${LIVECD_PATH}"/desktop/"$DISTRI".jpg /usr/share/grml/desktop.jpg
1962   fi
1963 fi
1964 }
1965 # }}}
1966
1967 ## END OF FILE #################################################################
1968 # vim:foldmethod=marker expandtab ai ft=zsh shiftwidth=2