]> pd.if.org Git - pdclib/blobdiff - functions/stdio/freopen.c
Reworking internal file handling.
[pdclib] / functions / stdio / freopen.c
index e8cc72a1f2924cba8e56c8acc5947ff2525ed7bf..a2c0adade6b91908d5644c7b3dbb1e7ad66fd6b7 100644 (file)
@@ -1,6 +1,6 @@
 /* $Id$ */
 
 /* $Id$ */
 
-/* freopen( const char *, const char * )
+/* freopen( const char *, const char *, FILE * )
 
    This file is part of the Public Domain C Library (PDCLib).
    Permission is granted to use, modify, and / or redistribute at will.
 
    This file is part of the Public Domain C Library (PDCLib).
    Permission is granted to use, modify, and / or redistribute at will.
    identified by the given filename with the given mode (equivalent to fopen()),
    and associate it with the given stream. If filename is a NULL pointer,
    attempt to change the mode of the given stream.
    identified by the given filename with the given mode (equivalent to fopen()),
    and associate it with the given stream. If filename is a NULL pointer,
    attempt to change the mode of the given stream.
-   This implementation allows the following mode changes: TODO
+   This implementation allows any mode changes.
    (Primary use of this function is to redirect stdin, stdout, and stderr.)
 */
    (Primary use of this function is to redirect stdin, stdout, and stderr.)
 */
-
-struct _PDCLIB_file_t * freopen( const char * _PDCLIB_restrict filename, const char * _PDCLIB_restrict mode, struct _PDCLIB_file_t * stream )
+struct _PDCLIB_file_t * freopen( const char * _PDCLIB_restrict filename, const char * _PDCLIB_restrict mode, struct _PDCLIB_file_t * _PDCLIB_restrict stream )
 {
 {
-    /* FIXME: This is ad-hoc (to make the vprintf() testdriver work), and must be checked. */
-    /* FIXME: If filename is NULL, change mode. */
+    unsigned int status = stream->status & ( _IONBF | _IOLBF | _IOFBF | _PDCLIB_FREEBUFFER | _PDCLIB_DELONCLOSE );
     /* TODO: This function can change wide orientation of a stream */
     /* TODO: This function can change wide orientation of a stream */
-    if ( filename == NULL ) return NULL;
-    if ( stream->status & _PDCLIB_FWRITE ) fflush( stream );
-    if ( stream->status & _PDCLIB_LIBBUFFER ) free( stream->buffer );
+    if ( stream->status & _PDCLIB_FWRITE )
+    {
+        _PDCLIB_flushbuffer( stream );
+    }
     _PDCLIB_close( stream->handle );
     clearerr( stream );
     _PDCLIB_close( stream->handle );
     clearerr( stream );
-    if ( ( mode == NULL ) || ( filename[0] == '\0' ) ) return NULL;
-    if ( ( stream->status = _PDCLIB_filemode( mode ) ) == 0 ) return NULL;
-    stream->handle = _PDCLIB_open( filename, stream->status );
-    if ( ( stream->buffer = malloc( BUFSIZ ) ) == NULL ) return NULL;
-    stream->bufsize = BUFSIZ;
+    /* FIXME: Copy filename into the FILE structure. */
+    /* FIXME: filename cannot reside in "big block" memory */
+    if ( filename == NULL )
+    {
+        filename = stream->filename;
+    }
+    if ( ( mode == NULL ) || ( filename[0] == '\0' ) )
+    {
+        return NULL;
+    }
+    if ( ( stream->status = _PDCLIB_filemode( mode ) ) == 0 )
+    {
+        return NULL;
+    }
+    /* Re-add the flags we saved above */
+    stream->status |= status;
     stream->bufidx = 0;
     stream->bufidx = 0;
-    stream->status |= _PDCLIB_LIBBUFFER;
+    stream->bufend = 0;
+    stream->ungetidx = 0;
     /* TODO: Setting mbstate */
     /* TODO: Setting mbstate */
+    if ( ( stream->handle = _PDCLIB_open( filename, stream->status ) ) == _PDCLIB_NOHANDLE )
+    {
+        return NULL;
+    }
     return stream;
 }
 
     return stream;
 }