Beispiel #1
0
int filbuf(FILE *stream) {
  if (stream->flag & _IOSTR) return EOF;

  if (stream->flag & _IOWR) {
    stream->flag |= _IOERR;
    return EOF;
  }

  stream->flag |= _IORD;

  // Get a buffer, if necessary.
  if (!anybuf(stream)) {
    getbuf(stream);
  } else {
    stream->ptr = stream->base;
  }
  stream->cnt = read(fileno(stream), stream->base, stream->bufsiz);

  if (stream->cnt <= 0) {
    stream->flag |= stream->cnt ? _IOERR : _IOEOF;
    stream->cnt = 0;
    return EOF;
  }

  stream->cnt--;

  return *stream->ptr++ & 0xff;
}
Beispiel #2
0
int __cdecl _filwbuf (
        FILE *str
        )

{

        REG1 FILE *stream;

        _ASSERTE(str != NULL);

        /* Init pointer to _iob2 entry. */
        stream = str;

        if (!inuse(stream) || stream->_flag & _IOSTRG)
                return(WEOF);

        if (stream->_flag & _IOWRT) {
                stream->_flag |= _IOERR;
                return(WEOF);
        }

        stream->_flag |= _IOREAD;

        /* Get a buffer, if necessary. */

        if (!anybuf(stream))
                _getbuf(stream);
        else
                stream->_ptr = stream->_base;

        stream->_cnt = _read(_fileno(stream), stream->_base, stream->_bufsiz);

        if ((stream->_cnt == 0) || (stream->_cnt == 1) || stream->_cnt == -1) {
                stream->_flag |= stream->_cnt ? _IOERR : _IOEOF;
                stream->_cnt = 0;
                return(WEOF);
        }

        if (  !(stream->_flag & (_IOWRT|_IORW)) &&
              ((_osfile_safe(_fileno(stream)) & (FTEXT|FEOFLAG)) ==
                (FTEXT|FEOFLAG)) )
                stream->_flag |= _IOCTRLZ;
        /* Check for small _bufsiz (_SMALL_BUFSIZ). If it is small and
           if it is our buffer, then this must be the first _filbuf after
           an fseek on a read-access-only stream. Restore _bufsiz to its
           larger value (_INTERNAL_BUFSIZ) so that the next _filbuf call,
           if one is made, will fill the whole buffer. */
        if ( (stream->_bufsiz == _SMALL_BUFSIZ) && (stream->_flag &
              _IOMYBUF) && !(stream->_flag & _IOSETVBUF) )
        {
                stream->_bufsiz = _INTERNAL_BUFSIZ;
        }
        stream->_cnt -= sizeof(wchar_t);
        return (0xffff & *((wchar_t *)(stream->_ptr))++);

}
int __cdecl _stbuf (
        FILE *str
        )
{
        FILE *stream;
        int index;

        _ASSERTE(str != NULL);

        /* Init near stream pointer */
        stream = str;

        /* do nothing if not a tty device */
        if (!_isatty(_fileno(stream)))
                return(0);

        /* Make sure stream is stdout/stderr and init _stdbuf index */
        if (stream == stdout)
                index = 0;
        else if (stream == stderr)
                index = 1;
        else
                return(0);

#ifndef CRTDLL
        /* force library pre-termination procedure */
        _cflush++;
#endif  /* CRTDLL */

        /* Make sure the stream is not already buffered. */
        if (anybuf(stream))
                return(0);

        /* Allocate a buffer for this stream if we haven't done so yet. */
        if ( (_stdbuf[index] == NULL) &&
             ((_stdbuf[index]=_malloc_crt(_INTERNAL_BUFSIZ)) == NULL) ) {
                /* Cannot allocate buffer. Use _charbuf this time */
                stream->_ptr = stream->_base = (void *)&(stream->_charbuf);
                stream->_cnt = stream->_bufsiz = 2;
        }
        else {
                /* Set up the buffer */
                stream->_ptr = stream->_base = _stdbuf[index];
                stream->_cnt = stream->_bufsiz = _INTERNAL_BUFSIZ;
        }

        stream->_flag |= (_IOWRT | _IOYOURBUF | _IOFLRTN);

        return(1);
}
Beispiel #4
0
int __cdecl _stbuf (
	FILE *str
	)
{
	REG1 FILE *stream;
	int index;

	_ASSERTE(str != NULL);

	/* Init near stream pointer */
	stream = str;

        /* do nothing if not a tty device */
#ifdef _POSIX_
	if (!isatty(fileno(stream)))
#else
	if (!_isatty(_fileno(stream)))
#endif
                return(0);

	/* Make sure stream is stdout/stderr and init _stdbuf index */
	if (stream == stdout)
		index = 0;
	else if (stream == stderr)
		index = 1;
	else
		return(0);

#ifndef CRTDLL
	/* force library pre-termination procedure */
	_cflush++;
#endif	/* CRTDLL */

	/* Make sure the stream is not already buffered. */
	if (anybuf(stream))
		return(0);

	/* Allocate a buffer for this stream if we haven't done so yet. */
	if (_stdbuf[index] == NULL)
#ifdef	_WIN32
		if ( (_stdbuf[index]=_malloc_crt(_INTERNAL_BUFSIZ)) == NULL )
#else
#if	defined(_M_MPPC) || defined(_M_M68K)
		if ( (_stdbuf[index]=_malloc_crt(BUFSIZ)) == NULL )
#endif
#endif
			return(0);	/* error */

	/* Set up the buffer */
	stream->_ptr = stream->_base = _stdbuf[index];
#ifdef	_WIN32
	stream->_cnt = stream->_bufsiz = _INTERNAL_BUFSIZ;
#else
#if	defined(_M_MPPC) || defined(_M_M68K)
	stream->_cnt = stream->_bufsiz = BUFSIZ;
#endif
#endif
	stream->_flag |= (_IOWRT | _IOYOURBUF | _IOFLRTN);

	return(1);
}
Beispiel #5
0
size_t fwrite(const void *buffer, size_t size, size_t num, FILE *stream) {
  const char *data;               // Point to where data comes from next
  unsigned total;                 // Total bytes to write
  unsigned count;                 // Num bytes left to write
  unsigned bufsize;               // Size of stream buffer
  unsigned nbytes;                // Number of bytes to write now
  unsigned nwritten;              // Number of bytes written
  int c;                          // A temp char

  // Initialize local vars
  data = buffer;
  count = total = size * num;
  if (count == 0) return 0;

  if (anybuf(stream)) {
    // Already has buffer, use its size
    bufsize = stream->bufsiz;
  } else {
    // Assume will get BUFSIZ buffer
    bufsize = BUFSIZ;
  }

  // Here is the main loop -- we go through here until we're done
  while (count != 0) {
    // If the buffer is big and has room, copy data to buffer
    if (bigbuf(stream) && stream->cnt != 0) {
      // How much do we want?
      nbytes = (count < (unsigned) stream->cnt) ? count : stream->cnt;
      memcpy(stream->ptr, data, nbytes);

      // Update stream and amount of data written
      count -= nbytes;
      stream->cnt -= nbytes;
      stream->ptr += nbytes;
      data += nbytes;
    } else if (count >= bufsize) {
      // If we have more than bufsize chars to write, write
      // data by calling write with an integral number of
      // bufsiz blocks.  If we reach here and we have a big
      // buffer, it must be full so flush it.

      if (bigbuf(stream)) {
        if (fflush(stream)) {
          // Error, stream flags set -- we're out of here
          return (total - count) / size;
        }
      }

      // Calc chars to write -- (count / bufsize) * bufsize
      nbytes = bufsize ? (count - count % bufsize) : count;

      if (stream->flag & _IOCRLF) {
        nwritten = write_translated(fileno(stream), (char *) data, nbytes);
      } else {
        nwritten = write(fileno(stream), data, nbytes);
      }

      if ((int) nwritten < 0) {
        // Error -- out of here
        stream->flag |= _IOERR;
        return (total - count) / size;
      }

      // Update count and data to reflect write
      count -= nwritten;
      data += nwritten;

      if (nwritten < nbytes) {
        // Error -- out of here
        stream->flag |= _IOERR;
        return (total - count) / size;
      }
    } else {
      // Buffer full and not enough chars to do direct write, so do a flsbuf.
      c = *data;  
      if (flsbuf(c, stream) == EOF) {
        // Error or eof, stream flags set by _flsbuf
        return (total - count) / size;
      }

      // flsbuf wrote a char -- update count
      ++data;
      --count;

      // Update buffer size
      bufsize = stream->bufsiz > 0 ? stream->bufsiz : 1;
    }
  }

  // We finished successfully, so just return num
  return num;
}
Beispiel #6
0
size_t fread(void *buffer, size_t size, size_t num, FILE *stream) {
  char *data;                     // Point to where should be read next
  unsigned total;                 // Total bytes to read
  unsigned count;                 // Num bytes left to read
  unsigned bufsize;               // Size of stream buffer
  unsigned nbytes;                // How much to read now
  unsigned nread;                 // How much we did read
  int c;                          // A temp char

  // Initialize local vars
  data = buffer;

  if ((count = total = size * num) == 0) return 0;

  if (anybuf(stream)) {
    // Already has buffer, use its size
    bufsize = stream->bufsiz;
  } else {
    // Assume will get BUFSIZ buffer
    bufsize = BUFSIZ;
  }

  // Here is the main loop -- we go through here until we're done
  while (count != 0) {
    // if the buffer exists and has characters, copy them to user buffer
    if (anybuf(stream) && stream->cnt != 0) {
      // How much do we want?
      nbytes = (count < (unsigned) stream->cnt) ? count : stream->cnt;
      memcpy(data, stream->ptr, nbytes);

      // Update stream and amount of data read
      count -= nbytes;
      stream->cnt -= nbytes;
      stream->ptr += nbytes;
      data += nbytes;
    } else if (count >= bufsize) {
      // If we have more than bufsize chars to read, get data
      // by calling read with an integral number of bufsiz
      // blocks.

      // Calc chars to read -- (count / bufsize) * bufsize
      nbytes = bufsize ? count - count % bufsize : count;

      nread = read(fileno(stream), data, nbytes);
      if (nread == 0) {
        // End of file -- out of here
        stream->flag |= _IOEOF;
        return (total - count) / size;
      } else if ((int) nread < 0) {
        // Error -- out of here
        stream->flag |= _IOERR;
        return (total - count) / size;
      }

      // Update count and data to reflect read
      count -= nread;
      data += nread;
    } else {
      // Less than bufsize chars to read, so call filbuf to fill buffer
      if ((c = filbuf(stream)) == EOF) {
        // Error or eof, stream flags set by filbuf
        return (total - count) / size;
      }

      // filbuf returned a char -- store it
      *data++ = (char) c;
      count--;

      // Update buffer size
      bufsize = stream->bufsiz;
    }
  }

  // We finished successfully, so just return num
  return num;
}
Beispiel #7
0
int flsbuf(int ch, FILE *stream) {
  int count;
  int written;
  int fh;
  char chbuf;

  fh = fileno(stream);

  if (!(stream->flag & (_IOWR | _IORW)) || (stream->flag & _IOSTR)) {
    stream->flag |= _IOERR;
    return -1;
  }

  if (stream->flag & _IORD) {
    stream->cnt = 0;
    if (stream->flag & _IOEOF) {
      stream->ptr = stream->base;
      stream->flag &= ~_IORD;
    } else {
      stream->flag |= _IOERR;
      return -1;
    }
  }

  stream->flag |= _IOWR;
  stream->flag &= ~_IOEOF;
  written = count = stream->cnt = 0;

  // Get a buffer for this stream, if necessary
  if (!anybuf(stream)) getbuf(stream);

  // If big buffer is assigned to stream
  if (bigbuf(stream)) {
    count = stream->ptr - stream->base;
    stream->ptr = stream->base + 1;
    stream->cnt = stream->bufsiz - 1;

    if (count > 0) {
      if (stream->flag & _IOCRLF) {
        written = write_translated(fh, stream->base, count);
      } else {
        written = write(fh, stream->base, count);
      }
    }

    *stream->base = (char) ch;
  } else {
    // Perform single character output (either _IONBF or no buffering)
    count = 1;
    chbuf = (char) ch;
    if (stream->flag & _IOCRLF) {
      written = write_translated(fh, &chbuf, count);
    } else {
      written = write(fh, &chbuf, count);
    }
  }

  // See if the write was successful.
  if (written != count) {
    stream->flag |= _IOERR;
    return -1;
  }

  return ch & 0xff;
}
Beispiel #8
0
/* define the normal version */
size_t __cdecl _fread_nolock_s(
    void *buffer,
    size_t bufferSize,
    size_t elementSize,
    size_t num,
    FILE *stream
)
{
    char *data;                     /* point inside the destination buffer to where we need to copy the read chars */
    size_t dataSize;                /* space left in the destionation buffer (in bytes) */
    size_t total;                   /* total bytes to read */
    size_t count;                   /* num bytes left to read */
    unsigned streambufsize;         /* size of stream buffer */
    unsigned nbytes;                /* how much to read now */
    unsigned nread;                 /* how much we did read */
    int c;                          /* a temp char */

    /* initialize local vars */
    data = buffer;
    dataSize = bufferSize;

    if (elementSize == 0 || num == 0)
    {
        return 0;
    }


    count = total = elementSize * num;

    if (anybuf(stream))
    {
        /* already has buffer, use its size */
        streambufsize = stream->_bufsiz;
    }
    else
    {
        /* assume will get _INTERNAL_BUFSIZ buffer */
        streambufsize = _INTERNAL_BUFSIZ;
    }

    /* here is the main loop -- we go through here until we're done */
    while (count != 0) {
        /* if the buffer exists and has characters, copy them to user
            buffer */
        if (anybuf(stream) && stream->_cnt != 0)
        {
            if(stream->_cnt < 0)
            {
                _ASSERTE(("Inconsistent Stream Count. Flush between consecutive read and write", stream->_cnt >= 0));
                stream->_flag |= _IOERR;
                return (total - count) / elementSize;
            }

            /* how much do we want? */
            nbytes = (count < (size_t)stream->_cnt) ? (unsigned)count : stream->_cnt;
            if (nbytes > dataSize)
            {
                if (bufferSize != SIZE_MAX)
                {
                    memset(buffer, _BUFFER_FILL_PATTERN, bufferSize);
                }
                _VALIDATE_RETURN(("buffer too small", 0), ERANGE, 0)
            }
            memcpy_s(data, dataSize, stream->_ptr, nbytes);

            /* update stream and amt of data read */
            count -= nbytes;
            stream->_cnt -= nbytes;
            stream->_ptr += nbytes;
            data += nbytes;
            dataSize -= nbytes;
        }
        else if (count >= streambufsize)
        {
            /* If we have more than streambufsize chars to read, get data
                by calling read with an integral number of bufsiz
                blocks.  Note that if the stream is text mode, read
                will return less chars than we ordered. */

            /* calc chars to read -- (count/streambufsize) * streambufsize */
            nbytes = ( streambufsize ? (unsigned)(count - count % streambufsize) :
                        (unsigned)count );
            if (nbytes > dataSize)
            {
                if (bufferSize != SIZE_MAX)
                {
                    memset(buffer, _BUFFER_FILL_PATTERN, bufferSize);
                }
                _VALIDATE_RETURN(("buffer too small", 0), ERANGE, 0)
            }

            nread = _read(_fileno(stream), data, nbytes);
            if (nread == 0) {
                    /* end of file -- out of here */
                    stream->_flag |= _IOEOF;
                    return (total - count) / elementSize;
            }
            else if (nread == (unsigned)-1) {
                    /* error -- out of here */
                    stream->_flag |= _IOERR;
                    return (total - count) / elementSize;
            }

            /* update count and data to reflect read */
            count -= nread;
            data += nread;
            dataSize -= nread;
        }
Beispiel #9
0
int __cdecl _filwbuf (
        FILE *str
        )

#endif  /* _UNICODE */

{

        REG1 FILE *stream=NULL;

                /* In safecrt, we assume we always have a buffer */
        _VALIDATE_RETURN(str != NULL, EINVAL, _TEOF);

        /* Init pointer to _iob2 entry. */
        stream = str;

        if (!inuse(stream) || stream->_flag & _IOSTRG)
                return(_TEOF);

        if (stream->_flag & _IOWRT) {
                stream->_flag |= _IOERR;
                return(_TEOF);
        }

        stream->_flag |= _IOREAD;

        /* Get a buffer, if necessary. */

        if (!anybuf(stream))
        {
#ifndef _SAFECRT_IMPL
            _getbuf(stream);
#else  /* _SAFECRT_IMPL */
            /* In safecrt, we assume we always have a buffer */
            _VALIDATE_RETURN(FALSE, EINVAL, _TEOF);
#endif  /* _SAFECRT_IMPL */
        }
        else
        {
            stream->_ptr = stream->_base;
        }

        stream->_cnt = _read(_fileno(stream), stream->_base, stream->_bufsiz);

#ifndef _UNICODE
        if ((stream->_cnt == 0) || (stream->_cnt == -1)) {
#else  /* _UNICODE */
        if ((stream->_cnt == 0) || (stream->_cnt == 1) || stream->_cnt == -1) {
#endif  /* _UNICODE */
                stream->_flag |= stream->_cnt ? _IOERR : _IOEOF;
                stream->_cnt = 0;
                return(_TEOF);
        }

        if (  !(stream->_flag & (_IOWRT|_IORW)) &&
              ((_osfile_safe(_fileno(stream)) & (FTEXT|FEOFLAG)) ==
                (FTEXT|FEOFLAG)) )
                stream->_flag |= _IOCTRLZ;
        /* Check for small _bufsiz (_SMALL_BUFSIZ). If it is small and
           if it is our buffer, then this must be the first _filbuf after
           an fseek on a read-access-only stream. Restore _bufsiz to its
           larger value (_INTERNAL_BUFSIZ) so that the next _filbuf call,
           if one is made, will fill the whole buffer. */
        if ( (stream->_bufsiz == _SMALL_BUFSIZ) && (stream->_flag &
              _IOMYBUF) && !(stream->_flag & _IOSETVBUF) )
        {
                stream->_bufsiz = _INTERNAL_BUFSIZ;
        }
#ifndef _UNICODE
        stream->_cnt--;
        return(0xff & *stream->_ptr++);
#else  /* _UNICODE */
        stream->_cnt -= sizeof(wchar_t);
        return (0xffff & *((wchar_t *)(stream->_ptr))++);
#endif  /* _UNICODE */

}
Beispiel #10
0
int __cdecl _flswbuf (
        int ch,
        FILE *str
        )

#endif  /* _UNICODE */

{

        REG1 FILE *stream;
        REG2 int charcount;
        REG3 int written;
        int fh;

        _ASSERTE(str != NULL);

        /* Init file handle and pointers */
        stream = str;
        fh = _fileno(stream);

        if (!(stream->_flag & (_IOWRT|_IORW))) {
                errno = EBADF;
                stream->_flag |= _IOERR;
                return(_TEOF);
        } else if ((stream->_flag & _IOSTRG)) {
                errno = ERANGE;
                stream->_flag |= _IOERR;
                return(_TEOF);
        }

        /* Check that _IOREAD is not set or, if it is, then so is _IOEOF. Note
           that _IOREAD and IOEOF both being set implies switching from read to
           write at end-of-file, which is allowed by ANSI. Note that resetting
           the _cnt and _ptr fields amounts to doing an fflush() on the stream
           in this case. Note also that the _cnt field has to be reset to 0 for
           the error path as well (i.e., _IOREAD set but _IOEOF not set) as
           well as the non-error path. */

        if (stream->_flag & _IOREAD) {
                stream->_cnt = 0;
                if (stream->_flag & _IOEOF) {
                        stream->_ptr = stream->_base;
                        stream->_flag &= ~_IOREAD;
                }
                else {
                        stream->_flag |= _IOERR;
                        return(_TEOF);
                }
        }

        stream->_flag |= _IOWRT;
        stream->_flag &= ~_IOEOF;
        written = charcount = stream->_cnt = 0;

        /* Get a buffer for this stream, if necessary. */
        if (!anybuf(stream)) {

                /* Do NOT get a buffer if (1) stream is stdout/stderr, and
                   (2) stream is NOT a tty.
                   [If stdout/stderr is a tty, we do NOT set up single char
                   buffering. This is so that later temporary buffering will
                   not be thwarted by the _IONBF bit being set (see
                   _stbuf/_ftbuf usage).]
                */
                if (!( ((stream==stdout) || (stream==stderr))
                && (_isatty(fh)) ))

                        _getbuf(stream);

        } /* end !anybuf() */

        /* If big buffer is assigned to stream... */
        if (bigbuf(stream)) {

                _ASSERTE(("inconsistent IOB fields", stream->_ptr - stream->_base >= 0));

                charcount = (int)(stream->_ptr - stream->_base);
                stream->_ptr = stream->_base + sizeof(TCHAR);
                stream->_cnt = stream->_bufsiz - (int)sizeof(TCHAR);

                if (charcount > 0)
                        written = _write(fh, stream->_base, charcount);
                else
                        if (_osfile_safe(fh) & FAPPEND)
                                                {
                                                        if( _lseeki64(fh,0L,SEEK_END)==-1)
                                                        {
                                                                stream->_flag |= _IOERR;
                                                                return(_TEOF);
                                                        }
                                                }

#ifndef _UNICODE
                *stream->_base = (char)ch;
#else  /* _UNICODE */
                *(wchar_t *)(stream->_base) = (wchar_t)(ch & 0xffff);
#endif  /* _UNICODE */
        }

    /* Perform single character output (either _IONBF or no buffering) */
        else {
                charcount = sizeof(TCHAR);
#ifndef _UNICODE
                written = _write(fh, &ch, charcount);
#else  /* _UNICODE */
                {
                        char mbc[4];

                        *(wchar_t *)mbc = (wchar_t)(ch & 0xffff);
                        written = _write(fh, mbc, charcount);
                }
#endif  /* _UNICODE */
        }

        /* See if the _write() was successful. */
        if (written != charcount) {
                stream->_flag |= _IOERR;
                return(_TEOF);
        }

#ifndef _UNICODE
        return(ch & 0xff);
#else  /* _UNICODE */
        return(ch & 0xffff);
#endif  /* _UNICODE */

}
Beispiel #11
0
int __cdecl _filwbuf (
	FILE *str
	)

#endif	/* _UNICODE */

{
#ifdef	_NTSUBSET_

	return(_TEOF);

#else	/* ndef _NTSUBSET_ */

	REG1 FILE *stream;

	_ASSERTE(str != NULL);

	/* Init pointer to _iob2 entry. */
	stream = str;

	if (!inuse(stream) || stream->_flag & _IOSTRG)
		return(_TEOF);

	if (stream->_flag & _IOWRT) {
#ifdef	_POSIX_
		errno = EBADF;
#endif
		stream->_flag |= _IOERR;
		return(_TEOF);
	}

	stream->_flag |= _IOREAD;

	/* Get a buffer, if necessary. */

	if (!anybuf(stream))
		_getbuf(stream);
	else
		stream->_ptr = stream->_base;

#ifdef	_POSIX_
	stream->_cnt = read(fileno(stream), stream->_base, stream->_bufsiz);
#else
	stream->_cnt = _read(_fileno(stream), stream->_base, stream->_bufsiz);
#endif

#ifndef _UNICODE
	if ((stream->_cnt == 0) || (stream->_cnt == -1)) {
#else /* _UNICODE */
	if ((stream->_cnt == 0) || (stream->_cnt == 1) || stream->_cnt == -1) {
#endif /* _UNICODE */
		stream->_flag |= stream->_cnt ? _IOERR : _IOEOF;
		stream->_cnt = 0;
		return(_TEOF);
	}

#ifndef _POSIX_
	if (  !(stream->_flag & (_IOWRT|_IORW)) &&
	      ((_osfile_safe(_fileno(stream)) & (FTEXT|FEOFLAG)) == 
                (FTEXT|FEOFLAG)) )
		stream->_flag |= _IOCTRLZ;
#endif
	/* Check for small _bufsiz (_SMALL_BUFSIZ). If it is small and
	   if it is our buffer, then this must be the first _filbuf after
	   an fseek on a read-access-only stream. Restore _bufsiz to its
	   larger value (_INTERNAL_BUFSIZ) so that the next _filbuf call,
	   if one is made, will fill the whole buffer. */
	if ( (stream->_bufsiz == _SMALL_BUFSIZ) && (stream->_flag &
	      _IOMYBUF) && !(stream->_flag & _IOSETVBUF) )
	{
		stream->_bufsiz = _INTERNAL_BUFSIZ;
	}
#ifndef _UNICODE
	stream->_cnt--;
	return(0xff & *stream->_ptr++);
#else	/* _UNICODE */
	stream->_cnt -= sizeof(wchar_t);
	return (0xffff & *((wchar_t *)(stream->_ptr))++);
#endif	/* _UNICODE */

#endif	/* _NTSUBSET_ */
}


#else	/* ndef _WIN32 */

#if	defined(_M_MPPC) || defined(_M_M68K)


#include <cruntime.h>
#include <stdio.h>
#include <file2.h>
#include <io.h>
#include <dbgint.h>
#include <malloc.h>
#include <internal.h>
#include <msdos.h>

/***
*int _filbuf(stream) - fill buffer and get first character
*
*Purpose:
*	get a buffer if the file doesn't have one, read into it, return first
*	char. try to get a buffer, if a user buffer is not assigned. called
*	only from getc; intended for use only within library. assume no input
*	stream is to remain unbuffered when memory is available unless it is
*	marked _IONBF. at worst, give it a single char buffer. the need for a
*	buffer, no matter how small, becomes evident when we consider the
*	ungetc's necessary in scanf
*
*Entry:
*	FILE *stream - stream to read from
*
*Exit:
*	returns first character from buffer (next character to be read)
*	returns EOF if the FILE is actually a string, or not open for reading,
*	or if open for writing or if no more chars to read.
*	all fields in FILE structure may be changed except _file.
*
*Exceptions:
*
*******************************************************************************/

int __cdecl _filbuf (
	FILE *str
	)
{
	REG1 FILE *stream;

	_ASSERTE(str != NULL);

	/* Init pointer to _iob2 entry. */
	stream = str;

	if (!inuse(stream) || stream->_flag & _IOSTRG)
		return(EOF);

	if (stream->_flag & _IOWRT) {
		stream->_flag |= _IOERR;
		return(EOF);
	}

	stream->_flag |= _IOREAD;

	/* Get a buffer, if necessary. */

	if (!anybuf(stream))
		_getbuf(stream);
	else
		stream->_ptr = stream->_base;

	stream->_cnt = _read(_fileno(stream), stream->_base, stream->_bufsiz);

	if ((stream->_cnt == 0) || (stream->_cnt == -1)) {
		stream->_flag |= stream->_cnt ? _IOERR : _IOEOF;
		stream->_cnt = 0;
		return(EOF);
	}

	if (  !(stream->_flag & (_IOWRT|_IORW)) &&
	((_osfile[_fileno(stream)] & (FTEXT|FEOFLAG)) == (FTEXT|FEOFLAG)) )
		stream->_flag |= _IOCTRLZ;

	stream->_cnt--;

	return(0xff & *stream->_ptr++);
}
Beispiel #12
0
/* define the normal version */
#ifdef _MT
size_t __cdecl _fwrite_lk (
#else  /* _MT */
size_t __cdecl fwrite (
#endif  /* _MT */
        const void *buffer,
        size_t size,
        size_t num,
        FILE *stream
        )
{
        const char *data;               /* point to where data comes from next */
        unsigned total;                 /* total bytes to write */
        unsigned count;                 /* num bytes left to write */
        unsigned bufsize;               /* size of stream buffer */
        unsigned nbytes;                /* number of bytes to write now */
        unsigned nwritten;              /* number of bytes written */
        int c;                          /* a temp char */

        /* initialize local vars */
        data = buffer;
        count = total = size * num;
        if (0 == count)
            return 0;

        if (anybuf(stream))
                /* already has buffer, use its size */
                bufsize = stream->_bufsiz;
        else
#if defined (_M_M68K) || defined (_M_MPPC)
                /* assume will get BUFSIZ buffer */
                bufsize = BUFSIZ;
#else  /* defined (_M_M68K) || defined (_M_MPPC) */
                /* assume will get _INTERNAL_BUFSIZ buffer */
                bufsize = _INTERNAL_BUFSIZ;
#endif  /* defined (_M_M68K) || defined (_M_MPPC) */

        /* here is the main loop -- we go through here until we're done */
        while (count != 0) {
                /* if the buffer is big and has room, copy data to buffer */
                if (bigbuf(stream) && stream->_cnt != 0) {
                        /* how much do we want? */
                        nbytes = (count < (unsigned)stream->_cnt) ? count : stream->_cnt;
                        memcpy(stream->_ptr, data, nbytes);

                        /* update stream and amt of data written */
                        count -= nbytes;
                        stream->_cnt -= nbytes;
                        stream->_ptr += nbytes;
                        data += nbytes;
                }
                else if (count >= bufsize) {
                        /* If we have more than bufsize chars to write, write
                           data by calling write with an integral number of
                           bufsiz blocks.  If we reach here and we have a big
                           buffer, it must be full so _flush it. */

                        if (bigbuf(stream)) {
                                if (_flush(stream)) {
                                        /* error, stream flags set -- we're out
                                           of here */
                                        return (total - count) / size;
                                }
                        }

                        /* calc chars to read -- (count/bufsize) * bufsize */
                        nbytes = ( bufsize ? (count - count % bufsize) :
                                   count );

                        nwritten = _write(_fileno(stream), data, nbytes);
                        if (nwritten == (unsigned)EOF) {
                                /* error -- out of here */
                                stream->_flag |= _IOERR;
                                return (total - count) / size;
                        }

                        /* update count and data to reflect write */

                        count -= nwritten;
                        data += nwritten;

                        if (nwritten < nbytes) {
                                /* error -- out of here */
                                stream->_flag |= _IOERR;
                                return (total - count) / size;
                        }
                }
                else {
                        /* buffer full and not enough chars to do direct write,
                           so do a _flsbuf. */
                        c = *data;  /* _flsbuf write one char, this is it */
                        if (_flsbuf(c, stream) == EOF) {
                                /* error or eof, stream flags set by _flsbuf */
                                return (total - count) / size;
                        }

                        /* _flsbuf wrote a char -- update count */
                        ++data;
                        --count;

                        /* update buffer size */
                        bufsize = stream->_bufsiz > 0 ? stream->_bufsiz : 1;
                }
        }

        /* we finished successfully, so just return num */
        return num;
}