#!/bin/sh
# shellcheck shell=dash

# Edited to boot squashfs
# Taken most parts from original init
VERSION=0.1.4 #based on alpine init 3.5.0-r0
sysroot=/sysroot
repofile=/tmp/repositories

if [ -z "$rootfs_net" ]; then
	echo "Variable \$rootfs_net not found! Executing /init_orig..."
	exec /init_orig
fi

quiet=${quiet:-no}

# some helpers
return_err() {
	echo "$*"
	echo "initramfs emergency recovery shell launched. Type 'exit' to continue boot"
	/bin/busybox sh
}
ebegin() {
	last_emsg="$*"
	echo "$last_emsg..." > /dev/kmsg
	[ "$quiet" = yes ] && return 0
	echo -n " * $last_emsg: "
}
eend() {
	if [ "$1" = 0 ] || [ $# -lt 1 ] ; then
		echo "$last_emsg: ok." > /dev/kmsg
		[ "$quiet" = yes ] && return 0
		echo "ok."
	else
		shift
		echo "$last_emsg: failed. $*" > /dev/kmsg
		if [ "$quiet" = "yes" ]; then
			echo -n "$last_emsg "
		fi
		return_err "failed. $*"
	fi
}
# find the dirs under ALPINE_MNT that are boot repositories
find_boot_repositories() {
	if [ -n "$ALPINE_REPO" ]; then
		echo "$ALPINE_REPO"
	else
		find /media/* -name .boot_repository -type f -maxdepth 3 \
			| sed 's:/.boot_repository$::'
	fi
}

# determine the default interface to use if ip=dhcp is set
# uses the first "eth" interface with operstate 'up'.
ip_choose_if() {
	if [ -n "$BOOTIF" ]; then
		mac=$(printf "%s\n" "$BOOTIF"|sed 's/^01-//;s/-/:/g')
		dev=$(grep -l "$mac" /sys/class/net/*/address|head -n 1)
		dev=${dev%/*}
		[ -n "$dev" ] && echo "${dev##*/}" && return
	fi
	for x in /sys/class/net/eth*; do
		if grep -iq up "$x/operstate"; then
			[ -e "$x" ] && echo "${x##*/}" && return
		fi
	done
	[ -e "$x" ] && echo "${x##*/}" && return
}

# Valid syntaxes:
#   ip=client-ip:server-ip:gw-ip:netmask:hostname:device:autoconf:
#     :dns0-ip:dns1-ip
#   ip=dhcp
configure_ip() {
	[ -n "$MAC_ADDRESS" ] && return

	IFS=':' set -- "${ip:-dhcp}"

	local client_ip="$1" gw_ip="$3" netmask="$4" device="$6" autoconf="$7" dns1="$8" dns2="$9"

	case "$client_ip" in
		off|none) return;;
		dhcp) autoconf="dhcp";;
	esac

	[ -n "$device" ] || device=$(ip_choose_if)

	[ -z "$device" ] && return_err "ERROR: IP requested but no network device was found"

	if [ "$autoconf" = "dhcp" ]; then
		[ ! -e /usr/share/udhcpc/default.script ] && return_err "ERROR: DHCP requested but not present in initrd"
		ebegin "Obtaining IP via DHCP ($device)"
		ifconfig "$device" 0.0.0.0
		udhcpc -i "$device" -f -q
		eend $?
	else
		[ -n "$client_ip" ] && [ -n "$netmask" ] || return
		ebegin "Setting IP ($device)"
		if ifconfig "$device" "$client_ip" netmask "$netmask"; then
			[ -z "$gw_ip" ] || ip route add 0.0.0.0/0 via "$gw_ip" dev "$device"
		fi
		eend $?
	fi

	# Never executes if variables are empty
	for i in $dns1 $dns2; do
		echo "nameserver $i" >> /etc/resolv.conf
	done

	MAC_ADDRESS=$(cat "/sys/class/net/$device/address")
}

is_url() {
	case "$1" in
	http://*|https://*|ftp://*)
		return 0;;
	*)
		return 1;;
	esac
}

