#!/bin/sh
#
#
# chkconfig: 345 12 05
# description: This startup script search and mount volumes with encrypted home directories


WITHOUT_RC_COMPAT=1

# Source function library.
. /etc/init.d/functions

RETVAL=0

MNT_PREFIX="/mnt"
UDEVADM="/sbin/udevadm"
MOUNT_OPTIONS_VFAT="users,noatime,codepage=866,shortname=winnt,iocharset=utf8,gid=0100,fmask=111,dmask=0000"
MOUNT_OPTIONS_NTFS3G="users,locale=ru_RU.utf8,gid=100,fmask=111,force,dmask=000" # force
MOUNT_OPTIONS_OTHER="users"
PAM_ENCFS="/etc/security/pam_encfs"
PAM_ENCFS_SUF=".conf"
SAVE_SUF=".livecd-encfs-save"

log()
{
    initlog $INITLOG_ARGS -n $0 -s "$1"
    return 0
}

start()
{
    msg_starting  $"a search for volumes for encFS configuration files"

    if ! [ -f "$PAM_ENCFS$PAM_ENCFS_SUF" ]; then
      cat - <<EOF > "$PAM_ENCFS$PAM_ENCFS_SUF"
drop_permissions
fuse_default allow_root,nonempty
EOF
    fi

    log "Backup $PAM_ENCFS$PAM_ENCFS_SUF"
    cp $PAM_ENCFS$PAM_ENCFS_SUF $PAM_ENCFS$SAVE_SUF

    blkid -o value -s UUID | while read uuid; do
        dev="$(blkid -o device -l -t UUID="$uuid")"

        if [ -z "$dev" ]; then
            log "Ignore bogus device with UUID=$uuid"
            continue
        fi

        if echo "$dev" | grep -q -s -e 'dm-' -e 'evms'; then
            log "Ignore $dev: device mapper or raid chunks"
            continue
        fi

        if grep -q -e "$dev" /proc/mounts; then
            log "Ignore $dev: already mounted"
            continue
        fi

        udev_info=$("$UDEVADM" info --query=all --name="$dev" 2>/dev/null)
        if [ -z "$udev_info" ]; then
            log "Ignore $dev: can't get partition info from udev database"
            continue
        fi

        fstype="$(echo "$udev_info" | grep "ID_FS_TYPE" | sed -n "s/.*ID_FS_TYPE=//p")"
        if [ -z "$fstype" ]; then
            log "$Ignore $dev: unknown ID_FS_TYPE"
            continue
        fi

        case "$fstype" in
            "mdraid" )
            log "Ignore $dev: mdraid"
            continue
            ;;
            "swsuspend" | "suspend")
            log "Ignore $dev: in suspend mode"
            continue
            ;;
            "swap")
            log "Ignore $dev: swap"
            continue
            ;;
            "vfat")
            mnt_options="$MOUNT_OPTIONS_VFAT"
            ;;
            "ntfs")
            mnt_options="$MOUNT_OPTIONS_NTFS3G"
            fstype="ntfs-3g"
            ;;
            *)
            mnt_options="$MOUNT_OPTIONS_OTHER"
        esac

        vol="$(basename $dev)"
        mnt_point="$MNT_PREFIX/$vol"
        mkdir -p "$mnt_point"
        mount "$dev" "$mnt_point" -t "$fstype" -o "$mnt_options"
        log "Examine $dev"
        rm -f $PAM_ENCFS.${vol}$PAM_ENCFS_SUF
        log "Search for $mnt_point/*/.encfs6.xml"
        ls -1 $mnt_point/*/.encfs6.xml 2>/dev/null | \
          while read f; do
            log "Found $f"
            tail="${f#${mnt_point}/*}"
            home="${f%%/.encfs6.xml}"
            username="${tail%%/.encfs6.xml}"
            if id "$username" >/dev/null 2>&1; then
              log "Found user $username"
              if [ "$fstype" != "vfat" ]; then
                chown $username:$username "$home"
              fi
              sed -e "\\%^$username .* /home/$username% d" \
                $PAM_ENCFS$PAM_ENCFS_SUF > \
                $PAM_ENCFS.${vol}$PAM_ENCFS_SUF
              echo "$username  $home  /home/$username  -v  allow_root" \
                >> $PAM_ENCFS.${vol}$PAM_ENCFS_SUF
              log "Add $home"
            fi
          done
        if [ -r "$PAM_ENCFS.${vol}$PAM_ENCFS_SUF" ]; then
          mv $PAM_ENCFS.${vol}$PAM_ENCFS_SUF \
            $PAM_ENCFS$PAM_ENCFS_SUF
        else
          while ! umount "$mnt_point"; do
            log "Waiting for $mnt_point release"
            sleep 1
          done
          log "Umount $mnt_point"
        fi

    done

    success
    echo

    return 0
}

stop()
{
    if [ -f "$PAM_ENCFS$SAVE_SUF" ]; then
      sed -n -e "s/^\(.\+\)  \(.\+\)  \(.\+\)  -v  allow_root/\2/p" \
        "$PAM_ENCFS$PAM_ENCFS_SUF" | \
        while read m; do
          d="$(dirname $m)"
          umount "$d" 2>/dev/null && log "Umount $d"
        done
      log "Restore $PAM_ENCFS$PAM_ENCFS_SUF"
      mv $PAM_ENCFS$SAVE_SUF $PAM_ENCFS$PAM_ENCFS_SUF
    fi
}

case "$1" in
    start)
      start
        ;;
    stop|condstop)
      stop
      ;;
    status)
        ;;
    restart|reload|condrestart|condreload)
        stop
        start
        ;;
    *)
        msg_usage "${0##*/} {start|stop|reload|restart|condstop|condrestart|condreload|status}"
        RETVAL=1
esac

exit $RETVAL
