From 7d16436c5c6dafa358c4beb7e04f3d783a178bfb Mon Sep 17 00:00:00 2001 From: gambas Date: Mon, 27 Aug 2018 23:57:30 +0200 Subject: [PATCH] Eof() now correctly works on file bigger than 4GB opened in direct mode. [INTERPRETER] * BUG: Eof() now correctly works on file bigger than 4GB opened in direct mode. --- main/gbx/gbx_stream.c | 4 ++-- main/gbx/gbx_stream.h | 3 +++ main/gbx/gbx_stream_direct.c | 30 +++++++++++++++++++++++++++++- main/gbx/gbx_stream_process.c | 14 -------------- 4 files changed, 34 insertions(+), 17 deletions(-) diff --git a/main/gbx/gbx_stream.c b/main/gbx/gbx_stream.c index 8da0ec2ab..e2797eedd 100644 --- a/main/gbx/gbx_stream.c +++ b/main/gbx/gbx_stream.c @@ -141,7 +141,7 @@ int STREAM_get_readable(STREAM *stream, int *len) return (-1); } -static int default_eof(STREAM *stream) +bool STREAM_default_eof(STREAM *stream) { int fd; int ilen; @@ -1710,7 +1710,7 @@ bool STREAM_eof(STREAM *stream) if (stream->type->eof) return ((*(stream->type->eof))(stream)); else - return default_eof(stream); + return STREAM_default_eof(stream); } diff --git a/main/gbx/gbx_stream.h b/main/gbx/gbx_stream.h index eeab36281..679c1b76c 100644 --- a/main/gbx/gbx_stream.h +++ b/main/gbx/gbx_stream.h @@ -83,6 +83,8 @@ typedef int64_t size; int fd; unsigned watch : 1; + unsigned has_size : 1; + unsigned use_size : 1; } STREAM_DIRECT; @@ -224,6 +226,7 @@ void STREAM_flush(STREAM *stream); int STREAM_handle(STREAM *stream); void STREAM_lof(STREAM *stream, int64_t *len); bool STREAM_eof(STREAM *stream); +bool STREAM_default_eof(STREAM *stream); void STREAM_load(const char *path, char **buffer, int *len); diff --git a/main/gbx/gbx_stream_direct.c b/main/gbx/gbx_stream_direct.c index 59becb047..c0ef4983d 100644 --- a/main/gbx/gbx_stream_direct.c +++ b/main/gbx/gbx_stream_direct.c @@ -119,6 +119,8 @@ static int stream_open(STREAM *stream, const char *path, int mode) stream->common.available_now = TRUE; } + stream->direct.has_size = FALSE; + FD = fd; return FALSE; } @@ -167,7 +169,33 @@ static int stream_flush(STREAM *stream) } -#define stream_eof NULL +static int stream_eof(STREAM *stream) +{ + struct stat info; + off_t pos; + + if (!stream->direct.has_size) + { + if (fstat(FD, &info) == 0) + { + stream->direct.use_size = TRUE; + stream->direct.size = info.st_size; + } + + stream->direct.has_size = TRUE; + } + + if (stream->direct.use_size && !stream->common.no_lseek) + { + pos = lseek(FD, 0, SEEK_CUR); + if (pos >= 0) + return pos >= stream->direct.size; + + stream->common.no_lseek = TRUE; + } + + return STREAM_default_eof(stream); +} static int stream_lof(STREAM *stream, int64_t *len) diff --git a/main/gbx/gbx_stream_process.c b/main/gbx/gbx_stream_process.c index de1df6d96..ad55f9b0c 100644 --- a/main/gbx/gbx_stream_process.c +++ b/main/gbx/gbx_stream_process.c @@ -102,23 +102,9 @@ static int stream_flush(STREAM *stream) } -/*static int stream_eof(STREAM *stream) -{ - int ilen; - - if (STREAM_get_readable(FD, &ilen)) - return TRUE; - - return (ilen == 0); -}*/ #define stream_eof NULL -/*static int stream_lof(STREAM *stream, int64_t *len) -{ - *len = 0; //stream->direct.size; - return FALSE; -}*/ #define stream_lof NULL