]> git.draconx.ca Git - dxcommon.git/blobdiff - m4/libhelper.m4
Add libpng detection macro.
[dxcommon.git] / m4 / libhelper.m4
diff --git a/m4/libhelper.m4 b/m4/libhelper.m4
new file mode 100644 (file)
index 0000000..500389c
--- /dev/null
@@ -0,0 +1,141 @@
+dnl Copyright © 2014 Nick Bowler
+dnl
+dnl License WTFPL2: Do What The Fuck You Want To Public License, version 2.
+dnl This is free software: you are free to do what the fuck you want to.
+dnl There is NO WARRANTY, to the extent permitted by law.
+
+dnl DX_LIB_SETUP(env-base, [human-name])
+dnl
+dnl Helper to setup a library test.  Defines two user variables FOO_CFLAGS
+dnl and FOO_LIBS, where FOO is replaced with env-base in uppercase.  The
+dnl human-name is the name of the library used in help text, by default the
+dnl same as env-base.
+AC_DEFUN([DX_LIB_SETUP], [m4_do(
+       [AC_ARG_VAR(m4_toupper([$1])[_CFLAGS],
+               [C compiler flags for ]m4_default([$2], [$1]))],
+       [AC_ARG_VAR(m4_toupper([$1])[_LIBS],
+               [linker flags for ]m4_default([$2], [$1]))])])
+
+dnl DX_LIB_PKGCONFIG_FLAGS(env-base, [library-name])
+dnl
+dnl Helper for querying a library's CFLAGS and LIBS values from the
+dnl pkg-config database.  The results are stored in the cache variables
+dnl dx_cv_foo_pkg_cflags and dx_cv_foo_pkg_libs, where foo is replaced with
+dnl env-base in lowercase.  If not specified, the library name defaults to
+dnl env-base.
+AC_DEFUN([DX_LIB_PKGCONFIG_FLAGS],
+       [_DX_LIB_PKGCONFIG_FLAGS(m4_tolower([$1]),
+               [m4_default([$2], [$1])])])
+
+dnl Internal helper macro for the above.
+AC_DEFUN([_DX_LIB_PKGCONFIG_FLAGS], [AS_IF([test x"$PKG_CONFIG" != x""],
+       [AC_CACHE_CHECK([pkg-config database for $2], [dx_cv_$1_pkg_found],
+               [m4_do([dx_cv_$1_pkg_found=yes],
+                       [m4_newline([DX_PKG_CONFIG([dx_cv_$1_pkg_cflags],
+                               [--cflags "$2"], [],
+                               [dx_cv_$1_pkg_found=no])])],
+                       [m4_newline([DX_PKG_CONFIG([dx_cv_$1_pkg_libs],
+                               [--libs "$2"], [],
+                               [dx_cv_$1_pkg_found=no])])])])])])
+
+dnl DX_LIB_SEARCH(env-base, test, test-matrix)
+dnl
+dnl Helper to search for the correct compiler/linker flags for a particular
+dnl library.  The test-matrix is an ordered, quoted list of quoted lists.
+dnl Each entry in the test matrix has the following form:
+dnl
+dnl    [cflags, libs, shell-condition]
+dnl
+dnl For each item, the specified cflags and libs are temporarily appended to
+dnl CFLAGS and LIBS, respectively, then the given test is run.  The test
+dnl argument must be an m4 macro which takes one argument (action-if-ok).
+dnl This macro shall expand to shell code which executes action-if-ok if and
+dnl only if the test was successful.  The test macro is expanded only once.
+dnl
+dnl If a test is successful, dx_cv_foo_lib_found is set to "yes", where foo is
+dnl replaced with env-base in lowercase.  Subsequent tests are not tried.
+dnl The cflags and libs values from a successful test are stored in FOO_CFLAGS
+dnl and FOO_LIBS, respectively, where FOO is replaced with env-base in
+dnl uppercase.  These values are AC_SUBST-ed.  If no test was successful,
+dnl dx_cv_foo_lib_found is set to "no".
+dnl
+dnl The result ("yes" or "no") are printed so this macro should be preceded
+dnl by a call to AC_MSG_CHECKING.
+AC_DEFUN([DX_LIB_SEARCH], [m4_divert_push([KILL])
+
+m4_pushdef([_DX_CVNAME], m4_tolower([dx_cv_$1_lib_])[$][1])
+m4_pushdef([_DX_FNNAME], m4_tolower([dx_fn_$1_lib_])[$][1])
+
+m4_divert([INIT_PREPARE])dnl
+# Helper function to test whether $1 works.
+_DX_FNNAME([test]) () {
+CFLAGS="$_dx_save_cflags $[]1"
+LIBS="$_dx_save_libs $[]2"
+m4_apply([$2], [dnl
+       _DX_CVNAME([found])=yes
+       _DX_CVNAME([cflags])=$[]1
+       _DX_CVNAME([libs])=$[]2])
+}
+
+m4_divert_pop()dnl
+AC_CACHE_VAL([_DX_CVNAME([found])], [dnl
+_DX_CVNAME([found])=no
+_dx_save_cflags=$CFLAGS
+_dx_save_libs=$LIBS
+m4_map_sep([_DX_LIB_TEST], [m4_newline], [$3])
+CFLAGS=$_dx_save_cflags
+LIBS=$_dx_save_libs])dnl
+
+AC_MSG_RESULT([$_DX_CVNAME([found])])
+AS_IF([test x"$_DX_CVNAME([found])" = x"yes"], [dnl
+       AC_SUBST(m4_toupper([$1_CFLAGS]), [$_DX_CVNAME([cflags])])dnl
+       AC_SUBST(m4_toupper([$1_LIBS]), [$_DX_CVNAME([libs])])])
+m4_popdef([_DX_CVNAME], [_DX_FNNAME])])
+
+dnl Internal helper macro for the above.
+AC_DEFUN([_DX_LIB_TEST],
+       [AS_IF([m4_do([test x"$_DX_CVNAME([found])" != x"yes"],
+               [m4_ifnblank([$3], [ && $3])])],
+       [_DX_FNNAME([test]) "$1" "$2"])])
+
+dnl DX_LIB_SEARCH_LINK(env-base, test-program, test-matrix)
+dnl
+dnl Convenience wrapper around DX_LIB_SEARCH which implements the test
+dnl function by attempting to linking the provided test program.
+AC_DEFUN([DX_LIB_SEARCH_LINK],
+       [DX_LIB_SEARCH([$1], [m4_curry([AC_LINK_IFELSE], [$2])], [$3])])
+
+dnl DX_LIB_USERFLAG_BLURB(env-base, [human-name])
+dnl
+dnl Expand to text explaining the FOO_CFLAGS and FOO_LIBS environment
+dnl variables, used in error messages, where FOO is replaced with env-base
+dnl in uppercase.  The human-name is the name of the library, by default the
+dnl same as env-base.
+AC_DEFUN([DX_LIB_USERFLAG_BLURB],
+       [_DX_LIB_USERFLAG_BLURB([m4_toupper([$1])], [m4_default([$2], [$1])])])
+
+dnl Internal helper macro for the above.
+AC_DEFUN([_DX_LIB_USERFLAG_BLURB], [dnl
+If $2 is installed but was not detected by this configure script,
+consider adjusting $1_CFLAGS and/or $1_LIBS as necessary.])
+
+dnl DX_LIB_USERFLAG_BLURB(env-base, [human-name])
+dnl
+dnl Expand to text explaining the PKG_CONFIG_PATH environment variable,
+dnl used in error messages.  The human-name is the name of the library, by
+dnl default the same as env-base.
+AC_DEFUN([DX_LIB_PKGCONFIG_BLURB],
+       [_DX_LIB_PKGCONFIG_BLURB([$1], [m4_default([$2], [$1])])])
+
+dnl Internal helper macro for the above.
+AC_DEFUN([_DX_LIB_PKGCONFIG_BLURB], [dnl
+If pkg-config is installed, it may help to adjust PKG_CONFIG_PATH if
+$2 is installed in a non-standard prefix.])
+
+dnl DX_LIB_COMPILE_ERROR([text])
+dnl
+dnl Expand to C code which should fail compilation.  The given text should
+dnl appear in any error message from the compiler, and should not contain
+dnl any newlines.
+AC_DEFUN([DX_LIB_COMPILE_ERROR], [m4_do([m4_newline([@%:@error $1])],
+       [m4_newline([static int AS_TR_SH([$1])@<:@-1@:>@;])])])