* aclocal.in: Don't pass $acdir to scan_m4_files.
[platform/upstream/automake.git] / aclocal.in
1 #!@PERL@
2 # -*- perl -*-
3 # @configure_input@
4
5 # aclocal - create aclocal.m4 by scanning configure.in
6 # Copyright (C) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
7
8 # This program is free software; you can redistribute it and/or modify
9 # it under the terms of the GNU General Public License as published by
10 # the Free Software Foundation; either version 2, or (at your option)
11 # any later version.
12
13 # This program is distributed in the hope that it will be useful,
14 # but WITHOUT ANY WARRANTY; without even the implied warranty of
15 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 # GNU General Public License for more details.
17
18 # You should have received a copy of the GNU General Public License
19 # along with this program; if not, write to the Free Software
20 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
21 # 02111-1307, USA.
22
23 # Written by Tom Tromey <tromey@cygnus.com>.
24
25 eval 'exec @PERL@ -S $0 ${1+"$@"}'
26     if 0;
27
28 # aclocal - scan configure.in and generate aclocal.m4.
29
30 # Some constants.
31 $VERSION = "@VERSION@";
32 $PACKAGE = "@PACKAGE@";
33 $prefix = "@prefix@";
34 # Note that this isn't pkgdatadir, but a separate directory.
35 $acdir = "@datadir@/aclocal";
36
37 # Some globals.
38
39 # Exit status.
40 $exit_status = 0;
41
42 # Text to output.
43 $output = '';
44
45 # Output file name.
46 $output_file = 'aclocal.m4';
47
48 # Which macros have been seen.
49 %macro_seen = ();
50
51 # Which files have been seen.
52 %file_seen = ();
53
54 # Map macro names to file names.
55 %map = ();
56
57 # Map file names to file contents.
58 %file_contents = ();
59
60 # How much to say.
61 $verbosity = 0;
62
63 # Map from obsolete macros to hints for new macros.
64 # If you change this, change the corresponding list in automake.in.
65 # FIXME: should just put this into a single file.
66 %obsolete_macros =
67     (
68      'AC_FEATURE_CTYPE', "use \`AC_HEADER_STDC'",
69      'AC_FEATURE_ERRNO', "add \`strerror' to \`AC_REPLACE_FUNCS(...)'",
70      'AC_FEATURE_EXIT', '',
71      'AC_SYSTEM_HEADER', '',
72
73      # Note that we do not handle this one, because it is still run
74      # from AM_CONFIG_HEADER.  So we deal with it specially in
75      # scan_configure.
76      # 'AC_CONFIG_HEADER', "use \`AM_CONFIG_HEADER'",
77
78      'fp_C_PROTOTYPES', "use \`AM_C_PROTOTYPES'",
79      'fp_PROG_CC_STDC', "use \`AM_PROG_CC_STDC'",
80      'fp_PROG_INSTALL', "use \`AC_PROG_INSTALL'",
81      'fp_WITH_DMALLOC', "use \`AM_WITH_DMALLOC'",
82      'fp_WITH_REGEX', "use \`AM_WITH_REGEX'",
83      'gm_PROG_LIBTOOL', "use \`AM_PROG_LIBTOOL'",
84      'jm_MAINTAINER_MODE', "use \`AM_MAINTAINER_MODE'",
85      'md_TYPE_PTRDIFF_T', "use \`AM_TYPE_PTRDIFF_T'",
86      'ud_PATH_LISPDIR', "use \`AM_PATH_LISPDIR'",
87      'ud_GNU_GETTEXT', "use \`AM_GNU_GETTEXT'",
88
89      # Now part of autoconf proper, under a different name.
90      'AM_FUNC_FNMATCH', "use \`AC_FUNC_FNMATCH'",
91      'fp_FUNC_FNMATCH', "use \`AC_FUNC_FNMATCH'",
92      'AM_SANITY_CHECK_CC', "automatically done by \`AC_PROG_CC'",
93      'AM_PROG_INSTALL', "use \`AC_PROG_INSTALL'",
94      'AM_EXEEXT', "use \`AC_EXEEXT'",
95      'AM_CYGWIN32', "use \`AC_CYGWIN'",
96      'AM_MINGW32', "use \`AC_MINGW32'",
97      'AM_FUNC_MKTIME', "use \`AC_FUNC_MKTIME'",
98
99 # These aren't quite obsolete.
100 #      'md_PATH_PROG',
101      );
102
103 # Regexp to match the above macros.
104 $obsolete_rx = '(' . join ('|', keys %obsolete_macros) . ')';
105
106 # Matches a macro definition.
107 $ac_defun_rx = "AC_DEFUN\\(\\[?([^],)\n]+)\\]?";
108
109 # Matches an AC_REQUIRE line.
110 $ac_require_rx = "AC_REQUIRE\\(\\[?([^])]*)\\]?\\)";
111
112 \f
113
114 local (@dirlist) = &parse_arguments (@ARGV);
115 &scan_m4_files (@dirlist);
116 &scan_configure;
117 if (! $exit_status)
118 {
119     &write_aclocal;
120 }
121 &check_acinclude;
122
123 exit $exit_status;
124
125 ################################################################
126
127 # Print usage and exit.
128 sub usage
129 {
130     local ($status) = @_;
131
132     print "Usage: aclocal [OPTIONS] ...\n\n";
133     print "Generate aclocal.m4 by scanning configure.in\n
134   --acdir=DIR           directory holding config files
135   --help                print this help, then exit
136   -I DIR                add directory to search list for .m4 files
137   --output=FILE         put output in FILE (default aclocal.m4)
138   --print-ac-dir        print name of directory holding m4 files
139   --verbose             don't be silent
140   --version             print version number, then exit
141
142 Report bugs to <bug-automake\@gnu.org>.\n";
143
144     exit $status;
145 }
146
147 # Parse command line.
148 sub parse_arguments
149 {
150     local (@arglist) = @_;
151     local (@dirlist);
152     local ($print_and_exit) = 0;
153
154     while (@arglist)
155     {
156         if ($arglist[0] =~ /^--acdir=(.+)$/)
157         {
158             $acdir = $1;
159         }
160         elsif ($arglist[0] =~/^--output=(.+)$/)
161         {
162             $output_file = $1;
163         }
164         elsif ($arglist[0] eq '-I')
165         {
166             shift (@arglist);
167             push (@dirlist, $arglist[0]);
168         }
169         elsif ($arglist[0] eq '--print-ac-dir')
170         {
171             $print_and_exit = 1;
172         }
173         elsif ($arglist[0] eq '--verbose')
174         {
175             ++$verbosity;
176         }
177         elsif ($arglist[0] eq '--version')
178         {
179             print "aclocal (GNU $PACKAGE) $VERSION\n\n";
180             print "Copyright (C) 1999 Free Software Foundation, Inc.\n";
181             print "This is free software; see the source for copying conditions.  There is NO\n";
182             print "warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n";
183             print "Written by Tom Tromey <tromey\@cygnus.com>\n";
184             exit 0;
185         }
186         elsif ($arglist[0] eq '--help')
187         {
188             &usage (0);
189         }
190         else
191         {
192             die "aclocal: unrecognized option -- \`$arglist[0]'\nTry \`aclocal --help' for more information.\n";
193         }
194
195         shift (@arglist);
196     }
197
198     if ($print_and_exit)
199     {
200         print $acdir, "\n";
201         exit 0;
202     }
203
204     # Search our install directory last.
205     push (@dirlist, $acdir);
206
207     return @dirlist;
208 }
209
210 ################################################################
211
212 sub scan_configure
213 {
214     open (CONFIGURE, "configure.in")
215         || die "aclocal: couldn't open \`configure.in': $!\n";
216
217     # Make sure we include acinclude.m4 if it exists.
218     if (-f 'acinclude.m4')
219     {
220         &add_file ('acinclude.m4');
221     }
222
223     while (<CONFIGURE>)
224     {
225         # Remove comments from current line.
226         s/\bdnl\b.*$//;
227         s/\#.*$//;
228
229         if (/$obsolete_rx/o)
230         {
231             local ($hint) = '';
232             if ($obsolete_macros{$1} ne '')
233             {
234                 $hint = '; ' . $obsolete_macros{$1};
235             }
236             warn "aclocal: configure.in: $.: \`$1' is obsolete$hint\n";
237             $exit_status = 1;
238             next;
239         }
240
241         # Search for things we know about.  The "search" sub is
242         # constructed dynamically by scan_m4_files.
243         if (! &search && /(^|\s+)(AM_[A-Z_]+)/)
244         {
245             # Macro not found, but AM_ prefix found.
246             warn "aclocal: configure.in: $.: macro \`$2' not found in library\n";
247             $exit_status = 1;
248         }
249     }
250
251     close (CONFIGURE);
252 }
253
254 ################################################################
255
256 # Check macros in acinclude.m4.  If one is not used, warn.
257 sub check_acinclude
258 {
259     local ($key);
260
261     foreach $key (keys %map)
262     {
263         next unless $map{$key} eq 'acinclude.m4';
264         if (! $macro_seen{$key})
265         {
266             # FIXME: should print line number of acinclude.m4.
267             warn "aclocal: macro \`$key' defined in acinclude.m4 but never used\n";
268         }
269     }
270 }
271
272 ################################################################
273
274 # Scan all the installed m4 files and construct a map.
275 sub scan_m4_files
276 {
277     local (@dirlist) = @_;
278
279     # First, scan acinclude.m4 if it exists.
280     if (-f 'acinclude.m4')
281     {
282         $file_contents{'acinclude.m4'} = &scan_file ('acinclude.m4');
283     }
284
285     local ($m4dir);
286     foreach $m4dir (@dirlist)
287     {
288         opendir (DIR, $m4dir)
289             || die "aclocal: couldn't open directory \`$m4dir': $!\n";
290         local ($file, $fullfile, $expr);
291         foreach $file (sort grep (! /^\./, readdir (DIR)))
292         {
293             # Only examine .m4 files.
294             next unless $file =~ /\.m4$/;
295
296             # Skip some files when running out of srcdir.
297             next if $file eq 'aclocal.m4';
298
299             $fullfile = $m4dir . '/' . $file;
300             $file_contents{$fullfile} = &scan_file ($fullfile);
301         }
302         closedir (DIR);
303     }
304
305     # Construct a new function that does the searching.  We use a
306     # function (instead of just evalling $search in the loop) so that
307     # "die" is correctly and easily propagated if run.
308     local ($search, $expr, $key) = '';
309     foreach $key (reverse sort keys %map)
310     {
311         # EXPR is a regexp matching the name of the macro.
312         ($expr = $key) =~ s/(\W)/\\$1/g;
313         $search .= ("if (/" . $expr . "/) { & add_macro (" . $key
314                     . "); return 1; }\n");
315     }
316     $search .= "return 0;\n";
317     eval 'sub search { ' . $search . '};';
318     die "internal error: $@\n search is $search " if $@;
319 }
320
321 ################################################################
322
323 # Add a macro to the output.
324 sub add_macro
325 {
326     local ($macro) = @_;
327
328     # We want to ignore AC_ macros.  However, if an AC_ macro is
329     # defined in (eg) acinclude.m4, then we want to make sure we mark
330     # it as seen.
331     return if $macro =~ /^AC_/ && ! defined $map{$macro};
332
333     if (! defined $map{$macro})
334     {
335         warn "aclocal: macro \`$macro' required but not defined\n";
336         $exit_status = 1;
337         return;
338     }
339
340     print STDERR "saw macro $macro\n" if $verbosity;
341     $macro_seen{$macro} = 1;
342     &add_file ($map{$macro});
343 }
344
345 # Add a file to output.
346 sub add_file
347 {
348     local ($file) = @_;
349
350     # Only add a file once.
351     return if ($file_seen{$file});
352     $file_seen{$file} = 1;
353
354     $output .= $file_contents{$file} . "\n";
355     local ($a, @rlist);
356     foreach (split ("\n", $file_contents{$file}))
357     {
358         # This is a hack for Perl 4.
359         $a = $_;
360         if ($a =~ /$ac_require_rx/g)
361         {
362             push (@rlist, $1);
363         }
364
365         # This function constructed dynamically.
366         if (! &search && /(^|\s+)(AM_[A-Z_]+)/)
367         {
368             # Macro not found, but AM_ prefix found.
369             warn "aclocal: configure.in: $.: macro \`$2' not found in library\n";
370             $exit_status = 1;
371         }
372     }
373
374     local ($macro);
375     foreach $macro (@rlist)
376     {
377         &add_macro ($macro);
378     }
379 }
380
381 # Scan a single M4 file.  Return contents.
382 sub scan_file
383 {
384     local ($file) = @_;
385
386     open (FILE, $file)
387         || die "aclocal: couldn't open \`$file': $!\n";
388     local ($contents) = '';
389     while (<FILE>)
390     {
391         # Ignore `##' lines.
392         next if /^##/;
393
394         $contents .= $_;
395
396         if (/$ac_defun_rx/)
397         {
398             if (! defined $map{$1})
399             {
400                 $map{$1} = $file;
401             }
402             elsif ($map{$1} eq $file)
403             {
404                 # You basically never want a macro in the same .m4
405                 # file twice.
406                 warn "aclocal: $file: $.: duplicated macro \`$1'\n";
407                 $exit_status = 1;
408             }
409             print STDERR "Found macro $1 in $file: $.\n" if $verbosity;
410         }
411     }
412     close (FILE);
413
414     return $contents;
415 }
416
417 ################################################################
418
419 # Write output.
420 sub write_aclocal
421 {
422     return if ! length ($output);
423
424     print STDERR "Writing $output_file\n" if $verbosity;
425
426     open (ACLOCAL, "> " . $output_file)
427         || die "aclocal: couldn't open \`$output_file' for writing: $!\n";
428     print ACLOCAL "dnl $output_file generated automatically by aclocal $VERSION\n";
429     print ACLOCAL "\
430 dnl Copyright (C) 1994, 1995-8, 1999 Free Software Foundation, Inc.
431 dnl This file is free software; the Free Software Foundation
432 dnl gives unlimited permission to copy and/or distribute it,
433 dnl with or without modifications, as long as this notice is preserved.
434
435 dnl This program is distributed in the hope that it will be useful,
436 dnl but WITHOUT ANY WARRANTY, to the extent permitted by law; without
437 dnl even the implied warranty of MERCHANTABILITY or FITNESS FOR A
438 dnl PARTICULAR PURPOSE.
439
440 ";
441     print ACLOCAL $output;
442     close (ACLOCAL);
443 }