#                                               -*- Autoconf -*-
# %CopyrightBegin%
# 
# Copyright Ericsson AB 2000-2009. All Rights Reserved.
# 
# The contents of this file are subject to the Erlang Public License,
# Version 1.1, (the "License"); you may not use this file except in
# compliance with the License. You should have received a copy of the
# Erlang Public License along with this software. If not, it can be
# retrieved online at http://www.erlang.org/.
# 
# Software distributed under the License is distributed on an "AS IS"
# basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
# the License for the specific language governing rights and limitations
# under the License.
# 
# %CopyrightEnd%
#
# Process this file with autoconf to produce a configure script.
# The starting point for this file was the output from 'autoscan'.

# Strange, VxWorks HAVE_SENS not set here, see "ei_resolve.h"

# Find the erl_interface version number and set m4 macro to it.
# We do this because AC_INIT can't handle shell variables. Still broken.
dnl m4_define(EI_VERSION,`grep EI_VSN ../vsn.mk | sed 's/^.*=[ ]*//'`)
dnl m4_define(EI_VERSION,regexp(m4_include(VERSION),[version \([-.0-9A-Za-z]+\)],[\1]))

AC_INIT()

if test "x$no_recursion" != "xyes" -a "x$OVERRIDE_CONFIG_CACHE" = "x"; then
    # We do not want to use a common cache!
    cache_file=/dev/null
fi

