source: trunk/third/perl/h2ph.SH @ 9610

Revision 9610, 6.7 KB checked in by ghudson, 27 years ago (diff)
From bert: improve thet handling of integer constants, and use eval() around evaluation of identifiers to prevent spurious warnings.
Line 
1case $CONFIG in
2'')
3    if test ! -f config.sh; then
4        ln ../config.sh . || \
5        ln ../../config.sh . || \
6        ln ../../../config.sh . || \
7        (echo "Can't find config.sh."; exit 1)
8    fi 2>/dev/null
9    . ./config.sh
10    ;;
11esac
12: This forces SH files to create target in same directory as SH file.
13: This is so that make depend always knows where to find SH derivatives.
14case "$0" in
15*/*) cd `expr X$0 : 'X\(.*\)/'` ;;
16esac
17echo "Extracting h2ph (with variable substitutions)"
18: This section of the file will have variable substitutions done on it.
19: Move anything that needs config subs from !NO!SUBS! section to !GROK!THIS!.
20: Protect any dollar signs and backticks that you do not want interpreted
21: by putting a backslash in front.  You may delete these comments.
22rm -f h2ph
23$spitshell >h2ph <<!GROK!THIS!
24#!$bin/perl
25'di';
26'ig00';
27
28\$perlincl = '$installprivlib';
29!GROK!THIS!
30
31: In the following dollars and backticks do not need the extra backslash.
32$spitshell >>h2ph <<'!NO!SUBS!'
33
34chdir '/usr/include' || die "Can't cd /usr/include";
35
36@isatype = split(' ',<<END);
37        char    uchar   u_char
38        short   ushort  u_short
39        int     uint    u_int
40        long    ulong   u_long
41        FILE
42END
43
44@isatype{@isatype} = (1) x @isatype;
45
46@ARGV = ('-') unless @ARGV;
47
48foreach $file (@ARGV) {
49    if ($file eq '-') {
50        open(IN, "-");
51        open(OUT, ">-");
52    }
53    else {
54        ($outfile = $file) =~ s/\.h$/.ph/ || next;
55        print "$file -> $outfile\n";
56        if ($file =~ m|^(.*)/|) {
57            $dir = $1;
58            if (!-d "$perlincl/$dir") {
59                mkdir("$perlincl/$dir",0777);
60            }
61        }
62        open(IN,"$file") || ((warn "Can't open $file: $!\n"),next);
63        open(OUT,">$perlincl/$outfile") || die "Can't create $outfile: $!\n";
64    }
65    while (<IN>) {
66        chop;
67        while (/\\$/) {
68            chop;
69            $_ .= <IN>;
70            chop;
71        }
72        if (s:/\*:\200:g) {
73            s:\*/:\201:g;
74            s/\200[^\201]*\201//g;      # delete single line comments
75            if (s/\200.*//) {           # begin multi-line comment?
76                $_ .= '/*';
77                $_ .= <IN>;
78                redo;
79            }
80        }
81        if (s/^#\s*//) {
82            if (s/^define\s+(\w+)//) {
83                $name = $1;
84                $new = '';
85                s/\s+$//;
86                if (s/^\(([\w,\s]*)\)//) {
87                    $args = $1;
88                    if ($args ne '') {
89                        foreach $arg (split(/,\s*/,$args)) {
90                            $arg =~ s/^\s*([^\s].*[^\s])\s*$/$1/;
91                            $curargs{$arg} = 1;
92                        }
93                        $args =~ s/\b(\w)/\$$1/g;
94                        $args = "local($args) = \@_;\n$t    ";
95                    }
96                    s/^\s+//;
97                    do expr();
98                    $new =~ s/(["\\])/\\$1/g;
99                    if ($t ne '') {
100                        $new =~ s/(['\\])/\\$1/g;
101                        print OUT $t,
102                          "eval 'sub $name {\n$t    ${args}eval \"$new\";\n$t}';\n";
103                    }
104                    else {
105                        print OUT "sub $name {\n    ${args}eval \"$new\";\n}\n";
106                    }
107                    %curargs = ();
108                }
109                else {
110                    s/^\s+//;
111                    do expr();
112                    $new = 1 if $new eq '';
113                    if ($t ne '') {
114                        $new =~ s/(['\\])/\\$1/g;
115                        print OUT $t,"eval 'sub $name {",$new,";}';\n";
116                    }
117                    else {
118                        print OUT $t,"sub $name {",$new,";}\n";
119                    }
120                }
121            }
122            elsif (/^include\s+<(.*)>/) {
123                ($incl = $1) =~ s/\.h$/.ph/;
124                print OUT $t,"require '$incl';\n";
125            }
126            elsif (/^ifdef\s+(\w+)/) {
127                print OUT $t,"if (defined &$1) {\n";
128                $tab += 4;
129                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
130            }
131            elsif (/^ifndef\s+(\w+)/) {
132                print OUT $t,"if (!defined &$1) {\n";
133                $tab += 4;
134                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
135            }
136            elsif (s/^if\s+//) {
137                $new = '';
138                do expr();
139                print OUT $t,"if ($new) {\n";
140                $tab += 4;
141                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
142            }
143            elsif (s/^elif\s+//) {
144                $new = '';
145                do expr();
146                $tab -= 4;
147                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
148                print OUT $t,"}\n${t}elsif ($new) {\n";
149                $tab += 4;
150                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
151            }
152            elsif (/^else/) {
153                $tab -= 4;
154                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
155                print OUT $t,"}\n${t}else {\n";
156                $tab += 4;
157                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
158            }
159            elsif (/^endif/) {
160                $tab -= 4;
161                $t = "\t" x ($tab / 8) . ' ' x ($tab % 8);
162                print OUT $t,"}\n";
163            }
164        }
165    }
166    print OUT "1;\n";
167}
168
169sub expr {
170    while ($_ ne '') {
171        s/^(\s+)//              && do {$new .= ' '; next;};
172        s/^(0x[0-9a-fA-F]+)//   && do {$new .= $1; next;};
173        s/^0X([0-9a-fA-F]+)//   && do {$new .= '0x' . $1; next;};
174        s/^(\d+\.\d*([eE][+-]?\d+))[fFlL]?//    && do {$new .= $1; next;};
175           s/^(\.\d+([eE][+-]?\d+))[fFlL]?//    && do {$new .= $1; next;};
176        s/^(\d+)[lL]?//         && do {$new .= $1; next;};
177        s/^("(\\"|[^"])*")//    && do {$new .= $1; next;};
178        s/^'((\\"|[^"])*)'//    && do {
179            if ($curargs{$1}) {
180                $new .= "ord('\$$1')";
181            }
182            else {
183                $new .= "ord('$1')";
184            }
185            next;
186        };
187        s/^sizeof\s*\(([^)]+)\)/{$1}/ && do {
188            $new .= '$sizeof';
189            next;
190        };
191        s/^([_a-zA-Z]\w*)//     && do {
192            $id = $1;
193            if ($id eq 'struct') {
194                s/^\s+(\w+)//;
195                $id .= ' ' . $1;
196                $isatype{$id} = 1;
197            }
198            elsif ($id eq 'unsigned') {
199                s/^\s+(\w+)//;
200                $id .= ' ' . $1;
201                $isatype{$id} = 1;
202            }
203            if ($curargs{$id}) {
204                $new .= '$' . $id;
205            }
206            elsif ($id eq 'defined') {
207                $new .= 'defined';
208                $no_eval = 1;
209            }
210            elsif (/^\(/) {
211                s/^\((\w),/("$1",/ if $id =~ /^_IO[WR]*$/i;     # cheat
212                $new .= " &$id";
213            }
214            elsif ($isatype{$id}) {
215                if ($new =~ /{\s*$/) {
216                    $new .= "'$id'";
217                }
218                elsif ($new =~ /\(\s*$/ && /^[\s*]*\)/) {
219                    $new =~ s/\(\s*$//;
220                    s/^[\s*]*\)//;
221                }
222                else {
223                    $new .= $id;
224                }
225            }
226            else {
227                if ($no_eval) {
228                  $new .= ' &' . $id;
229                  $no_eval = 0;
230                } else {
231                  $new .= "eval('&$id')";
232                }
233            }
234            next;
235        };
236        s/^(.)//                        && do {$new .= $1; next;};
237    }
238}
239##############################################################################
240
241        # These next few lines are legal in both Perl and nroff.
242
243.00;                    # finish .ig
244 
245'di                     \" finish diversion--previous line must be blank
246.nr nl 0-1              \" fake up transition to first page again
247.nr % 0                 \" start at page 1
248'; __END__ ############# From here on it's a standard manual page ############
249.TH H2PH 1 "August 8, 1990"
250.AT 3
251.SH NAME
252h2ph \- convert .h C header files to .ph Perl header files
253.SH SYNOPSIS
254.B h2ph [headerfiles]
255.SH DESCRIPTION
256.I h2ph
257converts any C header files specified to the corresponding Perl header file
258format.
259It is most easily run while in /usr/include:
260.nf
261
262        cd /usr/include; h2ph * sys/*
263
264.fi
265If run with no arguments, filters standard input to standard output.
266.SH ENVIRONMENT
267No environment variables are used.
268.SH FILES
269/usr/include/*.h
270.br
271/usr/include/sys/*.h
272.br
273etc.
274.SH AUTHOR
275Larry Wall
276.SH "SEE ALSO"
277perl(1)
278.SH DIAGNOSTICS
279The usual warnings if it can't read or write the files involved.
280.SH BUGS
281Doesn't construct the %sizeof array for you.
282.PP
283It doesn't handle all C constructs, but it does attempt to isolate
284definitions inside evals so that you can get at the definitions
285that it can translate.
286.PP
287It's only intended as a rough tool.
288You may need to dicker with the files produced.
289.ex
290!NO!SUBS!
291chmod 755 h2ph
292$eunicefix h2ph
293rm -f h2ph.man
294ln h2ph h2ph.man
Note: See TracBrowser for help on using the repository browser.