#! /bin/sh
# autoconf-style configuration script
#
set -e

name=rbldnsd


if [ -f rbldnsd.h -a -f rbldnsd_util.c ] ; then :
else
  echo "configure: error: sources not found at `pwd`" >&2
  exit 1
fi

options="ipv6 stats master_dump zlib dso asserts systemd"

for opt in $options; do
  eval enable_$opt=
done

if [ -f config.status ]; then
  . ./config.status
fi

enable() {
  opt=`echo "$1" | sed 's/^--[^-]*-//'`
  case "$opt" in
    ipv6|stats|master_dump|zlib|dso|asserts|systemd) ;;
    master-dump) opt=master_dump ;;
    *) echo "configure: unrecognized option \`$1'" >&2; exit 1;;
  esac
  eval enable_$opt=$2
}

while [ $# -gt 0 ]; do
  case "$1" in
    --disable-*|--without-*|--no-*) enable "$1" n;;
    --enable-*|--with-*) enable "$1" y;;
    --help | --hel | --he | --h | -help | -hel | -he | -h )
      cat <<EOF
configure: configure $name package.
Usage: ./configure [options]
where options are:
 --enable-option, --with-option --
   enable the named option/feature
 --disable-option, --without-option, --no-option --
   disable the named option/feature
 --help - print this help and exit
Optional features (all enabled by default if system supports a feature):
  ipv6 - enable/disable IP version 6 (IPv6) support
  stats - enable/disable runtime statistics
  master-dump - enable/disable master-format (bind) dump support (-d option)
  zlib - zlib support
  dso - dynamic extensions (using shared objects) -- disabled by default
  asserts - enable/disable debugging assertions -- disabled by default
  systemd - enable/disable systemd support -- disabled by default
EOF
      exit 0
      ;;
    *) echo "configure: unknown option \`$1'" >&2; exit 1 ;;
  esac
  shift
done

. ./configure.lib

rm -f confdef.h
cat >confdef.h <<EOF
/* $name autoconfiguration header file.
 * Generated automatically by configure. */

EOF

set -- $(sed -n -e '/[^0-9].* (.*)$/ { s/\(.*\) (\(.*\))$/\1 \2/p; q; }' NEWS)
VERSION=$1; shift
VERSION_DATE="$*"

ac_msg "configure: $name"
ac_result "$VERSION ($VERSION_DATE)"

ac_prog_c_compiler
ac_prog_ranlib

if ac_header_check_v stdint.h
then :
else
  echo "#define NO_STDINT_H 1" >>confdef.h

  if ac_yesno "sizes of standard integer types" \
     ac_compile_run <<EOF
#include <stdio.h>
int main() {
  printf("#define SIZEOF_SHORT %d\n", sizeof(short));
  printf("#define SIZEOF_INT %d\n", sizeof(int));
  printf("#define SIZEOF_LONG %d\n", sizeof(long));
  return 0;
}
EOF
  then
    cat conftest.out >> confdef.h
  else
    ac_fatal "cannot determine sizes of standard types"
  fi
  if ac_yesno "for long long" \
     ac_compile_run <<EOF
#include <stdio.h>
int main() {
  long long x;
  printf("#define SIZEOF_LONG_LONG %d\n", sizeof(long long));
  return 0;
}
EOF
  then
    cat conftest.out >>confdef.h
  else
    echo "#define NO_LONG_LONG" >>confdef.h
  fi
fi

if ac_compile_run_v "whether C compiler defines __SIZEOF_POINTER__" <<EOF
#include <stdio.h>
int main() {
#ifdef __SIZEOF_POINTER__
  return 0;
#else
  printf("#define __SIZEOF_POINTER__ %d\n", sizeof(int *));
  return 1;
#endif
}
EOF
then :
else
  cat conftest.out >>confdef.h
fi

if ac_verbose "byte order" "big-endian" "little-endian" \
   ac_compile_run <<EOF
int main() {
  long one = 1;
  if (*(char *)&one)
    return 1; /* little-endian */
  return 0;
}
EOF
then
  echo "#define WORDS_BIGENDIAN 1" >>confdef.h
fi

has_inline=
for c in inline __inline; do
  if ac_compile_v "for $c" <<EOF
static $c int foo() { return 0; }
int main() { return foo(); }
EOF
  then
    has_inline=$c
    break
  fi
done
if [ "$has_inline" != inline ]; then
  echo "#define inline" $has_inline >>confdef.h
fi

if ac_compile_v "for socklen_t" <<EOF
#include <sys/types.h>
#include <sys/socket.h>
int foo() { socklen_t len; len = 0; return len; }
EOF
then :
else
  echo "#define socklen_t int" >>confdef.h
fi

if ac_library_find_v 'connect()' "" "-lsocket -lnsl" <<EOF
int main() { gethostbyname(); connect(); return 0; }
EOF
then :
else
  ac_fatal "cannot find libraries needed for sockets"
fi

if [ n = "$enable_ipv6" ]; then
  echo "#define NO_IPv6	1	/* option disabled */" >>confdef.h
else

