#!/bin/sh
set -e
cd $(dirname "$0")

# There are four ways, in order of priority, that the Gerbil build may
# get version information:

#    1) the config arg `--version-string=<version>`
#    2) the git tag description if .git exists
#    3) a GERBIL_VERSION env var
#    4) a newly generated $GERBIL_RELEASE-<timestamp>

gerbil_version_string=''
gerbil_version() {
	if [ -n "$gerbil_version_string" ] ;
	then
		echo $GERBIL_VERSION_STRING
	elif [ -d ".git" ] ;
	then
		git describe --tags --always;
	elif [ -n "$GERBIL_VERSION" ];
	then
		echo $GERBIL_VERSION
	else
		local ts=$(date -Iseconds| sed 's/[-| |:]//g')
		echo ${GERBIL_RELEASE:-"v18.2"}-$ts
	fi
}


die() {
  echo "configuration failed"
  exit 1
}

usage() {
    local gambit_config_help="$(cd src/gambit && ./configure --help | tail -n +63)"

    cat <<EOF
This script configures the Gerbil and integrated Gambit build.

Usage: $0 [option] ... [var=value]...

Options controlling integrated Gambit configuration:
${gambit_config_help}

Options understood and processed by Gerbil:
  --prefix=PREFIX       where to install Gerbil; default prefix is /opt/gerbil
  --with-gambit=TAG     integrated gambit git tag to check out for the build;
                        defaults to ${default_gambit_tag}
  --enable-march=ARCH   specify the machine architecture; it can be empty.
                        defaults to native
  --enable-shared[=no]  do (not) use shared libraries for libgerbil and libgambit
  --disable-shared      default is to enable shared libraries

Gerbil Standard Library features:
  --enable-deprecated   Enable building of deprecated packages; disabled by default
  --enable-zlib         Enable or disable zlib support; enabled by default
  --disable-zlib
  --enable-sqlite       Enable or disable sqlite support; enabled by default
  --disable-sqlite

Default integrated Gambit configuration: ${default_gambit_config}
EOF
}


std_patch_feature() {
    sed -i -e "$1" src/std/build-features.ss
}

std_enable_feature() {
    std_patch_feature "s/$1 #f/$1 #t/"
}

std_disable_feature() {
    std_patch_feature "s/$1 #t/$1 #f/"
}

package_out_of_tree() {
    local pkg="$1"
    echo "*** ERROR package ${pkg} has been moved out of the master Gerbil tree"
    echo "It is now available as an external package: github.com/mighty-gerbils/gerbil-${pkg}"
}

readonly gerbil_targets=""
readonly default_gambit_tag=64f4d369f84299bc5d1086838347789a55f9cde1
readonly default_gambit_config="--enable-targets=${gerbil_targets} --enable-single-host --enable-dynamic-clib --enable-default-runtime-options=tE8,f8,-8 --enable-trust-c-tco"
prefix="/opt/gerbil"
readonly cflags_opt="-foptimize-sibling-calls"
readonly ldflags_rpath="-Wl,-rpath"

if [ $(uname) = "Darwin" ];
then
    readonly rpath_sep=","
else
    readonly rpath_sep="="
fi

case $(uname) in
    OpenBSD)
        gambit_march=""
        ;;
    *)
        gambit_march="native"
        ;;
esac

gerbil_shared=f
gambit_tag="${default_gambit_tag}"
gambit_config="${default_gambit_config}"
gambit_shared="--disable-shared"

while [ $# -gt 0 ]; do
    case "$1" in
        --help)
            usage
            exit 0
            ;;
        
        --version-string=*)
			gerbil_version_string=$(echo "$1" | cut -d = -f 2-)
            shift
            ;;
 
        --prefix=*)
            prefix=$(echo "$1" | cut -d = -f 2-)
            shift
            ;;

        --with-gambit=*)
            gambit_tag=$(echo "$1" | cut -d = -f 2-)
            shift
            ;;

        --enable-march=*)
            gambit_march=$(echo "$1" | cut -d = -f 2-)
            shift
            ;;

        --enable-shared)
            gerbil_shared=t
            gambit_shared="--enable-shared"
            shift
            ;;

        --disable-shared|--enable-shared=no)
            gerbil_shared=f
            gambit_shared="--disable-shared"
            shift
            ;;

        --enable-deprecated)
            std_enable_feature deprecated
            shift
            ;;

        --enable-zlib)
            std_enable_feature zlib
            shift
            ;;

        --disable-zlib)
            std_disable_feature zlib
            shift
            ;;

        --enable-sqlite)
            std_enable_feature sqlite
            shift
            ;;

        --disable-sqlite)
            std_disable_feature sqlite
            shift
            ;;

        --*-libxml)
            package_out_of_tree libxml
            exit 42
            ;;

        --*-libyaml)
            package_out_of_tree libyaml
            exit 42
            ;;

        --*-mysql)
            package_out_of_tree mysql
            exit 42
            ;;

        --*-lmdb)
            package_out_of_tree lmdb
            exit 42
            ;;

        --*-leveldb)
            package_out_of_tree leveldb
            exit 42
            ;;

        CFLAGS=*)
            flags=$(echo "$1" | cut -d = -f 2-)
            if [ -z "$CFLAGS" ]; then
                CFLAGS="$flags"
            else
                CFLAGS="$CFLAGS $flags"
            fi
            shift
            ;;

        LDFLAGS=*)
            flags=$(echo "$1" | cut -d = -f 2-)
            if [ -z "${LDFLAGS}" ]; then
                LDFLAGS="${flags}"
            else
                LDFLAGS="${LDFLAGS} ${flags}"
            fi
            shift
            ;;
        *)
            gambit_config="${gambit_config} $1"
            shift
        ;;
    esac
done

readonly gerbil_version="$(gerbil_version)"
gerbil_prefix="${prefix}/${gerbil_version}"

if [ -z "${CFLAGS}" ]; then
    CFLAGS="${cflags_opt}"
else
    CFLAGS="${CFLAGS} ${cflags_opt}"
fi
if [ -z "${LDFLAGS}" ]; then
    if [ "${gerbil_shared}" = "t" ]; then
	LDFLAGS="${ldflags_rpath}$rpath_sep${gerbil_prefix}/lib"
    fi
else
    if [ "${gerbil_shared}" = "t" ]; then
	LDFLAGS="${LDFLAGS} ${ldflags_rpath}$rpath_sep${gerbil_prefix}/lib"
    fi
fi

gambit_config="--prefix=${gerbil_prefix} --enable-march=${gambit_march} ${gambit_shared} ${gambit_config}"
(export LDFLAGS="$LDFLAGS"; export CFLAGS="$CFLAGS"; cd src/gambit && ./configure $gambit_config ) || die

rm -f build-env.sh
cat > build-env.sh <<EOF
GERBIL_PREFIX=${gerbil_prefix}
GERBIL_VERSION=${gerbil_version}
export GERBIL_PREFIX GERBIL_VERSION
EOF

if [ -n "$gerbil_version_string" ] ;
then
	cat >> build-env.sh <<EOF
GERBIL_VERSION_STRING=${gerbil_version_string}
export GERBIL_VERSION_STRING
EOF
fi

exit 0
