#!/bin/bash
# -*- coding: utf-8-unix -*-

Usage_C(){
    cat<<EOF
Usage:	$(basename $0) {--version [version]} {--arch [arch]} {--with-compat32} {--build|--clean|--build-rpm [src.rpm]|--install-rpm [arch.rpm|package]|--remove-rpm [package]}
	--version:		set [version] (default: ${DEFAULT_VERSION})
	--arch:			set [arch] (default: $(uname -i))
	--with-compat32:	build with compat32 on boostrap
	--clean:		clean boostrap of [version]
	--build:		build boostrap of [version]
	--build-rpm:		build [src.rpm] on boostrap
	--install-rpm:		install [arch.rpm|package] on boostrap
	--remove-rpm:		remove [package] on boostrap

For example, 
* make a clean/plain build environment on the current archtecture:
$(basename $0) --clean --build
* build source RPM:
$(basename $0) --build-rpm [src.rpm]
* make a plain build environment for Vine Linux 4.2:
$(basename $0) --version 4.2 --clean --build
* make a i386 chroot on x86_64:
$(basename $0) --arch i386 --clean --build
* build compat32:
$(basename $0) --arch i386 --with-compat32 --build-rpm [src.rpm]
$(/usr/sbin/vbootstrap | sed -e s/^Usage:.*// -e s/^E:.*//)
EOF
}

Usage_ja(){
    Usage_C
}

Msg_MissingParameter_C(){
    while read para; do
	cat<<EOF
E: Missing some parameter before ${para}
EOF
    done
}

Msg_MissingParameter_ja(){
    Msg_MissingParameter_C
}

Msg_NoSupportVARCH_C(){
    cat<<EOF
E: arch ${VARCH} is NO support on $(uname -i)
EOF
}

Msg_NoSupportVARCH_ja(){
    Msg_NoSupportVARCH_C
}

Msg_NoSupportVERSION_C(){
    cat<<EOF
E: version ${VERSION} is NO support
EOF
}

Msg_NoSupportVERSION_ja(){
    Msg_NoSupportVERSION_C
}

##############################################################################

setup-vbuilder(){
    ## load default settings
    if [ -r /etc/vbootstrap/vbuilder.conf ]; then
	. /etc/vbootstrap/vbuilder.conf
    fi
    [ -z "${VBOOTSTRAP_DIR}" ] && \
	VBOOTSTRAP_DIR=@@VBUILDER_VBOOTSTRAP_DIR@@
    [ -z "${DEFAULT_VERSION}" ] && \
	DEFAULT_VERSION=@@VBUILDER_DEFAULT_VERSION@@
    [ -z "${BUILT_RPMS_DIR}" ] && \
	BUILT_RPMS_DIR=@@VBUILDER_BUILT_RPMS_DIR@@
    [ -d $VBOOTSTRAP_DIR ] || mkdir -p $VBOOTSTRAP_DIR
    VERSION=$DEFAULT_VERSION

    ## set locale
    case $LANG in
	ja*)  LOCALE=ja ;;
	*)    LOCALE=C ;;
    esac
}

check-next-parameter(){
    while read arg; do
	if [ $(echo ${arg} | grep '^-') ]; then
	    echo ${arg} | Msg_MissingParameter_$LOCALE
	    return 1
	fi
    done
}

