]>
Commit | Line | Data |
---|---|---|
7afe1b4d PB |
1 | #!/bin/sh |
2 | # | |
3 | # SYNOPSIS | |
d7943819 | 4 | # fixproto TARGET-DIR SOURCE-DIR-ALL SOURCE-DIR-STD |
7afe1b4d PB |
5 | # |
6 | # COPYRIGHT | |
cbbf876b NN |
7 | # Copyright (C) 1993, 1994, 1997, 1998, 2002, 2003 |
8 | # Free Software Foundation, Inc. | |
1322177d | 9 | # This file is part of GCC. |
7afe1b4d | 10 | # |
1322177d | 11 | # GCC is free software; you can redistribute it and/or modify |
7afe1b4d PB |
12 | # it under the terms of the GNU General Public License as published by |
13 | # the Free Software Foundation; either version 2, or (at your option) | |
14 | # any later version. | |
15 | # | |
1322177d | 16 | # GCC is distributed in the hope that it will be useful, |
7afe1b4d PB |
17 | # but WITHOUT ANY WARRANTY; without even the implied warranty of |
18 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
19 | # GNU General Public License for more details. | |
20 | # | |
21 | # You should have received a copy of the GNU General Public License | |
1322177d | 22 | # along with GCC; see the file COPYING. If not, write to |
366ccddb KC |
23 | # the Free Software Foundation, 51 Franklin Street, Fifth Floor, |
24 | # Boston, MA 02110-1301, USA. | |
7afe1b4d PB |
25 | # |
26 | # DESCRIPTION | |
1322177d | 27 | # Adjunct script for GCC to populate a directory with ANSI, |
7afe1b4d PB |
28 | # Posix.1, and C++ compatible header files. |
29 | # | |
d7943819 PB |
30 | # Each file found under SOURCE-DIR-ALL is analyzed and "fixed." |
31 | # Only standard ANSI/POSIX files found under SOURCE-DIR-STD | |
32 | # are analyzed and "fixed." | |
7afe1b4d PB |
33 | # The SOURCE-DIRs are searched in order; a file found |
34 | # under multiple SOURCE-DIRs is only handled for the first one. | |
35 | # | |
36 | # STRATEGY | |
37 | # Each include file is fed through cpp, and the scan-decls program | |
38 | # parses it, and emits any found function declarations. | |
aab7bd19 | 39 | # The fix-header program analyzes the scan-decls output, |
7afe1b4d PB |
40 | # together with the original include file, and writes a "fixed" |
41 | # include file, if needed. | |
42 | # | |
aab7bd19 | 43 | # The comment at the beginning of fix-header.c lists specifically |
7afe1b4d PB |
44 | # what kind of changes are made. |
45 | # | |
46 | # NOTE | |
47 | # Some file space will be wasted, because the original header | |
48 | # files are copied. An earlier version just included the original | |
49 | # by "reference", using GNU cpp's #include_next mechanism. | |
50 | # This is currently not done, partly because #include_next is | |
9faa82d8 | 51 | # fragile (susceptible to version incompatibilities, and depends |
7afe1b4d PB |
52 | # and GCC-specific features), and partly for performance reasons. |
53 | # | |
54 | # AUTHORS | |
55 | # Ron Guilmette (rfg@netcom.com) (original idea and code) | |
56 | # Per Bothner (bothner@cygnus.com) (major re-write) | |
57 | ||
bcf1ba1d AO |
58 | dirname=`echo "$0" | sed 's,^[^/]*$,.,;s,//*[^/]*$,,'` |
59 | progname=`echo "$0" | sed 's,.*/,,'` | |
1e6347d8 | 60 | original_dir=`${PWDCMD-pwd}` |
1a655ca3 | 61 | FIX_HEADER=${FIX_HEADER-$original_dir/fix-header} |
e93ce7d4 | 62 | DEFINES="-D__STDC__=0 -D__cplusplus ${FIXPROTO_DEFINES}" |
e9cd0b25 | 63 | |
bcf1ba1d AO |
64 | if mkdir -p . 2> /dev/null; then |
65 | # Great, mkdir accepts -p | |
66 | mkinstalldirs="mkdir -p" | |
67 | else | |
68 | # We expect mkinstalldirs to be passed in the environment. | |
69 | # If it is not, assume it is in the directory that contains this script. | |
70 | mkinstalldirs=${mkinstalldirs-"/bin/sh $dirname/mkinstalldirs"} | |
71 | if $mkinstalldirs . 2> /dev/null; then | |
72 | : | |
73 | else | |
74 | # But, in case of failure, fallback to plain mkdir, and hope it works | |
75 | mkinstalldirs=mkdir | |
76 | fi | |
77 | fi | |
78 | ||
7afe1b4d PB |
79 | if [ `echo $1 | wc -w` = 0 ] ; then |
80 | echo $progname\: usage\: $progname target-dir \[ source-dir \.\.\. \] | |
81 | exit 1 | |
82 | fi | |
d7943819 | 83 | |
f6ae488b | 84 | std_files="ctype.h dirent.h errno.h curses.h fcntl.h grp.h locale.h math.h pwd.h setjmp.h signal.h stdio.h stdlib.h string.h sys/socket.h sys/stat.h sys/times.h sys/resource.h sys/utsname.h sys/wait.h tar.h termios.h time.h unistd.h utime.h" |
d7943819 | 85 | |
7afe1b4d | 86 | rel_target_dir=$1 |
d7943819 PB |
87 | # All files in $src_dir_all (normally same as $rel_target_dir) are |
88 | # processed. | |
89 | src_dir_all=$2 | |
90 | # In $src_dir_std (normally same as /usr/include), only the | |
91 | # "standard" ANSI/POSIX files listed in $std_files are processed. | |
92 | src_dir_std=$3 | |
7afe1b4d | 93 | |
87cf27fe LB |
94 | case $rel_target_dir in |
95 | /* | [A-Za-z]:[\\/]*) | |
96 | abs_target_dir=$rel_target_dir | |
97 | ;; | |
98 | *) | |
99 | abs_target_dir=$original_dir/$rel_target_dir | |
100 | ;; | |
101 | esac | |
7afe1b4d | 102 | |
e9cd0b25 PB |
103 | # Determine whether this system has symbolic links. |
104 | if ln -s X $rel_target_dir/ShouldNotExist 2>/dev/null; then | |
105 | rm -f $rel_target_dir/ShouldNotExist | |
106 | LINKS=true | |
107 | elif ln -s X /tmp/ShouldNotExist 2>/dev/null; then | |
108 | rm -f /tmp/ShouldNotExist | |
109 | LINKS=true | |
110 | else | |
111 | LINKS=false | |
112 | fi | |
113 | ||
7afe1b4d PB |
114 | if [ \! -d $abs_target_dir ] ; then |
115 | echo $progname\: creating directory $rel_target_dir | |
bcf1ba1d | 116 | $mkinstalldirs $abs_target_dir |
7afe1b4d PB |
117 | fi |
118 | ||
119 | echo $progname\: populating \`$rel_target_dir\' | |
120 | ||
7afe1b4d PB |
121 | include_path="" |
122 | ||
123 | if [ `echo $* | wc -w` != 0 ] ; then | |
d7943819 | 124 | for rel_source_dir in $src_dir_all $src_dir_std; do |
87cf27fe LB |
125 | case $rel_source_dir in |
126 | /* | [A-Za-z]:[\\/]*) | |
127 | abs_source_dir=$rel_source_dir | |
128 | ;; | |
129 | *) | |
130 | abs_source_dir=$original_dir/$rel_source_dir | |
131 | ;; | |
132 | esac | |
7afe1b4d PB |
133 | include_path="$include_path -I$abs_source_dir" |
134 | done | |
135 | fi | |
136 | ||
137 | done_dirs="" | |
7a790837 | 138 | subdirs_made="" |
e9cd0b25 | 139 | echo "" >fixproto.list |
7afe1b4d | 140 | |
d7943819 PB |
141 | for code in ALL STD ; do |
142 | ||
143 | subdirs="." | |
144 | ||
145 | case $code in | |
146 | ALL) | |
147 | rel_source_dir=$src_dir_all | |
e9cd0b25 | 148 | |
d7943819 PB |
149 | dirs="." |
150 | levels=2 | |
151 | while $LINKS && test -n "$dirs" -a $levels -gt 0 | |
152 | do | |
153 | levels=`expr $levels - 1` | |
154 | newdirs= | |
155 | for d in $dirs ; do | |
156 | # Find all directories under $d, relative to $d, excluding $d itself. | |
12a3cb7a RS |
157 | # Assume directory names ending in CC or containing ++ are |
158 | # for C++, so skip those. | |
d7943819 | 159 | subdirs="$subdirs "`cd $rel_source_dir/$d; find . -type d -print | \ |
12a3cb7a | 160 | sed -e '/^\.$/d' -e "s|^\./|${d}/|" -e 's|^\./||' \ |
b9a48d63 | 161 | -e '/CC$/d' -e '/[+][+]/d'` |
d7943819 PB |
162 | links= |
163 | links=`cd $rel_source_dir; find $d/. -type l -print | \ | |
e9cd0b25 | 164 | sed -e "s|$d/./|$d/|" -e 's|^\./||'` |
d7943819 PB |
165 | for link in $links --dummy-- ; do |
166 | test -d $rel_source_dir/$link/. && newdirs="$newdirs $link" | |
167 | done | |
e9cd0b25 | 168 | done |
d7943819 PB |
169 | dirs="$newdirs" |
170 | subdirs="$subdirs $newdirs" | |
7afe1b4d | 171 | done |
d7943819 PB |
172 | ;; |
173 | STD) | |
174 | rel_source_dir=$src_dir_std | |
175 | ;; | |
176 | esac | |
177 | ||
87cf27fe LB |
178 | case $rel_source_dir in |
179 | /* | [A-Za-z]:[\\/]*) | |
180 | abs_source_dir=$rel_source_dir | |
181 | ;; | |
182 | *) | |
183 | abs_source_dir=$original_dir/$rel_source_dir | |
184 | ;; | |
185 | esac | |
d7943819 PB |
186 | |
187 | if [ \! -d $abs_source_dir ] ; then | |
188 | echo $progname\: warning\: no such directory\: \`$rel_source_dir\' | |
189 | continue | |
190 | fi | |
191 | ||
192 | for rel_source_subdir in $subdirs; do | |
e9cd0b25 | 193 | |
e9cd0b25 PB |
194 | abs_target_subdir=${abs_target_dir}/${rel_source_subdir} |
195 | if [ \! -d $abs_target_subdir ] ; then | |
bcf1ba1d | 196 | if $mkinstalldirs $abs_target_subdir ; then |
7a790837 MH |
197 | subdirs_made="$abs_target_subdir $subdirs_made" |
198 | fi | |
e9cd0b25 PB |
199 | fi |
200 | # Append "/"; remove initial "./". Hence "." -> "" and "sys" -> "sys/". | |
201 | rel_source_prefix=`echo $rel_source_subdir | sed -e 's|$|/|' -e 's|^./||'` | |
7afe1b4d | 202 | |
d7943819 PB |
203 | case $code in |
204 | ALL) | |
205 | # The 'sed' is in case the *.h matches nothing, which yields "*.h" | |
206 | # which would then get re-globbed in the current directory. Sigh. | |
207 | rel_source_files=`cd ${abs_source_dir}/${rel_source_subdir}; echo *.h | sed -e 's|[*].h|NONE|'` | |
208 | ;; | |
209 | ||
210 | STD) | |
211 | files_to_check="$std_files" | |
212 | rel_source_files="" | |
213 | ||
214 | # Also process files #included by the $std_files. | |
215 | while [ -n "${files_to_check}" ] | |
216 | do | |
217 | new_files_to_check="" | |
218 | for file in $files_to_check ; do | |
fdd78221 | 219 | xxfile=`echo $file | sed -e 's|/\([^/\.][^/\.]*\)/\.\./|/|'` |
9080bb7f RS |
220 | # Create the dir where this file will go when fixed. |
221 | xxdir=`echo ./$file | sed -e 's|/[^/]*$||'` | |
222 | if [ \! -d $abs_target_subdir/$xxdir ] ; then | |
bcf1ba1d | 223 | if $mkinstalldirs $abs_target_subdir/$xxdir ; then |
7a790837 MH |
224 | subdirs_made="$abs_target_subdir/$xxdir $subdirs_made" |
225 | fi | |
9080bb7f | 226 | fi |
fdd78221 RS |
227 | # Just in case we have edited out a symbolic link |
228 | if [ -f $src_dir_std/$file -a -f $src_dir_std/$xxfile ] ; then | |
229 | file=$xxfile | |
230 | fi | |
d7943819 PB |
231 | case " $rel_source_files " in |
232 | *" ${file} "*) | |
233 | # Already seen $file; nothing to do | |
234 | ;; | |
235 | *) | |
41b21cfc PB |
236 | if test -f $src_dir_std/$file ; then |
237 | rel_dir=`echo $file | sed -n -e 's|^\(.*/\)[^/]*$|\1|p'` | |
238 | # For #include "foo.h", that might be either "foo.h" | |
239 | # or "${rel_dir}foo.h (or something bogus). | |
240 | new_files_to_check="$new_files_to_check "`sed -n \ | |
d7943819 | 241 | -e 's@ @ @g' \ |
41b21cfc PB |
242 | -e 's@^ *# *include *<\([^>]*\)>.*$@\1@p' -e \ |
243 | 's@^ *# *include *\"\([^\"]*\)\".*$@\1 '$rel_dir'\1@p'\ | |
244 | <$src_dir_std/$file` | |
245 | rel_source_files="$rel_source_files $file" | |
246 | fi | |
d7943819 PB |
247 | ;; |
248 | esac | |
249 | done | |
250 | files_to_check="$new_files_to_check" | |
251 | done | |
252 | rel_source_files="$rel_source_files" | |
253 | ;; | |
254 | esac | |
7afe1b4d | 255 | |
e9cd0b25 PB |
256 | for filename in $rel_source_files ; do |
257 | rel_source_file=${rel_source_prefix}${filename} | |
7afe1b4d PB |
258 | abs_source_file=$abs_source_dir/$rel_source_file |
259 | abs_target_file=$abs_target_dir/$rel_source_file | |
260 | ||
e9cd0b25 PB |
261 | if test "$filename" = 'NONE' ; then |
262 | echo "(No *.h files in $abs_source_dir/$rel_source_subdir)" | |
7afe1b4d PB |
263 | # If target file exists, check if was written while processing one |
264 | # of the earlier source directories; if so ignore it. | |
e9cd0b25 PB |
265 | elif test -f $abs_target_file -a -n "$done_dirs" \ |
266 | && grep "$rel_source_file" fixproto.list >/dev/null | |
267 | then true | |
7afe1b4d | 268 | else |
b3ca463c | 269 | $FIX_HEADER $rel_source_file $abs_source_file $abs_target_file ${DEFINES} $include_path |
01b2995f | 270 | if test $? != 0 ; then exit 1 ; fi |
e9cd0b25 | 271 | echo "${rel_source_file}" >>fixproto.list |
7afe1b4d PB |
272 | fi |
273 | done | |
e9cd0b25 | 274 | done |
7afe1b4d | 275 | done_dirs="$done_dir $rel_source_dir" |
d7943819 | 276 | done |
7afe1b4d | 277 | |
e9cd0b25 PB |
278 | # This might be more cleanly moved into the main loop, by adding |
279 | # a <dummy> source directory at the end. FIXME! | |
cbbf876b NN |
280 | |
281 | # All the headers we create define size_t and NULL. | |
282 | for rel_source_file in unistd.h stdlib.h string.h time.h ; do | |
283 | if grep "$rel_source_file" fixproto.list >/dev/null ; then | |
284 | : # It exists, we don't need to make it | |
7afe1b4d PB |
285 | else |
286 | echo Adding missing $rel_source_file | |
e9cd0b25 | 287 | rel_source_ident=`echo $rel_source_file | tr ./ __` |
7afe1b4d | 288 | cat >tmp.h <<EOF |
cbbf876b NN |
289 | /* Fake ${rel_source_file}, created by GCC. |
290 | The functions declared in this file do not necessarily exist in | |
291 | your C library. */ | |
08fbf99d MH |
292 | #ifndef __${rel_source_ident} |
293 | #define __${rel_source_ident} | |
7a790837 | 294 | |
cbbf876b | 295 | #define __need_NULL |
7a790837 MH |
296 | #define __need_size_t |
297 | #include <stddef.h> | |
298 | EOF | |
cbbf876b NN |
299 | # Insert special stuff for particular files here. |
300 | case ${rel_source_file} in | |
301 | time.h) | |
302 | # If time.h doesn't exist, find out if sys/time.h does. | |
303 | if test -f $src_dir_std/sys/time.h \ | |
304 | || grep "sys/time.h" fixproto.list >/dev/null ; then | |
305 | # It does; include it and hope it has the needed declarations. | |
306 | # Some versions require sys/types.h. | |
307 | cat >>tmp.h <<EOF | |
308 | ||
309 | #include <sys/types.h> | |
310 | #include <sys/time.h> | |
311 | EOF | |
312 | else | |
313 | # It doesn't. Make up plausible definitions for time_t, clock_t. | |
314 | # Forward-declare struct tm. Hope nobody tries to use it. (Odds | |
315 | # are they won't.) | |
316 | cat >>tmp.h <<EOF | |
317 | ||
318 | typedef long time_t; | |
319 | typedef long clock_t; | |
320 | struct tm; | |
321 | EOF | |
322 | fi ;; | |
323 | esac | |
7a790837 MH |
324 | cat >>tmp.h <<EOF |
325 | ||
08fbf99d | 326 | #endif /* __${rel_source_ident} */ |
7afe1b4d | 327 | EOF |
b3ca463c | 328 | ${FIX_HEADER} $rel_source_file tmp.h $abs_target_dir/$rel_source_file ${DEFINES} $include_path |
01b2995f | 329 | if test $? != 0 ; then exit 1 ; fi |
cbbf876b | 330 | if test -f $abs_target_dir/$rel_source_file ; then |
825ac704 MS |
331 | rm tmp.h |
332 | else | |
333 | mv tmp.h $abs_target_dir/$rel_source_file | |
334 | fi | |
7afe1b4d PB |
335 | fi |
336 | done | |
7a790837 MH |
337 | |
338 | # Remove any directories that we made that are still empty. | |
339 | rmdir $subdirs_made 2>/dev/null | |
340 | ||
7afe1b4d | 341 | exit 0 |