diff options
-rw-r--r-- | ChangeLog | 15 | ||||
-rw-r--r-- | HACKING | 4 | ||||
-rw-r--r-- | configure.ac | 4 | ||||
-rw-r--r-- | lib/Makefile.am | 79 | ||||
-rwxr-xr-x | lib/declared.sh | 135 | ||||
-rw-r--r-- | lib/exported.sh.in | 24 | ||||
-rw-r--r-- | m4/exported.m4 | 21 | ||||
-rw-r--r-- | tests/Makefile.am | 3 |
8 files changed, 285 insertions, 0 deletions
@@ -1,3 +1,18 @@ +2008-04-11 Bruno Haible <bruno@clisp.org> + + Limit the exported symbols through a config.h trick. + * m4/exported.m4: New file, from GNU gettext. + * lib/exported.sh.in: New file, from GNU gettext. + * configure.ac: Invoke gt_GLOBAL_SYMBOL_PIPE. + (AC_CONFIG_FILES): Add lib/exported.sh. + * lib/declared.sh: New file, borrowing from GNU gettext's moopp. + * lib/Makefile.am (HEADERS_WITH_EXTERNS): New variable. + (libunistring.sym, config.h): New rules. + (MOSTLYCLEANFILES, MAINTAINERCLEANFILES): Update accordingly. + (EXTRA_DIST): Add libunistring.sym. + * tests/Makefile.am (DEFAULT_INCLUDES): New variable. + * HACKING: Require GNU sed. + 2008-04-10 Bruno Haible <bruno@clisp.org> Install all auxiliary include files in a subdirectory. @@ -27,6 +27,10 @@ You will need reasonably recent versions of the build tools: + Homepage: http://www.gnu.org/software/gperf/ + * GNU sed + + Homepage: + http://www.gnu.org/software/sed/ + * Perl + Homepage: http://www.perl.org/ diff --git a/configure.ac b/configure.ac index 740516f..08541a6 100644 --- a/configure.ac +++ b/configure.ac @@ -55,6 +55,9 @@ dnl Checks for types, header files, functions and declarations. gl_INIT +dnl Check for prerequisites of exported.sh. +gt_GLOBAL_SYMBOL_PIPE + dnl Check for tools needed for formatting the documentation. ac_aux_dir_abs=`cd $ac_aux_dir && pwd` AC_PATH_PROG([TEXI2DVI], [texi2dvi], [$ac_aux_dir_abs/missing texi2dvi]) @@ -66,5 +69,6 @@ AC_CONFIG_FILES([doc/Makefile], [FIX_MAKEFILE_DISTRIB]) AC_CONFIG_FILES([gnulib-local/Makefile]) AC_CONFIG_FILES([lib/Makefile]) +AC_CONFIG_FILES([lib/exported.sh]) AC_CONFIG_FILES([tests/Makefile]) AC_OUTPUT diff --git a/lib/Makefile.am b/lib/Makefile.am index 4e8d6a6..6eaed43 100644 --- a/lib/Makefile.am +++ b/lib/Makefile.am @@ -136,6 +136,85 @@ clean-local: clean-generic fi; \ : +# List of header files that get installed and that declared 'extern' symbols. +HEADERS_WITH_EXTERNS = \ + unitypes.h \ + unistr.h \ + uniconv.h \ + unistdio.h \ + uniname.h \ + unictype.h \ + uniwidth.h \ + uniwbrk.h \ + unilbrk.h \ + uninorm.h \ + unicase.h \ + localcharset.h \ + iconveh.h + +# List of exported symbols. +# We extract it from the header files that get installed, removing symbols +# start with "_UC". +# This file has the same format as the one expected by the libtool option +# '-export-symbols', but we don't use this option, because it would prevent us +# from building some of the gnulib unit tests. +libunistring.sym : $(HEADERS_WITH_EXTERNS) + for f in $(HEADERS_WITH_EXTERNS); do cat $(srcdir)/$$f; done \ + | $(srcdir)/declared.sh | LC_ALL=C sort | LC_ALL=C uniq \ + | grep -v '^_UC' \ + > $@-t + mv $@-t $@ +# We distribute it because declared.sh relies on GNU sed. +MOSTLYCLEANFILES += libunistring.sym-t +MAINTAINERCLEANFILES += libunistring.sym +EXTRA_DIST += libunistring.sym + +# Hide undesired symbols that are defined by libunistring_la_SOURCES or +# libunistring_la_LIBADD from the global namespace, by prefixing them with +# "libunistring_". +all check install: config.h +config.h: $(BUILT_SOURCES) libunistring.sym + { echo '/* DO NOT EDIT! GENERATED AUTOMATICALLY! */'; \ + : "Avoid double inclusion, to avoid a warning about redefinition of DLL_VARIABLE."; \ + echo '#ifndef UNISTRING_CONFIG_H'; \ + echo '#define UNISTRING_CONFIG_H'; \ + echo; \ + echo '#include "../config.h"'; \ + : "All code is collected in a single library,"; \ + : "No references to variables in other libraries exist."; \ + echo '#undef DLL_VARIABLE'; \ + echo '#define DLL_VARIABLE'; \ + echo; \ + echo '#endif /* UNISTRING_CONFIG_H */'; \ + } > config.h && \ + if test -n "$(HAVE_GLOBAL_SYMBOL_PIPE)"; then \ + { \ + for f in $(libunistring_la_SOURCES) $(libunistring_la_LIBADD); do \ + case $$f in \ + *.c | *.$(OBJEXT) | *.lo ) \ + sf=`echo "$$f" | sed -e 's,\\.[^.]*$$,,'`.c; \ + test -f $$sf || sf=$(srcdir)/$$sf; \ + of=`echo "$$f" | sed -e 's,^.*/,,' -e 's,\\.[^.]*$$,,'`.$(OBJEXT); \ + $(COMPILE) -c $$sf || { rm -f config.h; exit 1; }; \ + sh ./exported.sh $$of 1>&5; \ + rm -f $$of `echo "$$of" | sed -e 's,\\.$(OBJEXT)$$,.lo,'`; \ + ;; \ + esac; \ + done; \ + } 5>&1 \ + | sed -e 's,.* ,,' | LC_ALL=C sort | LC_ALL=C uniq \ + | LC_ALL=C join -v 1 - $(srcdir)/libunistring.sym \ + | sed -e 's,^\(.*\)$$,#define \1 libunistring_\1,' > config.h-t && \ + if test -f config.h; then \ + cat config.h-t >> config.h; \ + rm -f config.h-t; \ + else \ + rm -f config.h-t; \ + exit 1; \ + fi \ + fi +MOSTLYCLEANFILES += config.h config.h-t + # Libtool's library version information for libunistring. # See the libtool documentation, section "Library interface versions". LTV_CURRENT=0 diff --git a/lib/declared.sh b/lib/declared.sh new file mode 100755 index 0000000..c254417 --- /dev/null +++ b/lib/declared.sh @@ -0,0 +1,135 @@ +#! /bin/sh +# +# Copyright (C) 2009 Free Software Foundation, Inc. +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see <http://www.gnu.org/licenses/>. +# + +# This script determines the declared global symbols in a C header file. +# Assumptions: +# - The header files are in C, with only C89 comments. +# - No use of macros with parameters. +# - All global declarations are marked with 'extern'. +# - All declarations end in ';' on the same line. +# - Not more than one symbol is declared in a declaration. + +# func_usage +# outputs to stdout the --help usage message. +func_usage () +{ + echo "\ +Usage: declared.sh [OPTION]... < SOURCE.h + +Extracts the declared global symbols of a C header file. + +Options: + --help print this help and exit + --version print version information and exit + +Report bugs to <bruno@clisp.org>." +} + +# func_version +# outputs to stdout the --version message. +func_version () +{ + echo "declared.sh (GNU libunistring)" + echo "Copyright (C) 2006, 2009 Free Software Foundation, Inc. +License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> +This is free software: you are free to change and redistribute it. +There is NO WARRANTY, to the extent permitted by law." + echo "Written by" "Bruno Haible" +} + +# func_fatal_error message +# outputs to stderr a fatal error message, and terminates the program. +func_fatal_error () +{ + echo "declared.sh: *** $1" 1>&2 + echo "declared.sh: *** Stop." 1>&2 + exit 1 +} + +# Command-line option processing. +while test $# -gt 0; do + case "$1" in + --help | --hel | --he | --h ) + func_usage + exit 0 ;; + --version | --versio | --versi | --vers | --ver | --ve | --v ) + func_version + exit 0 ;; + -- ) # Stop option prcessing + shift; break ;; + -* ) + func_fatal_error "unrecognized option: $option" + ;; + * ) + break ;; + esac +done + +if test $# -gt 0; then + func_fatal_error "too many arguments" +fi + +# A sed expression that removes ANSI C and ISO C99 comments. +sed_remove_comments=" +/[/][/*]/{ + ta + :a + s,^\\(\\([^\"'/]\\|\"\\([^\\\"]\\|[\\].\\)*\"\\|'\\([^\\']\\|[\\].\\)*'\\|[/][^\"'/*]\\|[/]\"\\([^\\\"]\\|[\\].\\)*\"\\|[/]'\\([^\\']\\|[\\].\\)*'\\)*\\)//.*,\\1, + te + s,^\\(\\([^\"'/]\\|\"\\([^\\\"]\\|[\\].\\)*\"\\|'\\([^\\']\\|[\\].\\)*'\\|[/][^\"'/*]\\|[/]\"\\([^\\\"]\\|[\\].\\)*\"\\|[/]'\\([^\\']\\|[\\].\\)*'\\)*\\)/[*]\\([^*]\\|[*][^/*]\\)*[*][*]*/,\\1 , + ta + /^\\([^\"'/]\\|\"\\([^\\\"]\\|[\\].\\)*\"\\|'\\([^\\']\\|[\\].\\)*'\\|[/][^\"'/*]\\|[/]\"\\([^\\\"]\\|[\\].\\)*\"\\|[/]'\\([^\\']\\|[\\].\\)*'\\)*[/][*]/{ + s,^\\(\\([^\"'/]\\|\"\\([^\\\"]\\|[\\].\\)*\"\\|'\\([^\\']\\|[\\].\\)*'\\|[/][^\"'/*]\\|[/]\"\\([^\\\"]\\|[\\].\\)*\"\\|[/]'\\([^\\']\\|[\\].\\)*'\\)*\\)/[*].*,\\1 , + tu + :u + n + s,^\\([^*]\\|[*][^/*]\\)*[*][*]*/,, + tv + s,^.*\$,, + bu + :v + } + :e +}" + +# Check that 'sed' supports the kind of regular expressions used in +# sed_remove_comments. The use of \| meaning alternation of basic regular +# expressions is a GNU extension. +sed_test='s,^\(\(a\|X\)*\)//.*,\1,' +sed_result=`echo 'aaa//bcd' | sed -e "$sed_test"` +test "$sed_result" = 'aaa' \ + || func_fatal_error "The 'sed' program is not GNU sed. Try installing GNU sed." + +# A sed expression that joins 'extern' declarations that are broken over +# several lines. +sed_join_multiline_externs=' +/^extern [^;]*$/{ + :a + N + s/\n/ /g + /^extern [^;]*$/{ + ba + } +}' + +# A sed expression that extracts the identifier of each 'extern' declaration. +sed_extract_extern_declared='s/^extern .* \([A-Za-z_][A-Za-z0-9_]*\) *[;(].*$/\1/p' + +sed -e "$sed_remove_comments" \ + | sed -e "$sed_join_multiline_externs" \ + | sed -n -e "$sed_extract_extern_declared" diff --git a/lib/exported.sh.in b/lib/exported.sh.in new file mode 100644 index 0000000..89e4008 --- /dev/null +++ b/lib/exported.sh.in @@ -0,0 +1,24 @@ +#! /bin/sh +# +# Copyright (C) 2006 Free Software Foundation, Inc. +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see <http://www.gnu.org/licenses/>. +# + +# This is a script that determines the exported symbols of an object file. +# This is a separate script because $(GLOBAL_SYMBOL_PIPE) cannot be used in a +# Makefile, since it may contain dollar signs. + +nm_cmd="@NM@ $1 | @GLOBAL_SYMBOL_PIPE@" +eval $nm_cmd diff --git a/m4/exported.m4 b/m4/exported.m4 new file mode 100644 index 0000000..fc37923 --- /dev/null +++ b/m4/exported.m4 @@ -0,0 +1,21 @@ +# exported.m4 serial 1 (gettext-0.18) +dnl Copyright (C) 2006, 2009 Free Software Foundation, Inc. +dnl This file is free software; the Free Software Foundation +dnl gives unlimited permission to copy and/or distribute it, +dnl with or without modifications, as long as this notice is preserved. + +dnl Prerequisites of the exported.sh script: +dnl Check for nm output filter that yields the exported symbols. +AC_DEFUN([gt_GLOBAL_SYMBOL_PIPE], [ + AC_REQUIRE([AC_PROG_NM]) dnl provided by libtool.m4 + AC_SUBST([NM]) + AC_REQUIRE([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE]) dnl provided by libtool.m4 + GLOBAL_SYMBOL_PIPE=$lt_cv_sys_global_symbol_pipe + AC_SUBST([GLOBAL_SYMBOL_PIPE]) + if test -n "$GLOBAL_SYMBOL_PIPE"; then + HAVE_GLOBAL_SYMBOL_PIPE=1 + else + HAVE_GLOBAL_SYMBOL_PIPE= + fi + AC_SUBST([HAVE_GLOBAL_SYMBOL_PIPE]) +]) diff --git a/tests/Makefile.am b/tests/Makefile.am index 7fbaa85..0ec1f3a 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -21,6 +21,9 @@ include Makefile.gnulib AUTOMAKE_OPTIONS += subdir-objects +# Ensure that ../lib/config.h is seen before ../config.h. +DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)/lib -I$(top_builddir) + # The test suite uses the 'localcharset' module. TESTS_ENVIRONMENT += @LOCALCHARSET_TESTS_ENVIRONMENT@ |