#!/bin/sh
############################################################
# <bsn.cl fy=2013 v=onl>
# 
#        Copyright 2013, 2014 BigSwitch Networks, Inc.        
# 
# Licensed under the Eclipse Public License, Version 1.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
# 
#        http://www.eclipse.org/legal/epl-v10.html
# 
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the
# License.
# 
# </bsn.cl>
############################################################
#
# switchroot
#
# This script is a wrapper for busybox switch_root, which works only if:
# - executed as PID 1 (i.e. replacing init)
# - /init is a regular file
# - /newroot is a tmpfs or ramfs
# - /newroot is a different filesystem from /
#
# The only way to execute as PID 1 with busybox init is to invoke it via
# the restart action in the inittab.
#
############################################################

# Unmount all filesystems except / and anything under /newroot
mtab=$(mktemp /tmp/tmp.XXXXXX)
cp /proc/mounts ${mtab}
while read dev mount x; do
    case "${mount}" in
	/|/proc|/sys|/dev|/newroot|/newroot/*)
	    ;;
	*)
            rm -f "${mount}".conf
            umount -l "${mount}" 2>/dev/null
	    ;;
    esac
done <${mtab}
rm -f ${mtab}

mount --move /proc /newroot/proc
if [ -d /sys/firmware/efi/efivars ]; then
    umount /sys/firmware/efi/efivars || :
fi
mount --move /sys /newroot/sys
if [ -d /newroot/sys/firmware/efi/efivars ]; then
    modprobe efivarfs || :
    mount -t efivarfs efivarfs /newroot/sys/firmware/efi/efivars
fi
mount --move /dev /newroot/dev

# Switch to /newroot if possible, else re-execute /init
if [ -x /newroot/sbin/init ]; then
    exec switch_root -c /dev/console /newroot /sbin/init
elif [ -x /newroot/lib/systemd/systemd ]; then
    exec switch_root -c /dev/console /newroot /lib/systemd/systemd
else
    exec /init
fi

# Local variables:
# sh-indentation: 4
# sh-basic-offset: 4
# End:
