1 /* Optimizing macros and inline functions for stdio functions. 2 Copyright (C) 1998-2015 Free Software Foundation, Inc. 3 This file is part of the GNU C Library. 4 5 The GNU C Library is free software; you can redistribute it and/or 6 modify it under the terms of the GNU Lesser General Public 7 License as published by the Free Software Foundation; either 8 version 2.1 of the License, or (at your option) any later version. 9 10 The GNU C Library is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public 16 License along with the GNU C Library; if not, see 17 <http://www.gnu.org/licenses/>. */ 18 19 #ifndef _STDIO_H 20 # error "Never include <bits/stdio.h> directly; use <stdio.h> instead." 21 #endif 22 23 #ifndef __extern_inline 24 # define __STDIO_INLINE inline 25 #else 26 # define __STDIO_INLINE __extern_inline 27 #endif 28 29 30 #ifdef __USE_EXTERN_INLINES 31 /* For -D_FORTIFY_SOURCE{,=2} bits/stdio2.h will define a different 32 inline. */ 33 # if !(__USE_FORTIFY_LEVEL > 0 && defined __fortify_function) 34 /* Write formatted output to stdout from argument list ARG. */ 35 __STDIO_INLINE int 36 vprintf (const char *__restrict __fmt, _G_va_list __arg) 37 { 38 return vfprintf (stdout, __fmt, __arg); 39 } 40 # endif 41 42 /* Read a character from stdin. */ 43 __STDIO_INLINE int 44 getchar (void) 45 { 46 return _IO_getc (stdin); 47 } 48 49 50 # ifdef __USE_MISC 51 /* Faster version when locking is not necessary. */ 52 __STDIO_INLINE int 53 fgetc_unlocked (FILE *__fp) 54 { 55 return _IO_getc_unlocked (__fp); 56 } 57 # endif /* misc */ 58 59 60 # ifdef __USE_POSIX 61 /* This is defined in POSIX.1:1996. */ 62 __STDIO_INLINE int 63 getc_unlocked (FILE *__fp) 64 { 65 return _IO_getc_unlocked (__fp); 66 } 67 68 /* This is defined in POSIX.1:1996. */ 69 __STDIO_INLINE int 70 getchar_unlocked (void) 71 { 72 return _IO_getc_unlocked (stdin); 73 } 74 # endif /* POSIX */ 75 76 77 /* Write a character to stdout. */ 78 __STDIO_INLINE int 79 putchar (int __c) 80 { 81 return _IO_putc (__c, stdout); 82 } 83 84 85 # ifdef __USE_MISC 86 /* Faster version when locking is not necessary. */ 87 __STDIO_INLINE int 88 fputc_unlocked (int __c, FILE *__stream) 89 { 90 return _IO_putc_unlocked (__c, __stream); 91 } 92 # endif /* misc */ 93 94 95 # ifdef __USE_POSIX 96 /* This is defined in POSIX.1:1996. */ 97 __STDIO_INLINE int 98 putc_unlocked (int __c, FILE *__stream) 99 { 100 return _IO_putc_unlocked (__c, __stream); 101 } 102 103 /* This is defined in POSIX.1:1996. */ 104 __STDIO_INLINE int 105 putchar_unlocked (int __c) 106 { 107 return _IO_putc_unlocked (__c, stdout); 108 } 109 # endif /* POSIX */ 110 111 112 # ifdef __USE_GNU 113 /* Like `getdelim', but reads up to a newline. */ 114 __STDIO_INLINE _IO_ssize_t 115 getline (char **__lineptr, size_t *__n, FILE *__stream) 116 { 117 return __getdelim (__lineptr, __n, '\n', __stream); 118 } 119 # endif /* GNU */ 120 121 122 # ifdef __USE_MISC 123 /* Faster versions when locking is not required. */ 124 __STDIO_INLINE int 125 __NTH (feof_unlocked (FILE *__stream)) 126 { 127 return _IO_feof_unlocked (__stream); 128 } 129 130 /* Faster versions when locking is not required. */ 131 __STDIO_INLINE int 132 __NTH (ferror_unlocked (FILE *__stream)) 133 { 134 return _IO_ferror_unlocked (__stream); 135 } 136 # endif /* misc */ 137 138 #endif /* Use extern inlines. */ 139 140 141 #if defined __USE_MISC && defined __GNUC__ && defined __OPTIMIZE__ \ 142 && !defined __cplusplus 143 /* Perform some simple optimizations. */ 144 # define fread_unlocked(ptr, size, n, stream) \ 145 (__extension__ ((__builtin_constant_p (size) && __builtin_constant_p (n) \ 146 && (size_t) (size) * (size_t) (n) <= 8 \ 147 && (size_t) (size) != 0) \ 148 ? ({ char *__ptr = (char *) (ptr); \ 149 FILE *__stream = (stream); \ 150 size_t __cnt; \ 151 for (__cnt = (size_t) (size) * (size_t) (n); \ 152 __cnt > 0; --__cnt) \ 153 { \ 154 int __c = _IO_getc_unlocked (__stream); \ 155 if (__c == EOF) \ 156 break; \ 157 *__ptr++ = __c; \ 158 } \ 159 ((size_t) (size) * (size_t) (n) - __cnt) \ 160 / (size_t) (size); }) \ 161 : (((__builtin_constant_p (size) && (size_t) (size) == 0) \ 162 || (__builtin_constant_p (n) && (size_t) (n) == 0)) \ 163 /* Evaluate all parameters once. */ \ 164 ? ((void) (ptr), (void) (stream), (void) (size), \ 165 (void) (n), (size_t) 0) \ 166 : fread_unlocked (ptr, size, n, stream)))) 167 168 # define fwrite_unlocked(ptr, size, n, stream) \ 169 (__extension__ ((__builtin_constant_p (size) && __builtin_constant_p (n) \ 170 && (size_t) (size) * (size_t) (n) <= 8 \ 171 && (size_t) (size) != 0) \ 172 ? ({ const char *__ptr = (const char *) (ptr); \ 173 FILE *__stream = (stream); \ 174 size_t __cnt; \ 175 for (__cnt = (size_t) (size) * (size_t) (n); \ 176 __cnt > 0; --__cnt) \ 177 if (_IO_putc_unlocked (*__ptr++, __stream) == EOF) \ 178 break; \ 179 ((size_t) (size) * (size_t) (n) - __cnt) \ 180 / (size_t) (size); }) \ 181 : (((__builtin_constant_p (size) && (size_t) (size) == 0) \ 182 || (__builtin_constant_p (n) && (size_t) (n) == 0)) \ 183 /* Evaluate all parameters once. */ \ 184 ? ((void) (ptr), (void) (stream), (void) (size), \ 185 (void) (n), (size_t) 0) \ 186 : fwrite_unlocked (ptr, size, n, stream)))) 187 #endif 188 189 /* Define helper macro. */ 190 #undef __STDIO_INLINE 191