FLAG_setup_vbootstrap=0
setup-vbootstrap(){
    if [ ${FLAG_setup_vbootstrap} -eq 0 ]; then
	FLAG_setup_vbootstrap=1

	## check a chroot archtecture
	if [ ! -z ${VARCH} ]; then
	    case "${VARCH}" in
		i386)
		    [ "$(uname -i)" = "ppc" ] && \
			Msg_NoSupportVARCH_$LOCALE
		    [ $? -eq 0 ] && exit 1
		    ;;
		x86_64)
		    [ "$(uname -i)" = "ppc" ] && \
			Msg_NoSupportVARCH_$LOCALE
		    [ $? -eq 0 ] && exit 1
		    ;;
		ppc)
		    [ "$(uname -i)" = "i386" -o "$(uname -i)" = "x86_64" ] && \
			Msg_NoSupportVARCH_$LOCALE
		    [ $? -eq 0 ] && exit 1
		    ;;
	    esac
	fi

	[ -z ${VARCH} ] && VARCH=$(uname -i)

	##!! IRREGULAR: 4.2 is NO support on x86_64
	if [ "${VERSION}" = "4.2" -a "$(uname -i)" = "x86_64" ]; then
	    Msg_NoSupportVERSION_${LOCALE}
	    exit 1
	fi

	## support for i386 chroot on x86_64 below: 
	[ "${VARCH}" != "$(uname -i)" ] && VERSION=${VERSION}_${VARCH}

        ## check support ${VERSION}
	if [ -z "$(/usr/sbin/vbootstrap | sed -e s/^Usage:.*// -e s/^E:.*// | grep -m 1 ${VERSION})" ]; then
	    Msg_NoSupportVERSION_$LOCALE
	    exit 1
	fi

    fi

    BUILD_ROOT=${VBOOTSTRAP_DIR}/${VERSION}
    BUILD_USER=vbuilder
    CACHE_DIR=${VBOOTSTRAP_DIR}/cache/${VERSION}
    BUILD_DIR=/home/${BUILD_USER}/rpm

    mkdir -p $VBOOTSTRAP_DIR
}

##############################################################################

