3 # Bootstrap this package from checked-out sources.
5 # Copyright (C) 2003-2009 Free Software Foundation, Inc.
7 # This program is free software: you can redistribute it and/or modify
8 # it under the terms of the GNU General Public License as published by
9 # the Free Software Foundation, either version 3 of the License, or
10 # (at your option) any later version.
12 # This program is distributed in the hope that it will be useful,
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
17 # You should have received a copy of the GNU General Public License
18 # along with this program. If not, see <http://www.gnu.org/licenses/>.
20 # Written by Paul Eggert.
25 # Ensure file names are sorted consistently across platforms.
31 # Temporary directory names.
33 bt_regex=`echo "$bt"| sed 's/\./[.]/g'`
39 Bootstrap this package from the checked-out sources.
42 --gnulib-srcdir=DIRNAME Specify the local directory where gnulib
43 sources reside. Use this if you already
44 have gnulib sources on your machine, and
45 do not want to waste your bandwidth downloading
47 --copy Copy files instead of creating symbolic links.
48 --force Attempt to bootstrap even if the sources seem
49 not to have been checked out.
50 --skip-po Do not download po files.
52 If the file $0.conf exists in the same directory as this script, its
53 contents are read as shell variables to configure the bootstrap.
55 For build prerequisites, environment variables like \$AUTOCONF and \$AMTAR
58 Running without arguments will suffice in most cases.
64 # Name of the Makefile.am
67 # List of gnulib modules needed.
70 # Any gnulib files needed that are not in modules.
73 # The command to download all .po files for a specified domain into
74 # a specified directory. Fill in the first %s is the domain name, and
75 # the second with the destination directory. Use rsync's -L and -r
76 # options because the latest/%s directory and the .po files within are
78 po_download_command_format=\
79 "rsync -Lrtvz 'translationproject.org::tp/latest/%s/' '%s'"
81 extract_package_name='
93 y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/
98 package=`sed -n "$extract_package_name" configure.ac` || exit
99 gnulib_name=lib$package
107 # Extra files from gnulib, which override files from other sources.
109 $build_aux/install-sh
112 $build_aux/texinfo.tex
114 $build_aux/config.guess
115 $build_aux/config.sub
119 # Additional gnulib-tool options to use. Use "\newline" to break lines.
120 gnulib_tool_option_extras=
122 # Other locale categories that need message catalogs.
123 EXTRA_LOCALE_CATEGORIES=
125 # Additional xgettext options to use. Use "\\\newline" to break lines.
126 XGETTEXT_OPTIONS='\\\
127 --flag=_:1:pass-c-format\\\
128 --flag=N_:1:pass-c-format\\\
129 --flag=error:3:c-format --flag=error_at_line:5:c-format\\\
132 # Package bug report address for gettext files
133 MSGID_BUGS_ADDRESS=bug-$package@gnu.org
135 # Files we don't want to import.
138 # File that should exist in the top directory of a checked out hierarchy,
139 # but not in a distribution tarball.
140 checkout_only_file=README-hacking
142 # Whether to use copies instead of symlinks.
145 # Set this to '.cvsignore .gitignore' in bootstrap.conf if you want
146 # those files to be generated in directories like lib/, m4/, and po/.
147 # Or set it to 'auto' to make this script select which to use based
148 # on which version control system (if any) is used in the source directory.
151 # find_tool ENVVAR NAMES...
152 # -------------------------
155 # Find sha1sum, named gsha1sum on MacPorts.
158 if eval test x"\$$find_tool_envvar" = x; then
161 if ($i --version </dev/null) >/dev/null 2>&1; then
167 if test x"$find_tool_res" = x; then
168 echo >&2 "$0: $find_tool_name is required"
171 ($find_tool_res --version </dev/null) >/dev/null 2>&1 || {
172 echo >&2 "$0: cannot run $find_tool_res --version"
175 eval "$find_tool_envvar=\"$find_tool_res\""
176 eval "export $find_tool_envvar"
179 # Find sha1sum, named gsha1sum on MacPorts.
180 find_tool SHA1SUM sha1sum gsha1sum
182 # Override the default configuration, if necessary.
183 # Make sure that bootstrap.conf is sourced from the current directory
184 # if we were invoked as "sh bootstrap".
186 */*) test -r "$0.conf" && . "$0.conf" ;;
187 *) test -r "$0.conf" && . ./"$0.conf" ;;
191 if test "$vc_ignore" = auto; then
193 test -d .git && vc_ignore=.gitignore
194 test -d CVS && vc_ignore="$vc_ignore .cvsignore"
197 # Translate configuration into internal form.
208 GNULIB_SRCDIR=`expr "X$option" : 'X--gnulib-srcdir=\(.*\)'`;;
212 checkout_only_file=;;
216 echo >&2 "$0: $option: unknown option"
221 if test -n "$checkout_only_file" && test ! -r "$checkout_only_file"; then
222 echo "$0: Bootstrapping from a non-checked-out distribution is risky." >&2
226 # If $STR is not already on a line by itself in $FILE, insert it,
227 # sorting the new contents of the file and replacing $FILE with the result.
228 insert_sorted_if_absent() {
231 test -f $file || touch $file
232 echo "$str" | sort -u - $file | cmp - $file > /dev/null \
233 || echo "$str" | sort -u - $file -o $file \
237 # Die if there is no AC_CONFIG_AUX_DIR($build_aux) line in configure.ac.
239 grep '^[ ]*AC_CONFIG_AUX_DIR(\['"$build_aux"'\])' configure.ac \
240 >/dev/null && found_aux_dir=yes
241 grep '^[ ]*AC_CONFIG_AUX_DIR('"$build_aux"')' configure.ac \
242 >/dev/null && found_aux_dir=yes
243 if test $found_aux_dir = no; then
244 echo "$0: expected line not found in configure.ac. Add the following:" >&2
245 echo " AC_CONFIG_AUX_DIR([$build_aux])" >&2
249 # If $build_aux doesn't exist, create it now, otherwise some bits
250 # below will malfunction. If creating it, also mark it as ignored.
251 if test ! -d $build_aux; then
253 for dot_ig in x $vc_ignore; do
254 test $dot_ig = x && continue
255 insert_sorted_if_absent $dot_ig $build_aux
259 # Note this deviates from the version comparison in automake
260 # in that it treats 1.5 < 1.5.0, and treats 1.4.4a < 1.4-p3a
261 # but this should suffice as we won't be specifying old
262 # version formats or redundant trailing .0 in bootstrap.conf.
263 # If we did want full compatibility then we should probably
264 # use m4_version_compare from autoconf.
265 sort_ver() { # sort -V is not generally available
269 # split on '.' and compare each component
272 p1=$(echo "$ver1" | cut -d. -f$i)
273 p2=$(echo "$ver2" | cut -d. -f$i)
277 elif [ ! "$p2" ]; then
280 elif [ ! "$p1" = "$p2" ]; then
281 if [ "$p1" -gt "$p2" ] 2>/dev/null; then # numeric comparison
283 elif [ "$p2" -gt "$p1" ] 2>/dev/null; then # numeric comparison
285 else # numeric, then lexicographic comparison
286 lp=$(printf "$p1\n$p2\n" | LANG=C sort -n | tail -n1)
287 if [ "$lp" = "$p2" ]; then
302 $app --version >/dev/null 2>&1 || return 1
304 $app --version 2>&1 |
305 sed -n 's/[^0-9.]*\([0-9]\{1,\}\.[.a-z0-9-]*\).*/\1/p
315 while read app req_ver; do
316 # Honor $APP variables ($TAR, $AUTOCONF, etc.)
317 appvar=`echo $app | tr '[a-z]' '[A-Z]'`
318 test "$appvar" = TAR && appvar=AMTAR
319 eval "app=\${$appvar-$app}"
320 inst_ver=$(get_version $app)
321 if [ ! "$inst_ver" ]; then
322 echo "Error: '$app' not found" >&2
324 elif [ ! "$req_ver" = "-" ]; then
325 latest_ver=$(sort_ver $req_ver $inst_ver | cut -d' ' -f2)
326 if [ ! "$latest_ver" = "$inst_ver" ]; then
327 echo "Error: '$app' version == $inst_ver is too old" >&2
328 echo " '$app' version >= $req_ver is required" >&2
338 echo "Program Min_version"
339 echo "----------------------"
341 echo "----------------------"
342 # can't depend on column -t
345 if ! printf "$buildreq" | check_versions; then
346 test -f README-prereq &&
347 echo "See README-prereq for notes on obtaining these prerequisite programs:" >&2
353 echo "$0: Bootstrapping from checked-out $package sources..."
355 # See if we can use gnulib's git-merge-changelog merge driver.
356 if test -d .git && (git --version) >/dev/null 2>/dev/null ; then
357 if git config merge.merge-changelog.driver >/dev/null ; then
359 elif (git-merge-changelog --version) >/dev/null 2>/dev/null ; then
360 echo "initializing git-merge-changelog driver"
361 git config merge.merge-changelog.name 'GNU-style ChangeLog merge driver'
362 git config merge.merge-changelog.driver 'git-merge-changelog %O %A %B'
364 echo "consider installing git-merge-changelog from gnulib"
375 git_modules_config () {
376 test -f .gitmodules && git config --file .gitmodules "$@"
381 case ${GNULIB_SRCDIR--} in
383 if git_modules_config submodule.gnulib.url >/dev/null; then
384 echo "$0: getting gnulib files..."
385 git submodule init || exit $?
386 git submodule update || exit $?
388 elif [ ! -d gnulib ]; then
389 echo "$0: getting gnulib files..."
391 trap cleanup_gnulib 1 2 13 15
393 git clone --help|grep depth > /dev/null && shallow='--depth 2' || shallow=
394 git clone $shallow git://git.sv.gnu.org/gnulib ||
402 # Redirect the gnulib submodule to the directory on the command line
404 if test -d "$GNULIB_SRCDIR"/.git && \
405 git_modules_config submodule.gnulib.url >/dev/null; then
407 GNULIB_SRCDIR=`cd $GNULIB_SRCDIR && pwd`
408 git config --replace-all submodule.gnulib.url $GNULIB_SRCDIR
409 echo "$0: getting gnulib files..."
410 git submodule update || exit $?
416 gnulib_tool=$GNULIB_SRCDIR/gnulib-tool
417 <$gnulib_tool || exit
421 download_po_files() {
424 echo "$0: getting translations into $subdir for $domain..."
425 cmd=`printf "$po_download_command_format" "$domain" "$subdir"`
429 # Download .po files to $po_dir/.reference and copy only the new
430 # or modified ones into $po_dir. Also update $po_dir/LINGUAS.
432 # Directory containing primary .po files.
433 # Overwrite them only when we're sure a .po file is new.
437 # Download *.po files into this dir.
438 # Usually contains *.s1 checksum files.
439 ref_po_dir="$po_dir/.reference"
441 test -d $ref_po_dir || mkdir $ref_po_dir || return
442 download_po_files $ref_po_dir $domain \
443 && ls "$ref_po_dir"/*.po 2>/dev/null |
444 sed 's|.*/||; s|\.po$||' > "$po_dir/LINGUAS"
446 langs=`cd $ref_po_dir && echo *.po|sed 's/\.po//g'`
447 test "$langs" = '*' && langs=x
449 case $po in x) continue;; esac
450 new_po="$ref_po_dir/$po.po"
451 cksum_file="$ref_po_dir/$po.s1"
452 if ! test -f "$cksum_file" ||
453 ! test -f "$po_dir/$po.po" ||
454 ! $SHA1SUM -c --status "$cksum_file" \
455 < "$new_po" > /dev/null; then
456 echo "updated $po_dir/$po.po..."
457 cp "$new_po" "$po_dir/$po.po" \
458 && $SHA1SUM < "$new_po" > "$cksum_file"
466 update_po_files po $package || exit
469 if test -d runtime-po; then
470 update_po_files runtime-po $package-runtime || exit
481 # If the destination directory doesn't exist, create it.
482 # This is required at least for "lib/uniwidth/cjk.h".
483 dst_dir=`dirname "$dst"`
484 if ! test -d "$dst_dir"; then
487 # If we've just created a directory like lib/uniwidth,
488 # tell version control system(s) it's ignorable.
489 # FIXME: for now, this does only one level
490 parent=`dirname "$dst_dir"`
491 for dot_ig in x $vc_ignore; do
492 test $dot_ig = x && continue
494 insert_sorted_if_absent $ig `echo "$dst_dir"|sed 's,.*/,,'`
500 test ! -h "$dst" || {
501 echo "$0: rm -f $dst" &&
506 cmp -s "$src" "$dst" || {
507 echo "$0: cp -fp $src $dst" &&
512 src_ls=`ls -diL "$src" 2>/dev/null` && set $src_ls && src_i=$1 &&
513 dst_ls=`ls -diL "$dst" 2>/dev/null` && set $dst_ls && dst_i=$1 &&
514 test "$src_i" = "$dst_i" || {
520 *//* | */../* | */./* | /*/*/*/*/*/)
521 echo >&2 "$0: invalid symlink calculation: $src -> $dst"
523 /*/*/*/*/) dot_dots=../../../;;
524 /*/*/*/) dot_dots=../../;;
525 /*/*/) dot_dots=../;;
529 echo "$0: ln -fs $dot_dots$src $dst" &&
530 ln -fs "$dot_dots$src" "$dst"
536 cp_mark_as_generated()
541 if cmp -s "$cp_src" "$GNULIB_SRCDIR/$cp_dst"; then
542 symlink_to_dir "$GNULIB_SRCDIR" "$cp_dst"
543 elif cmp -s "$cp_src" "$local_gl_dir/$cp_dst"; then
544 symlink_to_dir $local_gl_dir "$cp_dst"
547 *.[ch]) c1='/* '; c2=' */';;
548 *.texi) c1='@c '; c2= ;;
549 *.m4|*/Make*|Make*) c1='# ' ; c2= ;;
553 # If the destination directory doesn't exist, create it.
554 # This is required at least for "lib/uniwidth/cjk.h".
555 dst_dir=`dirname "$cp_dst"`
556 test -d "$dst_dir" || mkdir -p "$dst_dir"
558 if test -z "$c1"; then
559 cmp -s "$cp_src" "$cp_dst" || {
560 # Copy the file first to get proper permissions if it
561 # doesn't already exist. Then overwrite the copy.
562 echo "$0: cp -f $cp_src $cp_dst" &&
564 cp "$cp_src" "$cp_dst-t" &&
565 sed "s!$bt_regex/!!g" "$cp_src" > "$cp_dst-t" &&
566 mv -f "$cp_dst-t" "$cp_dst"
569 # Copy the file first to get proper permissions if it
570 # doesn't already exist. Then overwrite the copy.
571 cp "$cp_src" "$cp_dst-t" &&
573 echo "$c1-*- buffer-read-only: t -*- vi: set ro:$c2" &&
574 echo "${c1}DO NOT EDIT! GENERATED AUTOMATICALLY!$c2" &&
575 sed "s!$bt_regex/!!g" "$cp_src"
577 if cmp -s "$cp_dst-t" "$cp_dst"; then
580 echo "$0: cp $cp_src $cp_dst # with edits" &&
581 mv -f "$cp_dst-t" "$cp_dst"
587 version_controlled_file() {
592 grep -F "/$file/" $dir/CVS/Entries 2>/dev/null |
593 grep '^/[^/]*/[0-9]' > /dev/null && found=yes
594 elif test -d .git; then
595 git rm -n "$dir/$file" > /dev/null 2>&1 && found=yes
596 elif test -d .svn; then
597 svn log -r HEAD "$dir/$file" > /dev/null 2>&1 && found=yes
599 echo "$0: no version control for $dir/$file?" >&2
605 for dir in . `(cd $1 && find * -type d -print)`; do
608 for file in `ls -a $1/$dir`; do
611 .*) continue;; # FIXME: should all file names starting with "." be ignored?
613 test -d $1/$dir/$file && continue
614 for excluded_file in $excluded_files; do
615 test "$dir/$file" = "$excluded_file" && continue 2
617 if test $file = Makefile.am; then
618 copied=$copied${sep}$gnulib_mk; sep=$nl
619 remove_intl='/^[^#].*\/intl/s/^/#/;'"s!$bt_regex/!!g"
620 sed "$remove_intl" $1/$dir/$file | cmp - $dir/$gnulib_mk > /dev/null || {
621 echo "$0: Copying $1/$dir/$file to $dir/$gnulib_mk ..." &&
622 rm -f $dir/$gnulib_mk &&
623 sed "$remove_intl" $1/$dir/$file >$dir/$gnulib_mk
625 elif { test "${2+set}" = set && test -r $2/$dir/$file; } ||
626 version_controlled_file $dir $file; then
627 echo "$0: $dir/$file overrides $1/$dir/$file"
629 copied=$copied$sep$file; sep=$nl
630 if test $file = gettext.m4; then
631 echo "$0: patching m4/gettext.m4 to remove need for intl/* ..."
634 /^AC_DEFUN(\[AM_INTL_SUBDIR],/,/^]/c\
635 AC_DEFUN([AM_INTL_SUBDIR], [
636 /^AC_DEFUN(\[gt_INTL_SUBDIR_CORE],/,/^]/c\
637 AC_DEFUN([gt_INTL_SUBDIR_CORE], [])
639 AC_DEFUN([gl_LOCK_EARLY], [])
640 ' $1/$dir/$file >$dir/$file
642 cp_mark_as_generated $1/$dir/$file $dir/$file
647 for dot_ig in x $vc_ignore; do
648 test $dot_ig = x && continue
650 if test -n "$copied"; then
651 insert_sorted_if_absent $ig "$copied"
652 # If an ignored file name ends with .in.h, then also add
653 # the name with just ".h". Many gnulib headers are generated,
654 # e.g., stdint.in.h -> stdint.h, dirent.in.h ->..., etc.
655 # Likewise for .gperf -> .h, .y -> .c, and .sin -> .sed
656 f=`echo "$copied"|sed 's/\.in\.h$/.h/;s/\.sin$/.sed/;s/\.y$/.c/;s/\.gperf$/.h/'`
657 insert_sorted_if_absent $ig "$f"
659 # For files like sys_stat.in.h and sys_time.in.h, record as
660 # ignorable the directory we might eventually create: sys/.
661 f=`echo "$copied"|sed 's/sys_.*\.in\.h$/sys/'`
662 insert_sorted_if_absent $ig "$f"
669 # Create boot temporary directories to import from gnulib and gettext.
671 mkdir $bt $bt2 || exit
673 # Import from gnulib.
675 gnulib_tool_options="\
678 --aux-dir $bt/$build_aux\
679 --doc-base $bt/$doc_base\
681 --m4-base $bt/$m4_base/\
682 --source-base $bt/$source_base/\
683 --tests-base $bt/$tests_base\
684 --local-dir $local_gl_dir\
685 $gnulib_tool_option_extras\
687 echo "$0: $gnulib_tool $gnulib_tool_options --import ..."
688 $gnulib_tool $gnulib_tool_options --import $gnulib_modules &&
691 for file in $gnulib_files; do
692 symlink_to_dir "$GNULIB_SRCDIR" $file || exit
696 # Import from gettext.
698 grep '^[ ]*AM_GNU_GETTEXT_VERSION(' configure.ac >/dev/null || \
701 if test $with_gettext = yes; then
702 echo "$0: (cd $bt2; ${AUTOPOINT-autopoint}) ..."
703 cp configure.ac $bt2 &&
704 (cd $bt2 && ${AUTOPOINT-autopoint} && rm configure.ac) &&
705 slurp $bt2 $bt || exit
707 rm -fr $bt $bt2 || exit
709 # Remove any dangling symlink matching "*.m4" or "*.[ch]" in some
710 # gnulib-populated directories. Such .m4 files would cause aclocal to fail.
711 # The following requires GNU find 4.2.3 or newer. Considering the usual
712 # portability constraints of this script, that may seem a very demanding
713 # requirement, but it should be ok. Ignore any failure, which is fine,
714 # since this is only a convenience to help developers avoid the relatively
715 # unusual case in which a symlinked-to .m4 file is git-removed from gnulib
716 # between successive runs of this script.
717 find "$m4_base" "$source_base" \
718 -depth \( -name '*.m4' -o -name '*.[ch]' \) \
719 -type l -xtype l -delete > /dev/null 2>&1
721 # Reconfigure, getting other files.
725 "${ACLOCAL-aclocal} --force -I m4" \
726 "${AUTOCONF-autoconf} --force" \
727 "${AUTOHEADER-autoheader} --force" \
728 "${AUTOMAKE-automake} --add-missing --copy --force-missing"
730 if test "$command" = libtool; then
732 # We'd like to use grep -E, to see if any of LT_INIT,
733 # AC_PROG_LIBTOOL, AM_PROG_LIBTOOL is used in configure.ac,
734 # but that's not portable enough (e.g., for Solaris).
735 grep '^[ ]*A[CM]_PROG_LIBTOOL' configure.ac >/dev/null \
737 grep '^[ ]*LT_INIT' configure.ac >/dev/null \
739 test $use_libtool = 0 \
741 command="${LIBTOOLIZE-libtoolize} -c -f"
743 echo "$0: $command ..."
748 # Get some extra files from gnulib, overriding existing files.
749 for file in $gnulib_extra_files; do
751 */INSTALL) dst=INSTALL;;
752 build-aux/*) dst=$build_aux/`expr "$file" : 'build-aux/\(.*\)'`;;
755 symlink_to_dir "$GNULIB_SRCDIR" $file $dst || exit
758 if test $with_gettext = yes; then
759 # Create gettext configuration.
760 echo "$0: Creating po/Makevars from po/Makevars.template ..."
763 /^EXTRA_LOCALE_CATEGORIES *=/s/=.*/= '"$EXTRA_LOCALE_CATEGORIES"'/
764 /^MSGID_BUGS_ADDRESS *=/s/=.*/= '"$MSGID_BUGS_ADDRESS"'/
765 /^XGETTEXT_OPTIONS *=/{
768 '"$XGETTEXT_OPTIONS"' $${end_of_xgettext_options+}
770 ' po/Makevars.template >po/Makevars
772 if test -d runtime-po; then
773 # Similarly for runtime-po/Makevars, but not quite the same.
774 rm -f runtime-po/Makevars
776 /^DOMAIN *=.*/s/=.*/= '"$package"'-runtime/
777 /^subdir *=.*/s/=.*/= runtime-po/
778 /^MSGID_BUGS_ADDRESS *=/s/=.*/= bug-'"$package"'@gnu.org/
779 /^XGETTEXT_OPTIONS *=/{
782 '"$XGETTEXT_OPTIONS_RUNTIME"' $${end_of_xgettext_options+}
784 ' <po/Makevars.template >runtime-po/Makevars
786 # Copy identical files from po to runtime-po.
787 (cd po && cp -p Makefile.in.in *-quot *.header *.sed *.sin ../runtime-po)
791 echo "$0: done. Now you can run './configure'."
794 # indent-tabs-mode: nil