#!/bin/sh

# fiasco-image-update: schedule FIASCO images for flashing
# For every image that contains bits of cmt firmware, stage it
# for later (post-reboot or whatnot) flashing; for every image
# that does NOT contain cmt, proceed to flashing immediately.

# Scheduled updates are to be stored here:
STAGING_DIR=/var/lib/softupd/staging

# Command to actually flash images
CMD_DO_FLASH="/usr/bin/flasher --local -f -F"
# Command to used to obtain list of FIASCO image contents
CMD_FLASHER_LIST="/usr/bin/flasher -F"

# set -e

usage() {
	cat<<FIASCO
Usage:
	$(basename $0) [-h][-v] IMAGE [IMAGE] ...
FIASCO
}

say() {
	if [ -n "$verbose" ]; then
		echo "$*"
	fi
}

stage_one_image() {
	__image="$1"
	__path="$STAGING_DIR/$(basename $__image)"

	if [ -e "$__path" ]; then
		echo "Warning: $__path already exists;"
		echo "which means $__image was already scheduled for flashing once."
		rm -f "$__path"
	fi

	ln -sf "$__image" "$__path"
}

# In case staging directory is not a directory
if [ -e "$STAGING_DIR" -a ! -d "$STAGING_DIR" ]; then
	rm -rf "$STAGING_DIR"
fi

if [ ! -d "$STAGING_DIR" ]; then
	mkdir -p "$STAGING_DIR"
fi

# process command line arguments
while [ -n "$1" ]; do
	case "$1" in
		-h)
			usage
			exit 0
			;;
		-v)
			verbose=1
			;;
		-*)
			echo "More options to come"
			usage
			exit 1
			;;
		*)
			if [ -z "$images" ]; then
				images="$1"
			else
				images="$images $1"
			fi
			;;
	esac
	shift
done

if [ -z "$images" ]; then
	echo "Kindly supply at least one image. Thank you."
	usage
	exit 1
fi

# process images
for i in $images; do
	# basic sanity checks
	if [ "${i#/}" = "$i" ]; then
		echo "$i is not an absolute path, skipping"
		continue
	fi

	if [ ! -e "$i" ]; then
		echo "$i does not exist, skipping"
		continue
	fi

	say "Processing image: $i"

	# Check the image to be a valid FIASCO
	if $CMD_FLASHER_LIST "$i" 2>&1 | grep "^Invalid FIASCO file header" >/dev/null; then
		echo "   -> not a valid FIASCO image, skipping"
		continue
	fi

	# Check for CMT content
	if $CMD_FLASHER_LIST "$i" 2>/dev/null | grep "^Image 'cmt-" >/dev/null; then
		say "   -> contains cmt, scheduling for later flashing"
		stage_one_image $i
	else
		say "   -> doesn't contain cmt, flashing right away"
		if [ -z "$images_to_flash" ]; then
			images_to_flash="$i"
		else
			images_to_flash="$images_to_flash $i"
		fi
	fi
done

if [ -n "$images_to_flash" ]; then
	# we have to make sure the proper version of softupd is running
	# before calling flasher
	initctl stop softupd

	/usr/sbin/softupd --local --standalone -v -s &
	su_pid=$!
	sleep 1

	for i in $images_to_flash; do
		$CMD_DO_FLASH $i || \
			( echo "Flashing $i failed" && kill $su_pid; exit 1 )
		rm -f $i
	done

	kill $su_pid || echo "Problem: softupd died too soon"
	wait $su_pid
fi