dnl How to set srcdir absolute is taken from the GNU Emacs distribution
#### Make srcdir absolute, if it isn't already.  It's important to
#### avoid running the path through pwd unnecessary, since pwd can
#### give you automounter prefixes, which can go away.
case "${srcdir}" in
  /* ) ;;
  . )
    ## We may be able to use the $PWD environment variable to make this
    ## absolute.  But sometimes PWD is inaccurate.
    ## Make sure CDPATH doesn't affect cd (in case PWD is relative).
    CDPATH=
    if test "${PWD}" != "" && test "`(cd ${PWD} ; sh -c pwd)`" = "`pwd`"  ;
    then
      srcdir="$PWD"
    else
      srcdir="`(cd ${srcdir}; pwd)`"
    fi
  ;;
  *  ) srcdir="`(cd ${srcdir}; pwd)`" ;;
esac

AC_CONFIG_AUX_DIR([$srcdir/src/auxdir])

if test "X$host" != "Xfree_source" -a "X$host" != "Xwin32"; then
    AC_CANONICAL_HOST
else
    host_os=win32
fi

TARGET=$host
AC_SUBST(TARGET)

AC_CONFIG_HEADER([src/$host/config.h:src/auxdir/config.h.in])

dnl ----------------------------------------------------------------------
dnl Optional features
dnl ----------------------------------------------------------------------

AC_ARG_WITH(xcomp-conf,
[  --with-xcompconf=PATH     path to cross compilation configuration])
if test "x$with_xcompconf" != "xno" -a "x$with_xcompconf" != "x" ; then
    . $with_xcompconf
fi

# Use --disable-threads to force building single threaded libs even 
# if pthreads exists (for test purposes).
AC_ARG_ENABLE(threads,
[  --disable-threads       use to only build single threaded libs],
[ case "$enableval" in
    no) threads_disabled=yes ;;
    *)  threads_disabled=no ;;
  esac ],
[ threads_disabled=no ])

dnl ----------------------------------------------------------------------
dnl Checks for programs
dnl ----------------------------------------------------------------------

AC_PROG_CC
AC_PROG_CPP
dnl AC_PROG_LIBTOOL
AC_PROG_RANLIB
if test "x$LD" = "x"; then
   AC_CHECK_TOOL([LD],[ld],[ld])
fi
AC_SUBST(LD)

AC_CHECK_SIZEOF(short, $erl_xcomp_short)
AC_CHECK_SIZEOF(int, $erl_xcomp_int)
AC_CHECK_SIZEOF(long, $erl_xcomp_long)
AC_CHECK_SIZEOF(void *, $erl_xcomp_void_p)
AC_CHECK_SIZEOF(long long, $erl_xcomp_long_long)

if test $ac_cv_sizeof_void_p = 8; then
  CFLAGS="$CFLAGS -DEI_64BIT"
fi

AC_CHECK_PROG(AR, ar, ar, false)
if test "$ac_cv_prog_AR" = false; then
  AC_MSG_ERROR([No 'ar' command found in PATH])
fi

dnl
dnl We can live with Solaris /usr/ucb/install
dnl
case $host in
  *-*-solaris*|free_source)
    if test -x /usr/ucb/install; then
      INSTALL="/usr/ucb/install -c"
    fi
    ;;
  *)
    ;;
esac

AC_PROG_INSTALL
LM_PROG_INSTALL_DIR
AC_SUBST(INSTALL_DIR)

case $host_os in
	darwin*)
		dnl Need to preserve modification time on archives;
		dnl otherwise, ranlib has to be run on archives
		dnl again after installation.
		INSTALL_DATA="$INSTALL_DATA -p";;
	*)
		;;
esac

# Checks for libraries.
AC_CHECK_LIB([nsl], [gethostbyname])
AC_CHECK_LIB([socket], [getpeername])

# Checks for header files.
AC_HEADER_STDC
AC_HEADER_SYS_WAIT
AC_CHECK_HEADERS([arpa/inet.h fcntl.h limits.h malloc.h netdb.h netinet/in.h stddef.h stdlib.h string.h sys/param.h sys/socket.h sys/select.h sys/time.h unistd.h sys/types.h])

# Checks for typedefs, structures, and compiler characteristics.
# fixme AC_C_CONST & AC_C_VOLATILE needed for Windows?
dnl AC_C_CONST
dnl AC_C_VOLATILE
AC_TYPE_UID_T
AC_TYPE_PID_T
AC_TYPE_SIZE_T
AC_HEADER_TIME
AC_MSG_CHECKING([for socklen_t usability])
AC_TRY_COMPILE([#include <sys/types.h>
#include <sys/socket.h>], 
[socklen_t mylen;],
[AC_MSG_RESULT(yes) 
 AC_DEFINE(HAVE_SOCKLEN_T)],
[AC_MSG_RESULT(no)])

# Checks for library functions.
AC_FUNC_ALLOCA
dnl AC_FUNC_FORK
# FIXME check that this isn't set in normal cases
AC_PROG_GCC_TRADITIONAL
# Check if malloc(0) is ok 
dnl AC_FUNC_MALLOC
dnl AC_FUNC_REALLOC
AC_FUNC_MEMCMP
dnl AC_FUNC_SELECT_ARGTYPES
dnl AC_TYPE_SIGNAL
dnl AC_FUNC_STRERROR_R
dnl AC_FUNC_VPRINTF
AC_CHECK_FUNCS([dup2 gethostbyaddr gethostbyname \
	gethostbyaddr_r \
	gethostbyname_r gethostname writev \
	gethrtime gettimeofday inet_ntoa memchr memmove memset select \
	socket strchr strerror strrchr strstr uname])
AC_CHECK_FUNC(res_gethostbyname, [],
    AC_CHECK_LIB(resolv, res_gethostbyname)
)
AC_CHECK_FUNC(clock_gettime, [],
    AC_CHECK_LIB(rt, clock_gettime)
)

# ---------------------------------------------------------------------------
# We don't link against libgmp except for "make check"
# but linking will also tell us that it is >= 4.1
# ---------------------------------------------------------------------------

AC_ARG_WITH(gmp,
[  --with-gmp=PATH         specify location of GNU MP include and lib
  --with-gmp              use GNU MP (will search for it)])

# We don't just want any GNU MP version, we want 4.1 or later
# that contain the import/export functions we need.

if test "x$with_gmp" = "xyes" ;then
    for dir in /usr /usr/pkg /usr/local /usr/local/gmp /usr/lib/gmp /usr/gmp; do
	AC_CHECK_HEADER($dir/include/gmp.h, ac_cv_gmp=yes, ac_cv_gmp=no)
	if test $ac_cv_gmp = yes ; then
	    CFLAGS="$CFLAGS -I$dir/include -L$dir/lib"
	    AC_DEFINE(HAVE_GMP_H)
	    break
	fi
    done
    if test $ac_cv_gmp = no ; then
	AC_MSG_ERROR([No GNU MP installation found])
    fi
    AC_CHECK_LIB(gmp, __gmpz_export)
    # FIXME return ERROR if no lib
elif test "x$with_gmp" != "xno" -a -n "$with_gmp" ;then
    # Option given with PATH to package
    AC_MSG_CHECKING(for GNU MP)
    if test ! -d "$with_gmp" ; then
	AC_MSG_ERROR(Invalid path to option --with-gmp=PATH)
    fi
    AC_MSG_RESULT(yes)
    CFLAGS="$CFLAGS -I$with_gmp/include -L$with_gmp/lib"
    AC_DEFINE(HAVE_GMP_H)
    AC_CHECK_LIB(gmp, __gmpz_export)
    # FIXME return ERROR if no lib
fi

MIXED_CYGWIN=no

AC_MSG_CHECKING(for mixed cygwin and native VC++ environment)
if test "X$CC" = "Xcc.sh" -a "X$host" = "Xwin32" -a "x$GCC" != x"yes"; then
	if test -x /usr/bin/cygpath; then
		CFLAGS="-O2"
		MIXED_CYGWIN=yes
		AC_MSG_RESULT([yes])
		MIXED_CYGWIN_VC=yes
	else
		AC_MSG_RESULT([undeterminable])
		AC_MSG_ERROR(Seems to be mixed windows but not with cygwin, cannot handle this!)
	fi
else
	AC_MSG_RESULT([no])
	MIXED_CYGWIN_VC=no
fi
AC_SUBST(MIXED_CYGWIN_VC)

AC_MSG_CHECKING(for mixed cygwin and native MinGW environment)
if test "X$CC" = "Xcc.sh" -a "X$host" = "Xwin32" -a "x$GCC" = x"yes"; then
	if test -x /usr/bin/cygpath; then
		CFLAGS="-O2"
		MIXED_CYGWIN=yes
		AC_MSG_RESULT([yes])
		MIXED_CYGWIN_MINGW=yes
	else
		AC_MSG_RESULT([undeterminable])
		AC_MSG_ERROR(Seems to be mixed windows but not with cygwin, cannot handle this!)
	fi
else
	AC_MSG_RESULT([no])
	MIXED_CYGWIN_MINGW=no
fi
AC_SUBST(MIXED_CYGWIN_MINGW)

AC_MSG_CHECKING(if we mix cygwin with any native compiler)
if test "X$MIXED_CYGWIN" = "Xyes" ; then
	AC_MSG_RESULT([yes])	
else
	AC_MSG_RESULT([no])
fi

AC_SUBST(MIXED_CYGWIN)
	
dnl
dnl Threads
dnl
found_threads=no
THR_LIBS=
THR_DEFS=
EI_THREADS="false"
AC_SUBST(THR_LIBS)
AC_SUBST(THR_DEFS)
AC_SUBST(EI_THREADS)

case "$threads_disabled" in
	no)
		AC_MSG_CHECKING([for native win32 threads])
		if test "X$host_os" = "Xwin32"; then
		    THR_DEFS="-DWIN32_THREADS"
		    found_threads=yes
		    EI_THREADS="true"	
		    AC_MSG_RESULT([yes])
		    AC_MSG_CHECKING([for __declspec(thread) usability])
		    if test "X$GCC" = "Xyes"; then
		        AC_MSG_RESULT([no])
		    else
		        THR_DEFS="$THR_DEFS -DUSE_DECLSPEC_THREAD"
			AC_MSG_RESULT([yes])
		    fi	
		else
		    AC_MSG_RESULT(no)

		    dnl Check for POSIX threads

		    pthread_lib=""
		    AC_CHECK_LIB(pthread,
				 pthread_create,
				 [found_threads=yes
		                  EI_THREADS="true"
				  THR_LIBS="-lpthread"
				  THR_DEFS="-D_REENTRANT -D_THREAD_SAFE -DPOSIX_THREADS"
				  pthread_lib=pthread])

		    # FreeBSD has pthreads in special c library, c_r
		    if test $found_threads = no; then
			AC_CHECK_LIB(c_r,
				     pthread_create,
				     [found_threads=yes
		                      EI_THREADS="true"
				      THR_LIBS="-lc_r"
				      THR_DEFS="-D_REENTRANT -D_THREAD_SAFE -DPOSIX_THREADS"
				      pthread_lib=c_r])
		    fi

		    if test "x$pthread_lib" != "x"; then
			AC_CHECK_LIB($pthread_lib,pthread_atfork,AC_DEFINE(HAVE_PTHREAD_ATFORK))
			AC_CHECK_HEADER(pthread.h, AC_DEFINE(HAVE_PTHREAD_H))
			dnl Some Linuxes have <pthread/mit/pthread.h> instead of <pthread.h>
			AC_CHECK_HEADER(pthread/mit/pthread.h, AC_DEFINE(HAVE_MIT_PTHREAD_H))
			case $host_os in
			    solaris*)
				THR_DEFS="$THR_DEFS -D_POSIX_PTHREAD_SEMANTICS";;
			    linux*)
				dnl NPTL test stolen from $ERL_TOP/erts/aclocal.m4
				AC_MSG_CHECKING(for Native POSIX Thread Library)
				case `getconf GNU_LIBPTHREAD_VERSION 2>/dev/null` in
				    nptl*) nptl=yes;;
				    NPTL*) nptl=yes;;
				    *)  nptl=no;;
				esac
				AC_MSG_RESULT($nptl)
				if test $nptl = yes; then
				    need_nptl_incldir=no
				    AC_CHECK_HEADER(nptl/pthread.h, need_nptl_incldir=yes)
				    if test $need_nptl_incldir = yes; then
					# Ahh...
					nptl_path="$C_INCLUDE_PATH:$CPATH:/usr/local/include:/usr/include"
					nptl_ws_path=
					save_ifs="$IFS"; IFS=":"
					for dir in $nptl_path; do
					    if test "x$dir" != "x"; then
						nptl_ws_path="$nptl_ws_path $dir"
					    fi
					done
					IFS=$save_ifs
					nptl_incldir=
					for dir in $nptl_ws_path; do
				            AC_CHECK_HEADER($dir/nptl/pthread.h,
							    nptl_incldir=$dir/nptl)
					    if test "x$nptl_incldir" != "x"; then
						THR_DEFS="$THR_DEFS -isystem $nptl_incldir"
						break
					    fi
					done
					if test "x$nptl_incldir" = "x"; then
					    AC_MSG_ERROR(Failed to locate nptl system include directory)
					fi
				    fi
				fi

				;;
			    *)
				;;
			esac
		    fi
		fi
		;;
	yes)
	    # Threads disabled
	    ;;
esac

# ---------------------------------------------------------------------------
# Warning flags to the C compiler
# ---------------------------------------------------------------------------
AC_SUBST(WFLAGS)

if test "x$GCC" = xyes; then
  WFLAGS="-Wall -Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations -Wnested-externs -Winline"
  # check which GCC version
  GCC_VERSION=`$CC -v 2>&1 | sed -n 's/gcc version //p'`
  # GCC 3.3 and later supports C99 strict aliasing
  # until all source is compliant with strict aliasing we disable it
  case "$GCC_VERSION" in
    1*) ;;
    2*) ;;
    3.0*) ;; 
    3.1*) ;;
    3.2*) ;;
    *)
        WFLAGS="$WFLAGS -fno-strict-aliasing";;
  esac
else
  WFLAGS=""
fi

# ---------------------------------------------------------------------------
# FIXME We want to use libtool but until then....
# ---------------------------------------------------------------------------

AC_SUBST(DED_CFLAGS)
dnl AC_SUBST(DED_LD)
dnl AC_SUBST(DED_LDFLAGS)

if test "X$host" = "Xwin32"; then
  DED_CFLAGS="$CFLAGS"
else
  case $host_os in
    darwin*)
	CFLAGS="$CFLAGS -no-cpp-precomp"
	;;
  esac

  if test "x$GCC" = xyes; then
	DED_CFLAGS="$CFLAGS -fPIC"
  else
	DED_CFLAGS="$CFLAGS"
  fi
fi

# ---------------------------------------------------------------------------
# XXX
# ---------------------------------------------------------------------------

AC_OUTPUT(
	src/$host/Makefile:src/Makefile.in
	src/$host/eidefs.mk:src/eidefs.mk.in
	)