#!/bin/bash
#
# Copyright (C) 2017 Jason Graham <jgraham@compukix.net>
#
# Copying and distribution of this file, with or without modification,
# are permitted in any medium without royalty provided the copyright
# notice and this notice are preserved.  This file is offered as-is,
# without any warranty.
# 
# Creates a LUKS encrypted ISO formated file
#
# Usage: mkisofs-luks [mkisofs-options] FILE...
#
# Date:
#   2017-10-15
#

CRYPTFS_SIZE=4194304 # bytes
TMP_ISOFS=/tmp/.isofs
CRYPT_FILE=/tmp/.isoluks
CRYPT_NAME=isoluks
CRYPT_DEV=/dev/mapper/$CRYPT_NAME

ISOFS=/dev/stdout
SUDO=sudo

function cleanup {
    set +eE

    # Remove the generated temporary ISO file
    [[ -f $TMP_ISOFS ]] && shred -u -n 27 $TMP_ISOFS

    # Close the encrypted device if present
    [[ -e $CRYPT_DEV ]] && \
	$SUDO /sbin/cryptsetup luksClose $CRYPT_NAME

    # Detach the loop device from the encrypted ISO file
    [[ ! -z $(/sbin/losetup -j $CRYPT_FILE) ]] && \
	$SUDO /sbin/losetup -d $loopdev

    # Remove the encrypted ISO file (forcefully)
    rm -f $CRYPT_FILE
}

function cleanup_and_exit {
    echo "Error caught"
    cleanup
    exit 1
}

# Find the output flag
ARGV=""

while (( $# > 0 ))
do
    case $1 in
	-o)
	    shift 1
	    ISOFS="${1}.luks"
	    ;;
	-*)
	    ARGV="${ARGV} $1"
	    ;;
	*)
	    # The rest are input files
	    break
	    ;;
    esac
    shift 1	
done

[[ $UID == 0 ]] && SUDO=""

# Make sure sudo works
$SUDO /bin/true
rc=$?
[[ $rc != 0 ]] && exit $rc

set -eE  # same as: `set -o errexit -o errtrace`
trap "cleanup_and_exit" ERR INT TERM

mkisofs $ARGV -o $TMP_ISOFS "$@"
isofs_size=$(( $(ls --block-size=M -s $TMP_ISOFS | cut -d'M' -f1) * 1024*1024 + CRYPTFS_SIZE ))

num_blocks=$(( ( isofs_size + 4095 ) / 4096 ))
dd if=/dev/urandom of=$CRYPT_FILE bs=4096 count=$num_blocks

# Attach the encrypted ISO file to a loop device
loopdev=$(/sbin/losetup -f)
$SUDO /sbin/losetup $loopdev $CRYPT_FILE

# Encrypt the ISO file backed loop device
$SUDO /sbin/cryptsetup luksFormat -c aes -s 256 -h sha256 -y $loopdev
$SUDO /sbin/cryptsetup luksOpen $loopdev $CRYPT_NAME

# Copy the mkisofs generated ISO file to the encrypted ISO file backed crypt device
$SUDO dd if=$TMP_ISOFS of=$CRYPT_DEV bs=512

# Copy the encrypted ISO file to the output
$SUDO cat $CRYPT_FILE > $ISOFS

cleanup
exit 0




	
