1 /* Copyright (C) 2004 Manuel Novoa III <mjn3@codepoet.org>
3 * GNU Library General Public License (LGPL) version 2 or later.
5 * Dedicated to Toni. See uClibc/DEDICATION.mjn3 for details.
12 libc_hidden_proto(close)
13 libc_hidden_proto(fflush_unlocked)
15 int fclose(register FILE *stream)
18 __STDIO_AUTO_THREADLOCK_VAR;
20 /* First, remove the file from the open file list. */
21 #ifdef __STDIO_HAS_OPENLIST
25 __STDIO_THREADLOCK_OPENLIST;
26 if ((ptr = _stdio_openlist) == stream) {
27 _stdio_openlist = stream->__nextopen;
30 if (ptr->__nextopen == stream) {
31 ptr->__nextopen = stream->__nextopen;
34 ptr = ptr->__nextopen;
37 __STDIO_THREADUNLOCK_OPENLIST;
39 if (!ptr) { /* Did not find stream in the open file list! */
45 __STDIO_AUTO_THREADLOCK(stream);
47 __STDIO_STREAM_VALIDATE(stream);
49 #ifdef __STDIO_BUFFERS
50 /* Write any pending buffered chars. */
51 if (__STDIO_STREAM_IS_WRITING(stream)) {
52 rv = fflush_unlocked(stream);
56 if (__CLOSE(stream) < 0) { /* Must close even if fflush failed. */
60 stream->__filedes = -1;
62 /* We need a way for freopen to know that a file has been closed.
63 * Since a file can't be both readonly and writeonly, that makes
64 * an effective signal. It also has the benefit of disabling
65 * transitions to either reading or writing. */
66 stream->__modeflags &= (__FLAG_FREEBUF|__FLAG_FREEFILE);
67 stream->__modeflags |= (__FLAG_READONLY|__FLAG_WRITEONLY);
70 __STDIO_STREAM_RESET_GCS(stream);
72 /* Reinitialize everything (including putc since fflush could fail). */
73 __STDIO_STREAM_DISABLE_GETC(stream);
74 __STDIO_STREAM_DISABLE_PUTC(stream);
75 __STDIO_STREAM_INIT_BUFREAD_BUFPOS(stream);
77 # ifdef __UCLIBC_HAS_WCHAR__
78 stream->__ungot_width[0] = 0;
80 # ifdef __STDIO_MBSTATE
81 __INIT_MBSTATE(&(stream->__state));
85 __STDIO_AUTO_THREADUNLOCK(stream);
87 __STDIO_STREAM_FREE_BUFFER(stream);
88 __STDIO_STREAM_FREE_FILE(stream);
92 libc_hidden_proto(fclose)
93 libc_hidden_def(fclose)