Clean(){
    setup-vbootstrap

    [ -d ${BUILD_ROOT}/proc ] && \
	umount ${BUILD_ROOT}/proc

    if [ -d ${BUILD_ROOT}/var/cache/apt/archives ]; then
	echo -n "Caching RPMs in ${CACHE_DIR}/apt/archives ... "
	[ -d ${CACHE_DIR}/apt/archives ] || mkdir -p ${CACHE_DIR}/apt/archives
	mv -f ${BUILD_ROOT}/var/cache/apt/archives/*.rpm ${CACHE_DIR}/apt/archives/
	echo "done."
    fi

    if [ -d ${BUILD_ROOT} ]; then
	echo -n "Cleaning build root \"${BUILD_ROOT}\" ... "
	rm -rf ${BUILD_ROOT}
	echo "done."
    fi
}

Build(){
    setup-vbootstrap

    /usr/sbin/vbootstrap ${VERSION} ${BUILD_ROOT}

    [ -d ${BUILD_ROOT}/proc ] || mkdir -p ${BUILD_ROOT}/proc
    mount -t proc proc ${BUILD_ROOT}/proc

    # ## mount /tmp with --bind option
    # mount --bind /tmp ${BUILD_ROOT}/tmp

    if [ -d ${CACHE_DIR} ]; then
	echo -n "Copying cached RPMs to ${BUILD_ROOT}/var/cache/apt/archives ... "
	cp -f ${CACHE_DIR}/apt/archives/*.rpm ${BUILD_ROOT}/var/cache/apt/archives/
	echo "done."
    fi

    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c 'apt-get update && apt-get -y dist-upgrade'
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c 'apt-get -y install apt-sourceslist-plus && apt-get update'
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c 'apt-get -y install apt-sourceslist-nonfree && apt-get update'
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c 'apt-get -y install build-essential self-build-setup'
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c 'apt-get -y install etcskel shadow-utils'

    /usr/sbin/chroot ${BUILD_ROOT} /bin/sh -c 'cd /dev && /sbin/MAKEDEV console'
    /usr/sbin/chroot ${BUILD_ROOT} /bin/sh -c 'cd /dev && /sbin/MAKEDEV null'
    /usr/sbin/chroot ${BUILD_ROOT} /bin/sh -c 'cd /dev && /sbin/MAKEDEV zero'
    
    /usr/sbin/chroot ${BUILD_ROOT} /bin/sh -c '/usr/sbin/pwconv'
    /usr/sbin/chroot ${BUILD_ROOT} /bin/sh -c "/usr/sbin/useradd ${BUILD_USER}"

    echo "Making a build farm for ${VERSION} done."
}

setup-vbootstrap-rpm(){
    setup-vbootstrap

    ## check ${BUILD_ROOT}
    [ -d ${BUILD_ROOT} ] || Build

    if [ -f $RPM_PKG ]; then
	BASE_RPM_PKG=$(basename $RPM_PKG)
	cp -f $RPM_PKG $BUILD_ROOT${BUILD_DIR}
    else
	BASE_RPM_PKG=$RPM_PKG	
    fi
}

RPM_Remove(){
    setup-vbootstrap-rpm

    if [ -f $RPM_PKG ]; then
	echo "$RPM_PKG: not package name."
	exit 1
    fi
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c "apt-get -y remove $BASE_RPM_PKG"
}

RPM_Install(){
    setup-vbootstrap-rpm

    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c "cd ${BUILD_DIR} && apt-get -y install $BASE_RPM_PKG"
}

RPM_Build(){
    setup-vbootstrap-rpm

    if [ ! -f $RPM_PKG ]; then
	echo "$RPM_PKG: not source RPM package."
	exit 1
    fi
    
    RPM_PKG_USER=$(stat -c %U $RPM_PKG)
    local __install="install -p -v -o ${RPM_PKG_USER} -g ${RPM_PKG_USER}"
    RPM_PKG_ARCH_LIST="RPMS/i386 RPMS/x86_64 RPMS/ppc RPMS/noarch SRPMS"

    /usr/sbin/chroot ${BUILD_ROOT} \
    	/bin/sh -c "cd ${BUILD_DIR} && apt-get -y build-dep $BASE_RPM_PKG"
    /usr/sbin/chroot ${BUILD_ROOT} \
    	/bin/sh -c "cd ${BUILD_DIR} && su ${BUILD_USER} -c 'rpmbuild --rebuild $RPM_OPTS $BASE_RPM_PKG'"
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c "cd ${BUILD_DIR} && apt-get -y install $(find $BUILD_ROOT${BUILD_DIR}/RPMS -type f -regex '.*\.rpm' | sed -e s@${BUILD_ROOT}@@g -e 's|.*\/compat32-.*||g' -e 's|.*\/.*\.src\.rpm||g' -e 's/$/ \\/g')"

    ## make src.rpm for $VERSION
    /usr/sbin/chroot ${BUILD_ROOT} \
    	/bin/sh -c "cd ${BUILD_DIR} && su ${BUILD_USER} -c 'rpm -ivh $BASE_RPM_PKG'"
    /usr/sbin/chroot ${BUILD_ROOT} \
	/bin/sh -c "cd ${BUILD_DIR} && su ${BUILD_USER} -c 'rpmbuild -bs --nodeps --clean --rmsource --rmspec ${BUILD_DIR}/SPECS/*.spec'"

    ## copy built rpms to ${HOME}/rpm/ for each archtectures
    echo "Copying built rpms to ${HOME}/rpm/ for each archtectures ... "
    for i in $RPM_PKG_ARCH_LIST; do \
	if [ -d $BUILD_ROOT${BUILD_DIR}/${i} ]; then
	    [ -d ${BUILT_RPMS_DIR}/${i} ] || \
		$__install -d ${BUILT_RPMS_DIR}/${i}/
	    find $BUILD_ROOT${BUILD_DIR}/${i} -type f -regex '.*\.rpm' \
		-exec $__install -m0644 {} ${BUILT_RPMS_DIR}/${i}/ \;
	fi
    done
    echo "done."
}


##############################################################################

setup-vbuilder

[ $# -eq 0 ] && Usage_$LOCALE
while [ $# -gt 0 ]; do
    case "$1" in
	--version)
	    shift;
	    echo $1 | check-next-parameter
	    [ $? -eq 1 ] && exit 1
	    VERSION=$1
	    ;;
	--arch)
	    shift;
	    echo $1 | check-next-parameter
	    [ $? -eq 1 ] && exit 1
	    VARCH=$1
	    ;;
	--with-compat32)
	    RPM_OPTS="--with compat32"
	    ;;
	--build-rpm)
	    shift;
	    echo $1 | check-next-parameter
	    [ $? -eq 1 ] && exit 1
	    RPM_PKG=$1
	    RPM_Build
	    ;;
	--install-rpm)
	    shift;
	    echo $1 | check-next-parameter
	    [ $? -eq 1 ] && exit 1
	    RPM_PKG=$1
	    RPM_Install
	    ;;
	--remove-rpm)
	    shift;
	    echo $1 | check-next-parameter
	    [ $? -eq 1 ] && exit 1
	    RPM_PKG=$1
	    RPM_Remove
	    ;;
	--build)
	    Build
	    ;;
	--clean)
	    Clean
	    ;;
	*)
	    Usage_$LOCALE
	    exit 1
	    ;;
    esac
    shift
done

exit