/bin/busybox mkdir -p /usr/bin /usr/sbin /proc /sys /dev /tmp $sysroot
/bin/busybox --install -s
export PATH=/usr/bin:/bin:/usr/sbin:/sbin
[ -c /dev/null ] || mknod -m 666 /dev/null c 1 3
mount -t sysfs -o noexec,nosuid,nodev sysfs /sys
mount -t devtmpfs -o exec,nosuid,mode=0755,size=2M devtmpfs /dev 2>/dev/null \
	|| mount -t tmpfs -o exec,nosuid,mode=0755,size=2M tmpfs /dev
[ -c /dev/kmsg ] || mknod -m 660 /dev/kmsg c 1 11
mount -t proc -o noexec,nosuid,nodev proc /proc
[ -c /dev/ptmx ] || mknod -m 666 /dev/ptmx c 5 2
[ -d /dev/pts ] || mkdir -m 755 /dev/pts
mount -t devpts -o gid=5,mode=0620,noexec,nosuid devpts /dev/pts
[ -d /dev/shm ] || mkdir /dev/shm
mount -t tmpfs -o nodev,nosuid,noexec shm /dev/shm
set -- "$(cat /proc/cmdline)"
echo "Linux_install Init $VERSION"

ebegin "Loading boot drivers"
modprobe -a "$(echo "${rootfstype:-}" | tr ',' ' ' )" loop squashfs 2> /dev/null
eend 0

ln -s /proc/mounts /etc/mtab

echo "rootfs_net=[${rootfs_net}]" > /dev/kmsg

ebegin "Mounting boot media"
if ! is_url "$rootfs_net"; then
	find_boot_repositories > $repofile
	nlplug-findfs -p /sbin/mdev -b $repofile -a /tmp/apkovls
else
	nlplug-findfs -p /sbin/mdev -n
	echo -n "skip - "
fi
eend $?

overlayfs="/media"
mkdir -p $overlayfs/root-rw
mount -t tmpfs root-tmpfs $overlayfs/root-rw
mkdir -p $overlayfs/root-ro $overlayfs/root-rw/root $overlayfs/root-rw/work

if is_url "$rootfs_net"; then
    configure_ip || return_err "Failed to setup network."
	wget -O $overlayfs/root-rw/squashfs.img "$rootfs_net"
	ebegin "Mounting rootfs"
	mount -o loop,ro $overlayfs/root-rw/squashfs.img $overlayfs/root-ro
	mount -t overlay -o lowerdir=$overlayfs/root-ro,upperdir=$overlayfs/root-rw/root,workdir=$overlayfs/root-rw/work LIVE_OS $sysroot
	eend $?
else
	ebegin "Mounting rootfs"
	repo_dir=$(head -n 1 $repofile)
	if [ -f "$repo_dir/$rootfs_net" ]; then
		mount -o loop,ro "$repo_dir/$rootfs_net" $overlayfs/root-ro
		mount -t overlay -o lowerdir=$overlayfs/root-ro,upperdir=$overlayfs/root-rw/root,workdir=$overlayfs/root-rw/work LIVE_OS $sysroot
	fi
	eend $?
fi
: "${init:=/sbin/init}"
if [ -f $sysroot/$init ]; then
	[ -f /etc/resolv.conf ] && cp /etc/resolv.conf $sysroot/etc/resolv.conf
	ebegin "Preparing to switch root"
	#shellcheck disable=SC2034
	while read -r DEV DIR TYPE OPTS; do
		if [ "$DIR" != "/" ] && [ "$DIR" != "$sysroot" ] && [ -d "$DIR" ]; then
			mkdir -p "$sysroot/$DIR"
			mount -o move "$DIR" "$sysroot/$DIR"
		fi
	done < /proc/mounts
	sync
	if [ -e "$sysroot/proc/cmdline" ]; then
		cmdline="$(cat $sysroot/proc/cmdline)"
	else
		cmdline="$(cat /proc/cmdline)"
	fi
	eend 0
	ebegin "exec /bin/busybox switch_root sysroot=[$sysroot] init=[$init] cmdline=[$cmdline]"
	exec /bin/busybox switch_root $sysroot $init "$cmdline"
else
    echo "File $sysroot/$init does not exist!"
fi


return_err "Unexpected end"
reboot
