diff options
author | Andreas Kling <awesomekling@gmail.com> | 2019-04-27 16:19:11 +0200 |
---|---|---|
committer | Andreas Kling <awesomekling@gmail.com> | 2019-04-27 16:19:11 +0200 |
commit | 100cb2a23720936369bf12bbc9d2ea59fa88f4fe (patch) | |
tree | 5a2cae1470b875a44b7d6ee438766a069b72cac8 /LibC/stdio.cpp | |
parent | 679ac386eb8e48628a08071e1a95cd2f1f1ca5af (diff) | |
download | serenity-100cb2a23720936369bf12bbc9d2ea59fa88f4fe.zip |
LibC: Various stdio correctness fixes.
Diffstat (limited to 'LibC/stdio.cpp')
-rw-r--r-- | LibC/stdio.cpp | 33 |
1 files changed, 22 insertions, 11 deletions
diff --git a/LibC/stdio.cpp b/LibC/stdio.cpp index 8b28d8e2ad..c5850cc2f9 100644 --- a/LibC/stdio.cpp +++ b/LibC/stdio.cpp @@ -95,16 +95,19 @@ int feof(FILE* stream) int fflush(FILE* stream) { - // FIXME: Implement buffered streams, duh. - if (!stream) - return -EBADF; + // FIXME: fflush(NULL) should flush all open output streams. + ASSERT(stream); if (!stream->buffer_index) return 0; int rc = write(stream->fd, stream->buffer, stream->buffer_index); stream->buffer_index = 0; - if (rc < 0) + stream->error = 0; + stream->eof = 0; + if (rc < 0) { stream->error = errno; - return rc; + return EOF; + } + return 0; } char* fgets(char* buffer, int size, FILE* stream) @@ -155,6 +158,8 @@ int getchar() int ungetc(int c, FILE* stream) { ASSERT(stream); + if (stream->have_ungotten) + return EOF; stream->have_ungotten = true; stream->ungotten = c; stream->eof = false; @@ -170,7 +175,7 @@ int fputc(int ch, FILE* stream) fflush(stream); else if (stream->mode == _IONBF || (stream->mode == _IOLBF && ch == '\n')) fflush(stream); - if (stream->eof) + if (stream->eof || stream->error) return EOF; return (byte)ch; } @@ -192,14 +197,14 @@ int fputs(const char* s, FILE* stream) if (rc == EOF) return EOF; } - return 0; + return 1; } int puts(const char* s) { int rc = fputs(s, stdout); - if (rc < 0) - return rc; + if (rc == EOF) + return EOF; return fputc('\n', stdout); } @@ -250,28 +255,34 @@ size_t fwrite(const void* ptr, size_t size, size_t nmemb, FILE* stream) { assert(stream); int rc = fflush(stream); - if (rc < 0) + if (rc == EOF) return 0; ssize_t nwritten = write(stream->fd, ptr, nmemb * size); if (nwritten < 0) { stream->error = errno; return 0; } - return nwritten; + return nwritten / size; } int fseek(FILE* stream, long offset, int whence) { assert(stream); + fflush(stream); off_t off = lseek(stream->fd, offset, whence); if (off < 0) return off; + stream->eof = false; + stream->error = 0; + stream->have_ungotten = false; + stream->ungotten = 0; return 0; } long ftell(FILE* stream) { assert(stream); + fflush(stream); return lseek(stream->fd, 0, SEEK_CUR); } |