/* * Flush a single file, or (if fp is NULL) all files. * MT-safe version */ int fflush(FILE *fp) { int retval; if (fp == NULL) return (_fwalk(sflush_locked)); FLOCKFILE(fp); /* * There is disagreement about the correct behaviour of fflush() * when passed a file which is not open for reading. According to * the ISO C standard, the behaviour is undefined. * Under linux, such an fflush returns success and has no effect; * under Windows, such an fflush is documented as behaving instead * as fpurge(). * Given that applications may be written with the expectation of * either of these two behaviours, the only safe (non-astonishing) * option is to return EBADF and ask that applications be fixed. */ if ((fp->pub._flags & (__SWR | __SRW)) == 0) { errno = EBADF; retval = EOF; } else { retval = __sflush(fp); } FUNLOCKFILE(fp); return (retval); }
/* Flush a single file, or (if fp is NULL) all files. */ int fflush(register FILE *fp) { if (fp == NULL) return (_fwalk(__sflush)); if ((fp->_flags & (__SWR | __SRW)) == 0) { errno = EBADF; return (EOF); } return (__sflush(fp)); }
/* * Flush a single file, or (if fp is NULL) all files. * Non-MT-safe version */ int __fflush(FILE *fp) { int retval; if (fp == NULL) return (_fwalk(sflush_locked)); if ((fp->_flags & (__SWR | __SRW)) == 0) retval = 0; else retval = __sflush(fp); return (retval); }
int fflush_unlocked(FILE *fp) { int r; if (fp == NULL) return (_fwalk(__sflush)); if ((fp->_flags & (__SWR | __SRW)) == 0) { errno = EBADF; r = EOF; } else { r = __sflush(fp); } return (r); }
/* * Flush a single file, or (if fp is NULL) all files. * Non-MT-safe version */ int __fflush(FILE *fp) { int retval; if (fp == NULL) return (_fwalk(sflush_locked)); if ((fp->pub._flags & (__SWR | __SRW)) == 0) { errno = EBADF; retval = EOF; } else { retval = __sflush(fp); } return (retval); }
/* Flush a single file, or (if fp is NULL) all files. */ int fflush(FILE *fp) { int r; if (fp == NULL) return (_fwalk(__sflush_locked)); FLOCKFILE(fp); if ((fp->_flags & (__SWR | __SRW)) == 0) { errno = EBADF; r = EOF; } else r = __sflush(fp); FUNLOCKFILE(fp); return (r); }
int fflush(FILE *f) { char *base; int n, rn; if (f == NULL) { int e = errno; errno = 0; _fwalk((void (*)(FILE *))fflush); if (errno) return EOF; errno = e; return 0; } f->_flag &= ~_IOUNGETC; if ((f->_flag&(_IONBF|_IOWRT))==_IOWRT && (base = f->_base) != NULL && (rn = n = f->_ptr - base) > 0) { f->_ptr = base; f->_cnt = (f->_flag&(_IOLBF|_IONBF)) ? 0 : f->_bufsiz; do { if (!FsWrite(fileno(f), base, f->_offset, rn, &n) || n <= 0) { f->_flag |= _IOERR; return EOF; } rn -= n; base += n; f->_offset += n; } while (rn > 0); } if (f->_flag & _IORW) { f->_cnt = 0; f->_flag &= ~(_IOWRT|_IOREAD); f->_ptr = f->_base; } return 0; }
/* iterate over all FILE *'s for this thread */ static void sync_per_thread(Thread_Control *t) { struct _reent *current_reent; struct _reent *this_reent; /* * The sync_wrapper() function will operate on the current thread's * reent structure so we will temporarily use that. */ this_reent = t->libc_reent; if ( this_reent ) { current_reent = _Thread_Executing->libc_reent; _Thread_Executing->libc_reent = this_reent; _fwalk (t->libc_reent, sync_wrapper); _Thread_Executing->libc_reent = current_reent; } }
void sync(void) { /* * Walk the one used initially by RTEMS. */ _fwalk(_global_impure_ptr, sync_wrapper); /* * XXX Do we walk the one used globally by newlib? * XXX Do we need the RTEMS global one? */ /* * Now walk all the per-thread reentrancy structures. */ rtems_iterate_over_all_threads(sync_per_thread); }
/* iterate over all FILE *'s for this thread */ static bool sync_per_thread(Thread_Control *t, void *arg) { struct _reent *current_reent; struct _reent *this_reent; /* * The sync_wrapper() function will operate on the current thread's * reent structure so we will temporarily use that. */ this_reent = t->libc_reent; if ( this_reent ) { Thread_Control *executing = _Thread_Get_executing(); current_reent = executing->libc_reent; executing->libc_reent = this_reent; _fwalk (t->libc_reent, sync_wrapper); executing->libc_reent = current_reent; } return false; }
/** Flush a stream. If the given stream has been opened for writing operations the output buffer is phisically written to the file. If the stream was open for reading operations the content of the input buffer is cleared. The stream remains open after this call. @param fp pointer to an open file. @return On Success, a 0 value indicates success. On Failure, EOF is returned and errno may be set. */ EXPORT_C int fflush (FILE * fp) { register unsigned char *p; register int n, t; if (fp == NULL) { struct _reent *r = _REENT2; if (!r) return EOF; // Memory for library globals is not allocated (errno not set). return _fwalk (r, fflush); } CHECK_INIT (fp); t = fp->_flags; if ((t & __SWR) == 0 || (p = fp->_bf._base) == NULL) return 0; n = fp->_p - p; /* write this much */ /* * Set these immediately to avoid problems with longjmp * and to allow exchange buffering (via setvbuf) in user * write function. */ fp->_p = p; fp->_w = t & (__SLBF | __SNBF) ? 0 : fp->_bf._size; while (n > 0) { t = (*fp->_write) (fp->_cookie, (char *) p, n); if (t <= 0) { fp->_flags |= __SERR; return EOF; } p += t; n -= t; } return 0; }
int _filbuf(FILE *iop) { if ( !(iop->_flag & _IOREAD) ) if (iop->_flag & _IORW) iop->_flag |= _IOREAD; else return(EOF); if (iop->_flag&_IOSTRG) return(EOF); if (iop->_base == NULL) /* get buffer if we don't have one */ _findbuf(iop); /* if this device is a terminal (line-buffered) or unbuffered, then */ /* flush buffers of all line-buffered devices currently writing */ if (iop->_flag & (_IOLBF | _IONBF)) _fwalk(lbfflush); iop->_ptr = iop->_base; iop->_cnt = read(fileno(iop), (char *)iop->_base, (unsigned)((iop->_flag & _IONBF) ? 1 : iop->_bufsiz )); if (--iop->_cnt >= 0) /* success */ return (*iop->_ptr++); if (iop->_cnt != -1) /* error */ iop->_flag |= _IOERR; else { /* end-of-file */ iop->_flag |= _IOEOF; if (iop->_flag & _IORW) iop->_flag &= ~_IOREAD; } iop->_cnt = 0; return (EOF); }
/* * exit() calls _cleanup() through *__cleanup, set whenever we * open or buffer a file. This chicanery is done so that programs * that do not use stdio need not link it all in. * * The name `_cleanup' is, alas, fairly well known outside stdio. */ void _cleanup(void) { /* (void) _fwalk(fclose); */ (void) _fwalk(__sflush); /* `cheating' */ }
/* * Refill a stdio buffer. * Return EOF on eof or error, 0 otherwise. */ int __srefill(FILE *fp) { _DIAGASSERT(fp != NULL); if(fp == NULL) { errno = EINVAL; return (EOF); } /* make sure stdio is set up */ if (!__sdidinit) __sinit(); fp->_r = 0; /* largely a convenience for callers */ /* SysV does not make this test; take it out for compatibility */ if (fp->_flags & __SEOF) { return (EOF); } /* if not already reading, have to be reading and writing */ if ((fp->_flags & __SRD) == 0) { if ((fp->_flags & __SRW) == 0) { errno = EBADF; fp->_flags |= __SERR; //<dvm> Allows differentiation between errors and EOF return (EOF); } /* switch to reading */ if (fp->_flags & __SWR) { if (__sflush(fp)) { return (EOF); } fp->_flags &= ~__SWR; fp->_w = 0; fp->_lbfsize = 0; } fp->_flags |= __SRD; } else { /* * We were reading. If there is an ungetc buffer, * we must have been reading from that. Drop it, * restoring the previous buffer (if any). If there * is anything in that buffer, return. */ if (HASUB(fp)) { FREEUB(fp); if ((fp->_r = fp->_ur) != 0) { fp->_p = fp->_up; return (0); } } } if (fp->_bf._base == NULL) __smakebuf(fp); /* * Before reading from a line buffered or unbuffered file, * flush all line buffered output files, per the ANSI C * standard. */ if (fp->_flags & (__SLBF|__SNBF)) { rwlock_rdlock(&__sfp_lock); (void) _fwalk(lflush); rwlock_unlock(&__sfp_lock); } fp->_p = fp->_bf._base; fp->_r = (*fp->_read)(fp->_cookie, (char *)fp->_p, fp->_bf._size); fp->_flags &= ~__SMOD; /* buffer contents are again pristine */ if (fp->_r <= 0) { if (fp->_r == 0) fp->_flags |= __SEOF; else { fp->_r = 0; fp->_flags |= __SERR; } return (EOF); } return (0); }
/* * Refill a stdio buffer. * Return EOF on eof or error, 0 otherwise. */ int __srefill(FILE *fp) { /* make sure stdio is set up */ if (!__sdidinit) __sinit(); ORIENT(fp, -1); fp->_r = 0; /* largely a convenience for callers */ /* SysV does not make this test; take it out for compatibility */ if (fp->_flags & __SEOF) return (EOF); /* if not already reading, have to be reading and writing */ if ((fp->_flags & __SRD) == 0) { if ((fp->_flags & __SRW) == 0) { errno = EBADF; fp->_flags |= __SERR; return (EOF); } /* switch to reading */ if (fp->_flags & __SWR) { if (__sflush(fp)) return (EOF); fp->_flags &= ~__SWR; fp->_w = 0; fp->_lbfsize = 0; } fp->_flags |= __SRD; } else { /* * We were reading. If there is an ungetc buffer, * we must have been reading from that. Drop it, * restoring the previous buffer (if any). If there * is anything in that buffer, return. */ if (HASUB(fp)) { FREEUB(fp); if ((fp->_r = fp->_ur) != 0) { fp->_p = fp->_up; return (0); } } } if (fp->_bf._base == NULL) __smakebuf(fp); /* * Before reading from a line buffered or unbuffered file, * flush all line buffered output files, per the ANSI C * standard. */ if (fp->_flags & (__SLBF|__SNBF)) { /* Ignore this file in _fwalk to avoid potential deadlock. */ fp->_flags |= __SIGN; (void) _fwalk(lflush); fp->_flags &= ~__SIGN; /* Now flush this file without locking it. */ if ((fp->_flags & (__SLBF|__SWR)) == (__SLBF|__SWR)) __sflush(fp); } fp->_p = fp->_bf._base; fp->_r = _sread(fp, (char *)fp->_p, fp->_bf._size); fp->_flags &= ~__SMOD; /* buffer contents are again pristine */ if (fp->_r <= 0) { if (fp->_r == 0) fp->_flags |= __SEOF; else { fp->_r = 0; fp->_flags |= __SERR; } return (EOF); } return (0); }
void __fcloseall(void) { _fwalk(fclose); }
int __srefill (register FILE * fp) { /* make sure stdio is set up */ CHECK_INIT (fp); fp->_r = 0; /* largely a convenience for callers */ /* SysV does not make this test; take it out for compatibility */ if (fp->_flags & __SEOF) return EOF; /* if not already reading, have to be reading and writing */ if ((fp->_flags & __SRD) == 0) { if ((fp->_flags & __SRW) == 0) return EOF; /* switch to reading */ if (fp->_flags & __SWR) { if (fflush (fp)) return EOF; fp->_flags &= ~__SWR; fp->_w = 0; fp->_lbfsize = 0; } fp->_flags |= __SRD; } else { /* * We were reading. If there is an ungetc buffer, * we must have been reading from that. Drop it, * restoring the previous buffer (if any). If there * is anything in that buffer, return. */ if (HASUB (fp)) { FREEUB (fp); if ((fp->_r = fp->_ur) != 0) { fp->_p = fp->_up; return 0; } } } if (fp->_bf._base == NULL) __smakebuf (fp); /* * Before reading from a line buffered or unbuffered file, * flush all line buffered output files, per the ANSI C * standard. */ if (fp->_flags & (__SLBF | __SNBF)) (void) _fwalk (fp->_data, lflush); fp->_p = fp->_bf._base; fp->_r = (*fp->_read) (fp->_cookie, (char *) fp->_p, fp->_bf._size); fp->_flags &= ~__SMOD; /* buffer contents are again pristine */ if (fp->_r <= 0) { if (fp->_r == 0) fp->_flags |= __SEOF; else { fp->_r = 0; fp->_flags |= __SERR; } return EOF; } return 0; }