diff options
-rw-r--r-- | libc/stdio/_stdio.h | 153 | ||||
-rw-r--r-- | libc/stdio/fflush.c | 29 | ||||
-rw-r--r-- | libc/sysdeps/linux/common/bits/uClibc_stdio.h | 1 |
3 files changed, 75 insertions, 108 deletions
diff --git a/libc/stdio/_stdio.h b/libc/stdio/_stdio.h index 6647a6f0e..4c1e4415f 100644 --- a/libc/stdio/_stdio.h +++ b/libc/stdio/_stdio.h @@ -20,75 +20,53 @@ #include <wchar.h> #endif -#ifdef __UCLIBC_HAS_THREADS__ -#include <pthread.h> +#include <bits/uClibc_mutex.h> -#define __STDIO_THREADLOCK_OPENLIST_ADD \ - do { \ - struct _pthread_cleanup_buffer __infunc_pthread_cleanup_buffer; \ - _pthread_cleanup_push_defer(&__infunc_pthread_cleanup_buffer, \ - __pthread_mutex_unlock, \ - &_stdio_openlist_add_lock); \ - __pthread_mutex_lock(&_stdio_openlist_add_lock); \ - -#define __STDIO_THREADUNLOCK_OPENLIST_ADD \ - _pthread_cleanup_pop_restore(&__infunc_pthread_cleanup_buffer,1); \ - } while (0) +#define __STDIO_THREADLOCK_OPENLIST_ADD \ + __UCLIBC_MUTEX_LOCK(_stdio_openlist_add_lock) +#define __STDIO_THREADUNLOCK_OPENLIST_ADD \ + __UCLIBC_MUTEX_UNLOCK(_stdio_openlist_add_lock) #ifdef __STDIO_BUFFERS -#define __STDIO_THREADLOCK_OPENLIST_DEL \ - do { \ - struct _pthread_cleanup_buffer __infunc_pthread_cleanup_buffer; \ - _pthread_cleanup_push_defer(&__infunc_pthread_cleanup_buffer, \ - __pthread_mutex_unlock, \ - &_stdio_openlist_del_lock); \ - __pthread_mutex_lock(&_stdio_openlist_del_lock); \ +#define __STDIO_THREADLOCK_OPENLIST_DEL \ + __UCLIBC_MUTEX_LOCK(_stdio_openlist_del_lock) -#define __STDIO_THREADUNLOCK_OPENLIST_DEL \ - _pthread_cleanup_pop_restore(&__infunc_pthread_cleanup_buffer,1); \ - } while (0) +#define __STDIO_THREADUNLOCK_OPENLIST_DEL \ + __UCLIBC_MUTEX_UNLOCK(_stdio_openlist_del_lock) -#define __STDIO_OPENLIST_INC_USE \ -do { \ - __STDIO_THREADLOCK_OPENLIST_DEL; \ - ++_stdio_openlist_use_count; \ - __STDIO_THREADUNLOCK_OPENLIST_DEL; \ +#define __STDIO_OPENLIST_INC_USE \ +do { \ + __STDIO_THREADLOCK_OPENLIST_DEL; \ + ++_stdio_openlist_use_count; \ + __STDIO_THREADUNLOCK_OPENLIST_DEL; \ } while (0) extern void _stdio_openlist_dec_use(void); -#define __STDIO_OPENLIST_DEC_USE \ +#define __STDIO_OPENLIST_DEC_USE \ _stdio_openlist_dec_use() -#define __STDIO_OPENLIST_INC_DEL_CNT \ -do { \ - __STDIO_THREADLOCK_OPENLIST_DEL; \ - ++_stdio_openlist_del_count; \ - __STDIO_THREADUNLOCK_OPENLIST_DEL; \ +#define __STDIO_OPENLIST_INC_DEL_CNT \ +do { \ + __STDIO_THREADLOCK_OPENLIST_DEL; \ + ++_stdio_openlist_del_count; \ + __STDIO_THREADUNLOCK_OPENLIST_DEL; \ } while (0) -#define __STDIO_OPENLIST_DEC_DEL_CNT \ +#define __STDIO_OPENLIST_DEC_DEL_CNT \ do { \ - __STDIO_THREADLOCK_OPENLIST_DEL; \ - --_stdio_openlist_del_count; \ - __STDIO_THREADUNLOCK_OPENLIST_DEL; \ + __STDIO_THREADLOCK_OPENLIST_DEL; \ + --_stdio_openlist_del_count; \ + __STDIO_THREADUNLOCK_OPENLIST_DEL; \ } while (0) -#endif - -#endif /* __UCLIBC_HAS_THREADS__ */ - -#ifndef __STDIO_THREADLOCK_OPENLIST_ADD -#define __STDIO_THREADLOCK_OPENLIST_ADD ((void)0) -#define __STDIO_THREADUNLOCK_OPENLIST_ADD ((void)0) -#endif +#endif /* __STDIO_BUFFERS */ #ifndef __STDIO_THREADLOCK_OPENLIST_DEL #define __STDIO_THREADLOCK_OPENLIST_DEL ((void)0) #define __STDIO_THREADUNLOCK_OPENLIST_DEL ((void)0) -/* #define __STDIO_OPENLIST_USE_CNT() (0) */ #define __STDIO_OPENLIST_INC_USE ((void)0) #define __STDIO_OPENLIST_DEC_USE ((void)0) #define __STDIO_OPENLIST_INC_DEL_CNT ((void)0) @@ -176,30 +154,30 @@ extern int __stdio_seek(FILE *stream, register __offmax_t *pos, int whence) attr /**********************************************************************/ #ifdef __UCLIBC_HAS_WCHAR__ -#define __STDIO_STREAM_IS_NARROW_WRITING(S) \ - (((S)->__modeflags & (__FLAG_WRITING|__FLAG_NARROW)) \ +#define __STDIO_STREAM_IS_NARROW_WRITING(S) \ + (((S)->__modeflags & (__FLAG_WRITING|__FLAG_NARROW)) \ == (__FLAG_WRITING|__FLAG_NARROW)) -#define __STDIO_STREAM_IS_WIDE_WRITING(S) \ - (((S)->__modeflags & (__FLAG_WRITING|__FLAG_WIDE)) \ +#define __STDIO_STREAM_IS_WIDE_WRITING(S) \ + (((S)->__modeflags & (__FLAG_WRITING|__FLAG_WIDE)) \ == (__FLAG_WRITING|__FLAG_WIDE)) #if (__FLAG_NARROW <= __MASK_READING) #error assumption violated regarding __FLAG_NARROW #endif -#define __STDIO_STREAM_IS_NARROW_READING(S) \ +#define __STDIO_STREAM_IS_NARROW_READING(S) \ (((S)->__modeflags & (__MASK_READING|__FLAG_NARROW)) > __FLAG_NARROW) -#define __STDIO_STREAM_IS_WIDE_READING(S) \ +#define __STDIO_STREAM_IS_WIDE_READING(S) \ (((S)->__modeflags & (__MASK_READING|__FLAG_WIDE)) > __FLAG_WIDE) #define __STDIO_STREAM_IS_NARROW(S) ((S)->__modeflags & __FLAG_NARROW) #define __STDIO_STREAM_IS_WIDE(S) ((S)->__modeflags & __FLAG_WIDE) -#define __STDIO_STREAM_SET_NARROW(S) \ +#define __STDIO_STREAM_SET_NARROW(S) \ ((void)((S)->__modeflags |= __FLAG_NARROW)) -#define __STDIO_STREAM_SET_WIDE(S) \ +#define __STDIO_STREAM_SET_WIDE(S) \ ((void)((S)->__modeflags |= __FLAG_WIDE)) #else @@ -208,11 +186,11 @@ extern int __stdio_seek(FILE *stream, register __offmax_t *pos, int whence) attr #define __STDIO_STREAM_IS_NARROW_READING(S) __STDIO_STREAM_IS_READING(S) -#define __STDIO_STREAM_IS_NARROW(S) (1) -#define __STDIO_STREAM_IS_WIDE(S) (0) +#define __STDIO_STREAM_IS_NARROW(S) (1) +#define __STDIO_STREAM_IS_WIDE(S) (0) -#define __STDIO_STREAM_SET_NARROW(S) ((void)0) -#define __STDIO_STREAM_SET_WIDE(S) ((void)0) +#define __STDIO_STREAM_SET_NARROW(S) ((void)0) +#define __STDIO_STREAM_SET_WIDE(S) ((void)0) #endif /**********************************************************************/ @@ -242,7 +220,7 @@ extern int __stdio_seek(FILE *stream, register __offmax_t *pos, int whence) attr #else # define __STDIO_STREAM_DISABLE_GETC(S) ((void)0) # define __STDIO_STREAM_ENABLE_GETC(S) ((void)0) -# define __STDIO_STREAM_CAN_USE_BUFFER_GET(S) (0) +# define __STDIO_STREAM_CAN_USE_BUFFER_GET(S) (0) #endif #ifdef __UCLIBC_HAS_STDIO_PUTC_MACRO__ @@ -255,26 +233,28 @@ extern int __stdio_seek(FILE *stream, register __offmax_t *pos, int whence) attr #else # define __STDIO_STREAM_DISABLE_PUTC(S) ((void)0) # define __STDIO_STREAM_ENABLE_PUTC(S) ((void)0) -# define __STDIO_STREAM_CAN_USE_BUFFER_ADD(S) (0) +# define __STDIO_STREAM_CAN_USE_BUFFER_ADD(S) (0) #endif #ifdef __UCLIBC_HAS_GLIBC_CUSTOM_STREAMS__ #define __STDIO_STREAM_IS_CUSTOM(S) ((S)->__cookie != &((S)->__filedes)) #else -#define __STDIO_STREAM_IS_CUSTOM(S) (0) +#define __STDIO_STREAM_IS_CUSTOM(S) (0) #endif /**********************************************************************/ #ifdef __STDIO_BUFFERS -#define __STDIO_STREAM_FREE_BUFFER(S) \ - do { if ((S)->__modeflags & __FLAG_FREEBUF) free((S)->__bufstart); } while (0) +#define __STDIO_STREAM_FREE_BUFFER(S) \ + do { if ((S)->__modeflags & __FLAG_FREEBUF) \ + free((S)->__bufstart); } while (0) #else #define __STDIO_STREAM_FREE_BUFFER(S) ((void)0) #endif #define __STDIO_STREAM_FREE_FILE(S) \ - do { if ((S)->__modeflags & __FLAG_FREEFILE) free((S)); } while (0) + do { if ((S)->__modeflags & __FLAG_FREEFILE) \ + free((S)); } while (0) #ifdef __UCLIBC_HAS_LFS__ @@ -296,7 +276,7 @@ extern size_t __stdio_wcommit(FILE *__restrict stream) attribute_hidden; extern size_t __stdio_rfill(FILE *__restrict stream) attribute_hidden; extern size_t __stdio_fwrite(const unsigned char *__restrict buffer, - size_t bytes, FILE *__restrict stream) attribute_hidden; + size_t bytes, FILE *__restrict stream) attribute_hidden; #else #define __stdio_fwrite(B,N,S) __stdio_WRITE((S),(B),(N)) @@ -304,8 +284,9 @@ extern size_t __stdio_fwrite(const unsigned char *__restrict buffer, #endif extern size_t __stdio_WRITE(FILE *stream, const unsigned char *buf, - size_t bufsize) attribute_hidden; -extern size_t __stdio_READ(FILE *stream, unsigned char *buf, size_t bufsize) attribute_hidden; + size_t bufsize) attribute_hidden; +extern size_t __stdio_READ(FILE *stream, unsigned char *buf, + size_t bufsize) attribute_hidden; extern int __stdio_trans2r(FILE *__restrict stream) attribute_hidden; extern int __stdio_trans2w(FILE *__restrict stream) attribute_hidden; @@ -338,14 +319,14 @@ extern int __stdio_trans2w_o(FILE *__restrict stream, int oflag) attribute_hidde /* Valid when reading... */ #define __STDIO_STREAM_BUFFER_RAVAIL(S) ((S)->__bufread - (S)->__bufpos) #define __STDIO_STREAM_BUFFER_GET(S) (*(S)->__bufpos++) -#define __STDIO_FILL_READ_BUFFER(S) __stdio_rfill((S)) +#define __STDIO_FILL_READ_BUFFER(S) __stdio_rfill((S)) -#define __STDIO_STREAM_INIT_BUFREAD_BUFPOS(S) \ +#define __STDIO_STREAM_INIT_BUFREAD_BUFPOS(S) \ (S)->__bufread = (S)->__bufpos = (S)->__bufstart #define __STDIO_STREAM_FAKE_VSNPRINTF_FILEDES (-2) -#define __STDIO_STREAM_FAKE_VSSCANF_FILEDES (-2) +#define __STDIO_STREAM_FAKE_VSSCANF_FILEDES (-2) #define __STDIO_STREAM_FAKE_VSWPRINTF_FILEDES (-3) #define __STDIO_STREAM_FAKE_VSWSCANF_FILEDES (-3) @@ -360,9 +341,9 @@ extern int __stdio_trans2w_o(FILE *__restrict stream, int oflag) attribute_hidde #else /* __STDIO_BUFFERS */ -#define __STDIO_STREAM_IS_FBF(S) (0) -#define __STDIO_STREAM_IS_LBF(S) (0) -#define __STDIO_STREAM_IS_NBF(S) (1) +#define __STDIO_STREAM_IS_FBF(S) (0) +#define __STDIO_STREAM_IS_LBF(S) (0) +#define __STDIO_STREAM_IS_NBF(S) (1) #define __STDIO_STREAM_BUFFER_SIZE(S) (0) #define __STDIO_STREAM_BUFFER_ADD(S,C) ((void)0) @@ -374,8 +355,8 @@ extern int __stdio_trans2w_o(FILE *__restrict stream, int oflag) attribute_hidde #define __STDIO_STREAM_BUFFER_RAVAIL(S) (0) #define __STDIO_STREAM_BUFFER_GET(S) (EOF) -#define __STDIO_FILL_READ_BUFFER(S) (0) -#define __STDIO_STREAM_INIT_BUFREAD_BUFPOS(S) ((void)0) +#define __STDIO_FILL_READ_BUFFER(S) (0) +#define __STDIO_STREAM_INIT_BUFREAD_BUFPOS(S) ((void)0) #undef __STDIO_STREAM_FAKE_VSNPRINTF_FILEDES #undef __STDIO_STREAM_FAKE_VSSCANF_FILEDES @@ -386,14 +367,14 @@ extern int __stdio_trans2w_o(FILE *__restrict stream, int oflag) attribute_hidde #undef __STDIO_STREAM_IS_FAKE_VSWPRINTF # ifdef __USE_OLD_VFPRINTF__ -# define __STDIO_STREAM_FAKE_VSNPRINTF_FILEDES_NB (-2) -# define __STDIO_STREAM_IS_FAKE_VSNPRINTF_NB(S) \ +# define __STDIO_STREAM_FAKE_VSNPRINTF_FILEDES_NB (-2) +# define __STDIO_STREAM_IS_FAKE_VSNPRINTF_NB(S) \ ((S)->__filedes == __STDIO_STREAM_FAKE_VSNPRINTF_FILEDES_NB) # endif # ifndef __UCLIBC_HAS_WCHAR__ -# define __STDIO_STREAM_FAKE_VSSCANF_FILEDES_NB (-2) -# define __STDIO_STREAM_IS_FAKE_VSSCANF_NB(S) \ +# define __STDIO_STREAM_FAKE_VSSCANF_FILEDES_NB (-2) +# define __STDIO_STREAM_IS_FAKE_VSSCANF_NB(S) \ ((S)->__filedes == __STDIO_STREAM_FAKE_VSSCANF_FILEDES_NB) # endif @@ -404,7 +385,8 @@ extern int __stdio_adjust_position(FILE *__restrict stream, __offmax_t *pos) att #ifdef __STDIO_HAS_OPENLIST /* Uses an implementation hack!!! */ -#define __STDIO_FLUSH_LBF_STREAMS fflush_unlocked((FILE *) &_stdio_openlist) +#define __STDIO_FLUSH_LBF_STREAMS \ + fflush_unlocked((FILE *) &_stdio_openlist) #else #define __STDIO_FLUSH_LBF_STREAMS ((void)0) #endif @@ -427,13 +409,12 @@ extern void _stdio_validate_FILE(const FILE *stream); /**********************************************************************/ -extern FILE *_stdio_fopen(intptr_t fname_or_mode, - const char *__restrict mode, - FILE *__restrict stream, int filedes) attribute_hidden; +extern FILE *_stdio_fopen(intptr_t fname_or_mode, const char *__restrict mode, + FILE *__restrict stream, int filedes) attribute_hidden; #ifdef __UCLIBC_HAS_WCHAR__ -extern size_t _wstdio_fwrite(const wchar_t *__restrict ws, size_t n, - FILE *__restrict stream) attribute_hidden; +extern size_t _wstdio_fwrite(const wchar_t *__restrict ws, + size_t n, FILE *__restrict stream) attribute_hidden; #endif /**********************************************************************/ diff --git a/libc/stdio/fflush.c b/libc/stdio/fflush.c index 84e2a26cc..e1527b3a3 100644 --- a/libc/stdio/fflush.c +++ b/libc/stdio/fflush.c @@ -15,31 +15,16 @@ libc_hidden_proto(fflush_unlocked) #warning WISHLIST: Add option to test for undefined behavior of fflush. #endif /* __UCLIBC_MJN3_ONLY__ */ -#ifdef __UCLIBC_HAS_THREADS__ /* Even if the stream is set to user-locking, we still need to lock * when all (lbf) writing streams are flushed. */ -#define __MY_STDIO_THREADLOCK(__stream) \ - do { \ - struct _pthread_cleanup_buffer __infunc_pthread_cleanup_buffer; \ - if (_stdio_user_locking != 2) { \ - _pthread_cleanup_push_defer(&__infunc_pthread_cleanup_buffer, \ - __pthread_mutex_unlock, \ - &(__stream)->__lock); \ - __pthread_mutex_lock(&(__stream)->__lock); \ - } \ - ((void)0) - -#define __MY_STDIO_THREADUNLOCK(__stream) \ - if (_stdio_user_locking != 2) { \ - _pthread_cleanup_pop_restore(&__infunc_pthread_cleanup_buffer,1);\ - } \ - } while (0) - -#else -#define __MY_STDIO_THREADLOCK(STREAM) ((void)0) -#define __MY_STDIO_THREADUNLOCK(STREAM) ((void)0) -#endif +#define __MY_STDIO_THREADLOCK(__stream) \ + __UCLIBC_MUTEX_CONDITIONAL_LOCK((__stream)->__lock, \ + (_stdio_user_locking != 2)) + +#define __MY_STDIO_THREADUNLOCK(__stream) \ + __UCLIBC_MUTEX_CONDITIONAL_UNLOCK((__stream)->__lock, \ + (_stdio_user_locking != 2)) #if defined(__UCLIBC_HAS_THREADS__) && defined(__STDIO_BUFFERS) void _stdio_openlist_dec_use(void) diff --git a/libc/sysdeps/linux/common/bits/uClibc_stdio.h b/libc/sysdeps/linux/common/bits/uClibc_stdio.h index 5865ce564..7efaed31f 100644 --- a/libc/sysdeps/linux/common/bits/uClibc_stdio.h +++ b/libc/sysdeps/linux/common/bits/uClibc_stdio.h @@ -322,6 +322,7 @@ struct __STDIO_FILE_STRUCT { #define __FLAG_FREEFILE 0x2000U #define __FLAG_FREEBUF 0x4000U #define __FLAG_LARGEFILE 0x8000U /* fixed! == 0_LARGEFILE for linux */ +#define __FLAG_FAILED_FREOPEN __FLAG_LARGEFILE /* Note: In no-buffer mode, it would be possible to pack the necessary * flags into one byte. Since we wouldn't be buffering and there would |