if ac_link_v "for IPv6" <<EOF
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
int main() {
  char h[200];
  char s[200];
  struct sockaddr_in6 sa;
  sa.sin6_family = AF_INET6;
  getnameinfo((struct sockaddr*)&sa, sizeof(sa), h, sizeof(h), s, sizeof(s), 0);
  return 0;
}
EOF
then :
else
  if [ "$enable_ipv6" ]; then
    ac_fatal "IPv6 is requested but not available"
  fi
  echo "#define NO_IPv6 1" >>confdef.h
fi
fi # enable_ipv6?

if ac_link_v "for mallinfo()" <<EOF
#include <sys/types.h>
#include <stdlib.h>
#include <malloc.h>
int main() {
  struct mallinfo mi = mallinfo();
  return 0;
}
EOF
then :
else
  echo "#define NO_MEMINFO 1" >>confdef.h
fi

if ac_link_v "for poll()" <<EOF
#include <sys/types.h>
#include <sys/poll.h>
int main() {
  struct pollfd pfd[2];
  return poll(pfd, 2, 10);
}
EOF
then :
else
  echo "#define NO_POLL 1" >>confdef.h

  if ac_header_check_v "sys/select.h"
  then :
  else
    echo "#define NO_SELECT_H 1" >>confdefs.h
  fi
fi

if ac_link_v "for vsnprintf()" <<EOF
#include <stdio.h>
#include <string.h>
#include <stdarg.h>
int test(char *fmt, ...) {
  va_list ap;
  char buf[40];
  va_start(ap, fmt);
  vsnprintf(buf, sizeof(buf), fmt, ap);
  return 0;
}
int main() {
  test("test%d", 40);
  return 0;
}
EOF
then :
else
  ac_fatal "$name requires working vsnprintf() routine"
fi

if ac_link_v "for writev()/readv()" <<EOF
#include <sys/types.h>
#include <unistd.h>
#include <sys/uio.h>
int main() {
  struct iovec iov;
  return writev(1, &iov, 1) && readv(1, &iov, 1);
}
EOF
then :
else
  echo "#define NO_IOVEC 1" >>confdef.h
fi

if ac_link_v "for setitimer()" <<EOF
#include <sys/types.h>
#include <sys/time.h>
int main() {
  struct itimerval itv;
  itv.it_interval.tv_sec  = itv.it_value.tv_sec  = 10;
  itv.it_interval.tv_usec = itv.it_value.tv_usec = 20;
  setitimer(ITIMER_REAL, &itv, 0);
  return 0;
}
EOF
then
  echo "#define HAVE_SETITIMER 1" >>confdef.h
fi

if [ n = "$enable_zlib" ]; then
  echo "#define NO_ZLIB	1	/* option disabled */" >>confdef.h
elif ac_link_v "for zlib support" -lz <<EOF
#include <sys/types.h>
#include <stdio.h>
#include <zlib.h>
int main() {
  z_stream z;
  int r;
  r = inflateInit2(&z, 0);
  r = inflate(&z, Z_NO_FLUSH);
  r = inflateEnd(&z);
  return 0;
}
EOF
then
  LIBS="$LIBS -lz"
elif [ "$enable_zlib" ]; then
  ac_fatal "zlib support is requested but not found/available"
else
  echo "#define NO_ZLIB" >>confdef.h
fi

if [ -z "$enable_dso" ]; then
  echo "#define NO_DSO		1	/* disabled by default */" >> confdef.h
elif [ n = "$enable_dso" ]; then
  echo "#define NO_DSO		1	/* option disabled */" >>confdef.h
elif ac_link_v "for dlopen() in -dl with -rdynamic" -ldl -rdynamic <<EOF
#include <dlfcn.h>
int main() {
  void *handle, *func;
  handle = dlopen("testfile", RTLD_NOW);
  func = dlsym(handle, "function");
  return 0;
}
EOF
then
  LIBS="$LIBS -ldl -rdynamic"
elif [ "$enable_dso" ]; then
  ac_fatal "dso support requires dlopen() in -ldl"
else
  echo "#define NO_DSO	1	/* not available */" >> confdef.h
fi

if [ n = "$enable_stats" ]; then
  echo "#define NO_STATS	1	/* option disabled */" >>confdef.h
fi
if [ n = "$enable_master_dump" ]; then
  echo "#define NO_MASTER_DUMP	1	/* option disabled */" >>confdef.h
fi
if [ y != "$enable_asserts" ]; then
  echo "#define NDEBUG		1	/* option disabled */" >>confdef.h
fi

if [ y = "$enable_systemd" ]; then
  PKGCONFIG="pkg-config"
  if ac_run $PKGCONFIG --libs libsystemd; then
    echo "libsystemd FOUND"
    USE_SYSTEMD=1
    echo "#define USE_SYSTEMD	1	/* option enabled */" >>confdef.h
  else
    ac_fatal "libsystemd NOT FOUND. Aborting."
  fi
fi

ac_subst VERSION VERSION_DATE PKGCONFIG USE_SYSTEMD

ac_output Makefile
ac_msg "creating config.h"
mv -f confdef.h config.h
ac_result ok
ac_msg "creating config.status"
rm -f config.status
{
echo "# automatically generated by configure to hold command-line options"
echo
found=
for opt in $options; do
  eval val=\$enable_$opt
  if [ -n "$val" ]; then
    echo enable_$opt=$val
    found=y
  fi
done
if [ ! "$found" ]; then
  echo "# (no options encountered)"
fi
} > config.status
ac_result ok

ac_result "all done."
exit 0
