aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorH. Peter Anvin <hpa@linux.intel.com>2014-04-09 16:51:10 -0700
committerH. Peter Anvin <hpa@linux.intel.com>2014-04-09 16:51:10 -0700
commita51893a6d52a8cdf247cb1bd10dd8987d4d7eb49 (patch)
tree40236fab3b43770c581b5cc849724536e091e31a
parente845d9b10c5699ef5f2f41a117f2211508f3d6bf (diff)
downloadklibc-a51893a6d52a8cdf247cb1bd10dd8987d4d7eb49.tar.gz
[klibc] fwrite: use memrchr() to find the final '\n' in _IOLBF mode
In line buffered mode, we need to split the write at the final '\n' (which usually, but not always, is the last character in the string.) Use memrchr() instead of open-coding it. Signed-off-by: H. Peter Anvin <hpa@linux.intel.com>
-rw-r--r--usr/klibc/stdio/fwrite.c13
1 files changed, 4 insertions, 9 deletions
diff --git a/usr/klibc/stdio/fwrite.c b/usr/klibc/stdio/fwrite.c
index 5d2c3f01343eb..71ee75cc95892 100644
--- a/usr/klibc/stdio/fwrite.c
+++ b/usr/klibc/stdio/fwrite.c
@@ -59,6 +59,7 @@ size_t _fwrite(const void *buf, size_t count, FILE *file)
size_t bytes = 0;
size_t pf_len, pu_len;
const char *p = buf;
+ const char *q;
/* We divide the data into two chunks, flushed (pf)
and unflushed (pu) depending on buffering mode
@@ -67,23 +68,16 @@ size_t _fwrite(const void *buf, size_t count, FILE *file)
switch (f->bufmode) {
case _IOFBF:
pf_len = 0;
- pu_len = count;
break;
case _IOLBF:
- pf_len = count;
- pu_len = 0;
-
- while (pf_len && p[pf_len-1] != '\n') {
- pf_len--;
- pu_len++;
- }
+ q = memrchr(p, '\n', count);
+ pf_len = q ? q - p + 1 : 0;
break;
case _IONBF:
default:
pf_len = count;
- pu_len = 0;
break;
}
@@ -94,6 +88,7 @@ size_t _fwrite(const void *buf, size_t count, FILE *file)
return bytes;
}
+ pu_len = count - pf_len;
if (pu_len)
bytes += fwrite_noflush(p, pu_len, f);