maint-tool revision 1.1.1.7
1#!/usr/bin/perl 2# -*- perl -*- 3 4# Copyright (C) 2001-2022 Free Software Foundation, Inc. 5# 6# This file is part of the libiberty library. 7# Libiberty is free software; you can redistribute it and/or 8# modify it under the terms of the GNU Library General Public 9# License as published by the Free Software Foundation; either 10# version 2 of the License, or (at your option) any later version. 11# 12# Libiberty 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 GNU 15# Library General Public License for more details. 16# 17# You should have received a copy of the GNU Library General Public 18# License along with libiberty; see the file COPYING.LIB. If not, 19# write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor, 20# Boston, MA 02110-1301, USA. 21# 22# Originally written by DJ Delorie <dj@redhat.com> 23 24 25# This is a trivial script which checks the lists of C and O files in 26# the Makefile for consistency. 27 28$mode = shift; 29$srcdir = "."; 30 31if ($mode eq "-s") { 32 $srcdir = shift; 33 $mode = shift; 34} 35 36&missing() if $mode eq "missing"; 37&undoc() if $mode eq "undoc"; 38&deps() if $mode eq "deps"; 39 40exit 0; 41 42format STDOUT = 43^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<~ 44$out 45 ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<~~ 46$out 47. 48 49###################################################################### 50 51sub missing { 52 53 opendir(S, $srcdir); 54 while ($f = readdir S) { 55 $have{$f} = 1; 56 } 57 closedir(S); 58 opendir(S, "."); 59 while ($f = readdir S) { 60 $have{$f} = 1; 61 } 62 closedir(S); 63 64 for $a (@ARGV) { 65 $listed{$a} = 1; 66 $have{$a} = 0; 67 } 68 69 for $f (sort keys %have) { 70 next unless $have{$f}; 71 if ($f =~ /\.c$/) { 72 print "S $f\n"; 73 } 74 } 75 for $f (sort keys %listed) { 76 if ($f =~ /(.*)\.c$/) { 77 $base = $1; 78 if (! $listed{"./$base.o"}) { 79 print "O $f\n"; 80 } 81 } 82 } 83} 84 85###################################################################### 86 87sub undoc { 88 89 opendir(S, $srcdir); 90 while ($file = readdir S) { 91 if ($file =~ /\.texi$/) { 92 open(T, "$srcdir/$file"); 93 while (<T>) { 94 if (/^\@deftype[^\(]* ([^\s\(]+) *\(/) { 95 $documented{$1} = 1; 96 } 97 } 98 close(T); 99 } 100 if ($file =~ /\.c$/) { 101 open(C, "$srcdir/$file"); 102 while (<C>) { 103 if (/\@undocumented (\S+)/) { 104 $documented{$1} = 1; 105 } 106 if (/^static /) { 107 if (! /[\(;]/) { 108 s/[\r\n]+$/ /; 109 $_ .= <C>; 110 } 111 while ($_ =~ /\([^\)]*$/) { 112 s/[\r\n]+$/ /; 113 $_ .= <C>; 114 } 115 } 116 s/ VPARAMS([ \(])/$1/; 117 s/PREFIX\(([^\)]*)\)/byte_$1/; 118 if (/^static [^\(]* ([^\s\(]+) *\(.*\)$/) { 119 $documented{$1} = 1; 120 } 121 } 122 } 123 } 124 closedir(D); 125 126 # $out = join(' ', sort keys %documented); 127 # write; 128 # print "\n"; 129 130 system "etags $srcdir/*.c $srcdir/../include/*.h"; 131 open(TAGS, "TAGS"); 132 while (<TAGS>) { 133 s/[\r\n]+$//; 134 if (/^\014$/) { 135 $filename = <TAGS>; 136 $filename =~ s/[\r\n]+$//; 137 $filename =~ s/,\d+$//; 138 $filename =~ s@.*[/\\]@@; 139 next; 140 } 141 if ($filename =~ /\.c$/ ) { 142 next unless /^[_a-zA-Z]/; 143 } else { 144 next unless /^\# *define/; 145 s/\# *define *//; 146 } 147 148 s/ VPARAMS//; 149 s/ *\177.*//; 150 s/,$//; 151 s/DEFUN\(//; 152 s/\(//; 153 154 next if /^static /; 155 next if /\s/; 156 next if /^_/; 157 next if $documented{$_}; 158 next if /_H_?$/; 159 160 if ($seen_in{$_} ne $filename) { 161 $saw{$_} ++; 162 } 163 $seen_in{$_} = $filename; 164 } 165 166 for $k (keys %saw) { 167 delete $saw{$k} if $saw{$k} > 1; 168 } 169 170 for $k (sort keys %saw) { 171 $fromfile{$seen_in{$k}} .= " " if $fromfile{$seen_in{$k}}; 172 $fromfile{$seen_in{$k}} .= $k; 173 } 174 175 for $f (sort keys %fromfile) { 176 $out = "$f: $fromfile{$f}"; 177 write; 178 } 179} 180 181###################################################################### 182 183sub deps_for { 184 my($f) = @_; 185 my(%d); 186 open(F, $f); 187 %d = (); 188 while (<F>) { 189 if (/^#\s*include\s+["<](.*)[">]/) { 190 $d{$1} = 1; 191 } 192 } 193 close(F); 194 return keys %d; 195} 196 197sub canonicalize { 198 my ($p) = @_; 199 0 while $p =~ s@/\./@/@g; 200 0 while $p =~ s@^\./@@g; 201 0 while $p =~ s@/[^/]+/\.\./@/@g; 202 return $p; 203} 204 205sub locals_first { 206 my ($a,$b) = @_; 207 return -1 if $a eq "config.h"; 208 return 1 if $b eq "config.h"; 209 return $a cmp $b; 210} 211 212sub deps { 213 214 $crule = "\tif [ x\"\$(PICFLAG)\" != x ]; then \\\n"; 215 $crule .= "\t \$(COMPILE.c) \$(PICFLAG) \$< -o pic/\$@; \\\n"; 216 $crule .= "\telse true; fi\n"; 217 $crule .= "\tif [ x\"\$(NOASANFLAG)\" != x ]; then \\\n"; 218 $crule .= "\t \$(COMPILE.c) \$(PICFLAG) \$(NOASANFLAG) \$< -o noasan/\$@; \\\n"; 219 $crule .= "\telse true; fi\n"; 220 $crule .= "\t\$(COMPILE.c) \$< \$(OUTPUT_OPTION)\n"; 221 $crule .= "\n"; 222 223 $incdir = shift @ARGV; 224 225 opendir(INC, $incdir); 226 while ($f = readdir INC) { 227 next unless $f =~ /\.h$/ || $f =~ /\.def$/; 228 $mine{$f} = "\$(INCDIR)/$f"; 229 $deps{$f} = join(' ', &deps_for("$incdir/$f")); 230 } 231 $mine{'config.h'} = "config.h"; 232 233 opendir(INC, $srcdir); 234 while ($f = readdir INC) { 235 next unless $f =~ /\.h$/; 236 $mine{$f} = "\$(srcdir)/$f"; 237 $deps{$f} = join(' ', &deps_for("$srcdir/$f")); 238 } 239 $mine{'config.h'} = "config.h"; 240 241 open(IN, "$srcdir/Makefile.in"); 242 open(OUT, ">$srcdir/Makefile.tmp"); 243 while (<IN>) { 244 last if /remainder of this file/; 245 print OUT; 246 } 247 print OUT "# The dependencies in the remainder of this file are automatically\n"; 248 print OUT "# generated by \"make maint-deps\". Manual edits will be lost.\n\n"; 249 250 opendir(S, $srcdir); 251 for $f (sort readdir S) { 252 if ($f =~ /\.c$/) { 253 254 %scanned = (); 255 @pending = &deps_for("$srcdir/$f"); 256 while (@pending) { 257 @tmp = @pending; 258 @pending = (); 259 for $p (@tmp) { 260 next unless $mine{$p}; 261 if (!$scanned{$p}) { 262 push(@pending, split(' ', $deps{$p})); 263 $scanned{$p} = 1; 264 } 265 } 266 } 267 @deps = sort { &locals_first($a,$b) } keys %scanned; 268 $obj = $f; 269 $obj =~ s/\.c$/.\$(objext)/; 270 $obj = "./$obj:"; 271 if ($#deps >= 0) { 272 print OUT "$obj \$(srcdir)/$f"; 273 $len = length("$obj $f"); 274 for $dt (@deps) { 275 $d = $mine{$dt}; 276 if ($len + length($d) > 70) { 277 printf OUT " \\\n\t$d"; 278 $len = 8 + length($d); 279 } else { 280 print OUT " $d"; 281 $len += length($d) + 1; 282 } 283 } 284 print OUT "\n"; 285 } else { 286 print OUT "$obj \$(srcdir)/$f\n"; 287 } 288 $c = $crule; 289 $c =~ s@\$\<@\$\(srcdir\)\/$f@g; 290 print OUT $c; 291 } 292 } 293 closedir(S); 294 close(IN); 295 close(OUT); 296 297 rename("$srcdir/Makefile.tmp", "$srcdir/Makefile.in"); 298} 299