11573Srgrimes/*- 21573Srgrimes * Copyright (c) 1990, 1993 31573Srgrimes * The Regents of the University of California. All rights reserved. 41573Srgrimes * 51573Srgrimes * This code is derived from software contributed to Berkeley by 61573Srgrimes * Chris Torek. 71573Srgrimes * 81573Srgrimes * Redistribution and use in source and binary forms, with or without 91573Srgrimes * modification, are permitted provided that the following conditions 101573Srgrimes * are met: 111573Srgrimes * 1. Redistributions of source code must retain the above copyright 121573Srgrimes * notice, this list of conditions and the following disclaimer. 131573Srgrimes * 2. Redistributions in binary form must reproduce the above copyright 141573Srgrimes * notice, this list of conditions and the following disclaimer in the 151573Srgrimes * documentation and/or other materials provided with the distribution. 16249808Semaste * 3. Neither the name of the University nor the names of its contributors 171573Srgrimes * may be used to endorse or promote products derived from this software 181573Srgrimes * without specific prior written permission. 191573Srgrimes * 201573Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 211573Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 221573Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 231573Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 241573Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 251573Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 261573Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 271573Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 281573Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 291573Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 301573Srgrimes * SUCH DAMAGE. 311573Srgrimes */ 321573Srgrimes 331573Srgrimes#if defined(LIBC_SCCS) && !defined(lint) 341573Srgrimesstatic char sccsid[] = "@(#)refill.c 8.1 (Berkeley) 6/4/93"; 351573Srgrimes#endif /* LIBC_SCCS and not lint */ 3692986Sobrien#include <sys/cdefs.h> 3792986Sobrien__FBSDID("$FreeBSD$"); 381573Srgrimes 3972373Sdeischen#include "namespace.h" 401573Srgrimes#include <errno.h> 411573Srgrimes#include <stdio.h> 421573Srgrimes#include <stdlib.h> 4372373Sdeischen#include "un-namespace.h" 4471579Sdeischen 4572373Sdeischen#include "libc_private.h" 461573Srgrimes#include "local.h" 471573Srgrimes 4892905Sobrienstatic int lflush(FILE *); 4916586Sjraynard 5016586Sjraynardstatic int 5172373Sdeischenlflush(FILE *fp) 521573Srgrimes{ 5372373Sdeischen int ret = 0; 541573Srgrimes 5572373Sdeischen if ((fp->_flags & (__SLBF|__SWR)) == (__SLBF|__SWR)) { 5672373Sdeischen FLOCKFILE(fp); 5772373Sdeischen ret = __sflush(fp); 5872373Sdeischen FUNLOCKFILE(fp); 5972373Sdeischen } 6072373Sdeischen return (ret); 611573Srgrimes} 621573Srgrimes 631573Srgrimes/* 641573Srgrimes * Refill a stdio buffer. 651573Srgrimes * Return EOF on eof or error, 0 otherwise. 661573Srgrimes */ 6716586Sjraynardint 6872373Sdeischen__srefill(FILE *fp) 691573Srgrimes{ 7073689Sobrien 711573Srgrimes /* make sure stdio is set up */ 721573Srgrimes if (!__sdidinit) 731573Srgrimes __sinit(); 741573Srgrimes 75101776Stjr ORIENT(fp, -1); 76101776Stjr 771573Srgrimes fp->_r = 0; /* largely a convenience for callers */ 781573Srgrimes 791573Srgrimes /* SysV does not make this test; take it out for compatibility */ 801573Srgrimes if (fp->_flags & __SEOF) 811573Srgrimes return (EOF); 821573Srgrimes 831573Srgrimes /* if not already reading, have to be reading and writing */ 841573Srgrimes if ((fp->_flags & __SRD) == 0) { 851573Srgrimes if ((fp->_flags & __SRW) == 0) { 861573Srgrimes errno = EBADF; 8749613Srnordier fp->_flags |= __SERR; 881573Srgrimes return (EOF); 891573Srgrimes } 901573Srgrimes /* switch to reading */ 911573Srgrimes if (fp->_flags & __SWR) { 921573Srgrimes if (__sflush(fp)) 931573Srgrimes return (EOF); 941573Srgrimes fp->_flags &= ~__SWR; 951573Srgrimes fp->_w = 0; 961573Srgrimes fp->_lbfsize = 0; 971573Srgrimes } 981573Srgrimes fp->_flags |= __SRD; 991573Srgrimes } else { 1001573Srgrimes /* 1011573Srgrimes * We were reading. If there is an ungetc buffer, 1021573Srgrimes * we must have been reading from that. Drop it, 1031573Srgrimes * restoring the previous buffer (if any). If there 1041573Srgrimes * is anything in that buffer, return. 1051573Srgrimes */ 1061573Srgrimes if (HASUB(fp)) { 1071573Srgrimes FREEUB(fp); 1081573Srgrimes if ((fp->_r = fp->_ur) != 0) { 109178287Sjhb fp->_p = fp->_up; 1101573Srgrimes return (0); 1111573Srgrimes } 1121573Srgrimes } 1131573Srgrimes } 1141573Srgrimes 1151573Srgrimes if (fp->_bf._base == NULL) 1161573Srgrimes __smakebuf(fp); 1171573Srgrimes 1181573Srgrimes /* 1191573Srgrimes * Before reading from a line buffered or unbuffered file, 1201573Srgrimes * flush all line buffered output files, per the ANSI C 1211573Srgrimes * standard. 1221573Srgrimes */ 12372373Sdeischen if (fp->_flags & (__SLBF|__SNBF)) { 12472373Sdeischen /* Ignore this file in _fwalk to avoid potential deadlock. */ 12572373Sdeischen fp->_flags |= __SIGN; 1261573Srgrimes (void) _fwalk(lflush); 12772373Sdeischen fp->_flags &= ~__SIGN; 12872373Sdeischen 12972373Sdeischen /* Now flush this file without locking it. */ 13072373Sdeischen if ((fp->_flags & (__SLBF|__SWR)) == (__SLBF|__SWR)) 13172373Sdeischen __sflush(fp); 13272373Sdeischen } 1331573Srgrimes fp->_p = fp->_bf._base; 13482838Sache fp->_r = _sread(fp, (char *)fp->_p, fp->_bf._size); 1351573Srgrimes fp->_flags &= ~__SMOD; /* buffer contents are again pristine */ 1361573Srgrimes if (fp->_r <= 0) { 1371573Srgrimes if (fp->_r == 0) 1381573Srgrimes fp->_flags |= __SEOF; 1391573Srgrimes else { 1401573Srgrimes fp->_r = 0; 1411573Srgrimes fp->_flags |= __SERR; 1421573Srgrimes } 1431573Srgrimes return (EOF); 1441573Srgrimes } 1451573Srgrimes return (0); 1461573Srgrimes} 147