This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
Configure: eliminate some left over debug output
[metaconfig.git] / U / perl / fflushall.U
1 ?RCS: $Id$
2 ?RCS:
3 ?RCS: Copyright (c) 1999, Jarkko Hietaniemi
4 ?RCS:
5 ?RCS: You may redistribute only under the terms of the Artistic License,
6 ?RCS: as specified in the README file that comes with the distribution.
7 ?RCS: You may reuse parts of this distribution only within the terms of
8 ?RCS: that same Artistic License; a copy of which may be found at the root
9 ?RCS: of the source tree for dist 3.0.
10 ?RCS:
11 ?MAKE:fflushNULL fflushall: Compile cat rm rm_try test osname run to from \
12         Oldconfig Myread Setvar echo targethost \
13         d_sysconf i_unistd d_stdio_stream_array stdio_stream_array i_stdlib
14 ?MAKE:  -pick add $@ %<
15 ?S:fflushNULL:
16 ?S:     This symbol, if defined, tells that fflush(NULL) correctly
17 ?S:     flushes all pending stdio output without side effects. In
18 ?S:     particular, on some platforms calling fflush(NULL) *still*
19 ?S:     corrupts STDIN if it is a pipe.
20 ?S:.
21 ?S:fflushall:
22 ?S:     This symbol, if defined, tells that to flush
23 ?S:     all pending stdio output one must loop through all
24 ?S:     the stdio file handles stored in an array and fflush them.
25 ?S:     Note that if fflushNULL is defined, fflushall will not
26 ?S:     even be probed for and will be left undefined.
27 ?S:.
28 ?C:FFLUSH_NULL:
29 ?C:     This symbol, if defined, tells that fflush(NULL) correctly
30 ?C:     flushes all pending stdio output without side effects. In
31 ?C:     particular, on some platforms calling fflush(NULL) *still*
32 ?C:     corrupts STDIN if it is a pipe.
33 ?C:.
34 ?C:FFLUSH_ALL:
35 ?C:     This symbol, if defined, tells that to flush
36 ?C:     all pending stdio output one must loop through all
37 ?C:     the stdio file handles stored in an array and fflush them.
38 ?C:     Note that if fflushNULL is defined, fflushall will not
39 ?C:     even be probed for and will be left undefined.
40 ?C:.
41 ?H:#$fflushNULL FFLUSH_NULL             /**/
42 ?H:#$fflushall  FFLUSH_ALL              /**/
43 ?H:.
44 ?T:output code
45 ?F:!try.out !try !tryp
46 : Check how to flush
47 echo " "
48 $cat >&4 <<EOM
49 Checking how to flush all pending stdio output...
50 EOM
51 # I only know how to find the first 32 possibly open files on SunOS.
52 # See also hints/sunos_4_1.sh and util.c  --AD
53 case "$osname" in
54 sunos) $echo '#define PERL_FFLUSH_ALL_FOPEN_MAX 32' > try.c ;;
55 esac
56 $cat >>try.c <<EOCP
57 #include <stdio.h>
58 #$i_stdlib I_STDLIB
59 #ifdef I_STDLIB
60 #include <stdlib.h>
61 #endif
62 #$i_unistd I_UNISTD
63 #ifdef I_UNISTD
64 # include <unistd.h>
65 #endif
66 #$d_sysconf HAS_SYSCONF
67 #$d_stdio_stream_array HAS_STDIO_STREAM_ARRAY
68 #ifdef HAS_STDIO_STREAM_ARRAY
69 # define STDIO_STREAM_ARRAY $stdio_stream_array
70 #endif
71 int main() {
72   FILE* p;
73   unlink("try.out");
74   p = fopen("try.out", "w");
75 #ifdef TRY_FPUTC
76   fputc('x', p);
77 #else
78 # ifdef TRY_FPRINTF
79   fprintf(p, "x");
80 # endif
81 #endif
82 #ifdef TRY_FFLUSH_NULL
83   fflush(NULL);
84 #endif
85 #ifdef TRY_FFLUSH_ALL
86   {
87     long open_max = -1;
88 # ifdef PERL_FFLUSH_ALL_FOPEN_MAX
89     open_max = PERL_FFLUSH_ALL_FOPEN_MAX;
90 # else
91 #  if defined(HAS_SYSCONF) && defined(_SC_OPEN_MAX)
92     open_max = sysconf(_SC_OPEN_MAX);
93 #  else
94 #   ifdef FOPEN_MAX
95     open_max = FOPEN_MAX;
96 #   else
97 #    ifdef OPEN_MAX
98     open_max = OPEN_MAX;
99 #    else
100 #     ifdef _NFILE
101     open_max = _NFILE;
102 #     endif
103 #    endif
104 #   endif
105 #  endif
106 # endif
107 # ifdef HAS_STDIO_STREAM_ARRAY
108     if (open_max > 0) {
109       long i;
110       for (i = 0; i < open_max; i++)
111             if (STDIO_STREAM_ARRAY[i]._file >= 0 &&
112                 STDIO_STREAM_ARRAY[i]._file < open_max &&
113                 STDIO_STREAM_ARRAY[i]._flag)
114                 fflush(&STDIO_STREAM_ARRAY[i]);
115     }
116 # endif
117   }
118 #endif
119   _exit(42);
120 }
121 EOCP
122 : first we have to find out how _not_ to flush
123 $to try.c
124 if $test "X$fflushNULL" = X -o "X$fflushall" = X; then
125     output=''
126     set try -DTRY_FPUTC
127     if eval $compile; then
128             $run ./try 2>/dev/null
129             code="$?"
130             $from try.out
131             if $test ! -s try.out -a "X$code" = X42; then
132                 output=-DTRY_FPUTC
133             fi
134     fi
135     case "$output" in
136     '')
137             set try -DTRY_FPRINTF
138             if eval $compile; then
139                     $run ./try 2>/dev/null
140                     code="$?"
141                     $from try.out
142                     if $test ! -s try.out -a "X$code" = X42; then
143                         output=-DTRY_FPRINTF
144                     fi
145             fi
146         ;;
147     esac
148 fi
149 : check for fflush NULL behavior
150 case "$fflushNULL" in
151 '')     set try -DTRY_FFLUSH_NULL $output
152         if eval $compile; then
153                 $run ./try 2>/dev/null
154                 code="$?"
155                 $from try.out
156                 if $test -s try.out -a "X$code" = X42; then
157                         fflushNULL="`$cat try.out`"
158                 else
159                         if $test "X$code" != X42; then
160                                 $cat >&4 <<EOM
161 (If this test failed, don't worry, we'll try another method shortly.)
162 EOM
163                         fi
164                 fi
165         fi
166         $rm -f core try.core core.try.*
167         case "$fflushNULL" in
168         x)      $cat >&4 <<EOM
169 Your fflush(NULL) works okay for output streams.
170 Let's see if it clobbers input pipes...
171 EOM
172 # As of mid-March 2000 all versions of Solaris appear to have a stdio
173 # bug that improperly flushes the input end of pipes.  So we avoid the
174 # autoflush on fork/system/exec support for now. :-(
175 $cat >tryp.c <<EOCP
176 #include <stdio.h>
177 int
178 main(int argc, char **argv)
179 {
180     char buf[1024];
181     int i;
182     char *bp = buf;
183     while (1) {
184         while ((i = getc(stdin)) != -1
185                && (*bp++ = i) != '\n'
186                && bp < &buf[1024])
187         /* DO NOTHING */ ;
188         *bp = '\0';
189         fprintf(stdout, "%s", buf);
190         fflush(NULL);
191         if (i == -1)
192             return 0;
193         bp = buf;
194     }
195 }
196 EOCP
197                 fflushNULL="$define"
198                 set tryp
199                 if eval $compile; then
200                     $rm -f tryp.out
201                     # Copy the .c file to the remote host ($to is an ssh-alike if targethost is set)
202                     if $test "X$targethost" != X; then
203                         $to tryp.c
204                         $to tryp
205                         $run "cat tryp.c | ./tryp " 2>/dev/null > tryp.out
206                     else
207                         $cat tryp.c | $run ./tryp   2>/dev/null > tryp.out
208                     fi
209                     if cmp tryp.c tryp.out >/dev/null 2>&1; then
210                        $cat >&4 <<EOM
211 fflush(NULL) seems to behave okay with input streams.
212 EOM
213                         fflushNULL="$define"
214                     else
215                         $cat >&4 <<EOM
216 Ouch, fflush(NULL) clobbers input pipes!  We will not use it.
217 EOM
218                         fflushNULL="$undef"
219                     fi
220                 fi
221                 $rm -f core tryp.c tryp.core core.tryp.*
222                 ;;
223         '')     $cat >&4 <<EOM
224 Your fflush(NULL) isn't working (contrary to ANSI C).
225 EOM
226                 fflushNULL="$undef"
227                 ;;
228         *)      $cat >&4 <<EOM
229 Cannot figure out whether your fflush(NULL) works or not.
230 I'm assuming it doesn't (contrary to ANSI C).
231 EOM
232                 fflushNULL="$undef"
233                 ;;
234         esac
235         ;;
236 $define|true|[yY]*)
237         fflushNULL="$define"
238         ;;
239 *)
240         fflushNULL="$undef"
241         ;;
242 esac
243 : check explicit looping only if NULL did not work, and if the pipe
244 : bug does not show up on an explicit flush too
245 case "$fflushNULL" in
246 "$undef")
247         $cat >tryp.c <<EOCP
248 #include <stdio.h>
249 int
250 main(int argc, char **argv)
251 {
252     char buf[1024];
253     int i;
254     char *bp = buf;
255     while (1) {
256         while ((i = getc(stdin)) != -1
257                && (*bp++ = i) != '\n'
258                && bp < &buf[1024])
259         /* DO NOTHING */ ;
260         *bp = '\0';
261         fprintf(stdout, "%s", buf);
262         fflush(stdin);
263         if (i == -1)
264             return 0;
265         bp = buf;
266     }
267 }
268 EOCP
269         set tryp
270         if eval $compile; then
271             $rm -f tryp.out
272             if $test "X$targethost" != X; then
273                 $to tryp.c
274                 $to tryp
275                 $run "cat tryp.c | ./tryp " 2>/dev/null > tryp.out
276             else
277                 $cat tryp.c | $run ./tryp   2>/dev/null > tryp.out
278             fi
279             if cmp tryp.c tryp.out >/dev/null 2>&1; then
280                $cat >&4 <<EOM
281 Good, at least fflush(stdin) seems to behave okay when stdin is a pipe.
282 EOM
283                 : now check for fflushall behaviour
284                 case "$fflushall" in
285                 '')     set try -DTRY_FFLUSH_ALL $output
286                         if eval $compile; then
287                                 $cat >&4 <<EOM
288 (Now testing the other method--but note that this also may fail.)
289 EOM
290                                 $run ./try 2>/dev/null
291                                 code=$?
292                                 $from try.out
293                                 if $test -s try.out -a "X$code" = X42; then
294                                         fflushall="`$cat try.out`"
295                                 fi
296                         fi
297                         $rm_try
298                         case "$fflushall" in
299                         x)      $cat >&4 <<EOM
300 Whew. Flushing explicitly all the stdio streams works.
301 EOM
302                                 fflushall="$define"
303                                 ;;
304                         '')     $cat >&4 <<EOM
305 Sigh. Flushing explicitly all the stdio streams doesn't work.
306 EOM
307                                 fflushall="$undef"
308                                 ;;
309                         *)      $cat >&4 <<EOM
310 Cannot figure out whether flushing stdio streams explicitly works or not.
311 I'm assuming it doesn't.
312 EOM
313                                 fflushall="$undef"
314                                 ;;
315                         esac
316                         ;;
317                 "$define"|true|[yY]*)
318                         fflushall="$define"
319                         ;;
320                 *)
321                         fflushall="$undef"
322                         ;;
323                 esac
324             else
325                 $cat >&4 <<EOM
326 All is futile.  Even fflush(stdin) clobbers input pipes!
327 EOM
328                 fflushall="$undef"
329             fi
330         else
331             fflushall="$undef"
332         fi
333         $rm -f core tryp.c tryp.core core.tryp.*
334         ;;
335 *)      fflushall="$undef"
336         ;;
337 esac
338
339 case "$fflushNULL$fflushall" in
340 undefundef)
341         $cat <<EOM
342 OK, I give up.  I cannot figure out how to flush pending stdio output.
343 We won't be flushing handles at all before fork/exec/popen.
344 EOM
345         ;;
346 esac
347 $rm_try tryp
348