Skip site navigation (1)Skip section navigation (2)
Date:      Sat, 27 Aug 2016 10:34:01 +0000 (UTC)
From:      "Andrey A. Chernov" <ache@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org
Subject:   svn commit: r304893 - stable/10/lib/libc/stdio
Message-ID:  <201608271034.u7RAY1X1097431@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: ache
Date: Sat Aug 27 10:34:01 2016
New Revision: 304893
URL: https://svnweb.freebsd.org/changeset/base/304893

Log:
  MFC r304607,r304641,r304819,r304811
  
  1) Don't forget to set __SERR on __slbexpand() error.
  
  2) Remove "Fast path" from fgetwc()/fputwc() since it can't detect
  encoding errors and ignores them all.
  One of affected encoding example: US-ASCII
  
  3)  Original fgetln() from 44lite return success for line tail errors,
  i.e. partial line, but set __SERR and errno in the same time, which
  is inconsistent.
  Now both OpenBSD and NetBSD return failure, i.e. no line and set error
  indicators for such case, so make our fgetln() and fgetwln()
  (as its wide version) compatible with the rest of *BSD.
  
  PR:     212033

Modified:
  stable/10/lib/libc/stdio/fgetln.c
  stable/10/lib/libc/stdio/fgetwc.c
  stable/10/lib/libc/stdio/fgetwln.c
  stable/10/lib/libc/stdio/fputwc.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/lib/libc/stdio/fgetln.c
==============================================================================
--- stable/10/lib/libc/stdio/fgetln.c	Sat Aug 27 10:30:20 2016	(r304892)
+++ stable/10/lib/libc/stdio/fgetln.c	Sat Aug 27 10:34:01 2016	(r304893)
@@ -139,8 +139,11 @@ fgetln(FILE *fp, size_t *lenp)
 		(void)memcpy((void *)(fp->_lb._base + off), (void *)fp->_p,
 		    len - off);
 		off = len;
-		if (__srefill(fp))
-			break;	/* EOF or error: return partial line */
+		if (__srefill(fp)) {
+			if (__sfeof(fp))
+				break;
+			goto error;
+		}
 		if ((p = memchr((void *)fp->_p, '\n', (size_t)fp->_r)) == NULL)
 			continue;
 

Modified: stable/10/lib/libc/stdio/fgetwc.c
==============================================================================
--- stable/10/lib/libc/stdio/fgetwc.c	Sat Aug 27 10:30:20 2016	(r304892)
+++ stable/10/lib/libc/stdio/fgetwc.c	Sat Aug 27 10:34:01 2016	(r304893)
@@ -79,18 +79,9 @@ __fgetwc_mbs(FILE *fp, mbstate_t *mbs, i
 	size_t nconv;
 	struct xlocale_ctype *l = XLOCALE_CTYPE(locale);
 
-	if (fp->_r <= 0 && __srefill(fp)) {
-		*nread = 0;
-		return (WEOF);
-	}
-	if (MB_CUR_MAX == 1) {
-		/* Fast path for single-byte encodings. */
-		wc = *fp->_p++;
-		fp->_r--;
-		*nread = 1;
-		return (wc);
-	}
 	*nread = 0;
+	if (fp->_r <= 0 && __srefill(fp))
+		return (WEOF);
 	do {
 		nconv = l->__mbrtowc(&wc, fp->_p, fp->_r, mbs);
 		if (nconv == (size_t)-1)

Modified: stable/10/lib/libc/stdio/fgetwln.c
==============================================================================
--- stable/10/lib/libc/stdio/fgetwln.c	Sat Aug 27 10:30:20 2016	(r304892)
+++ stable/10/lib/libc/stdio/fgetwln.c	Sat Aug 27 10:34:01 2016	(r304893)
@@ -56,13 +56,15 @@ fgetwln_l(FILE * __restrict fp, size_t *
 	while ((wc = __fgetwc(fp, locale)) != WEOF) {
 #define	GROW	512
 		if (len * sizeof(wchar_t) >= fp->_lb._size &&
-		    __slbexpand(fp, (len + GROW) * sizeof(wchar_t)))
+		    __slbexpand(fp, (len + GROW) * sizeof(wchar_t))) {
+			fp->_flags |= __SERR;
 			goto error;
+		}
 		*((wchar_t *)fp->_lb._base + len++) = wc;
 		if (wc == L'\n')
 			break;
 	}
-	if (len == 0)
+	if (len == 0 || (wc == WEOF && !__sfeof(fp)))
 		goto error;
 
 	FUNLOCKFILE(fp);
@@ -74,6 +76,7 @@ error:
 	*lenp = 0;
 	return (NULL);
 }
+
 wchar_t *
 fgetwln(FILE * __restrict fp, size_t *lenp)
 {

Modified: stable/10/lib/libc/stdio/fputwc.c
==============================================================================
--- stable/10/lib/libc/stdio/fputwc.c	Sat Aug 27 10:30:20 2016	(r304892)
+++ stable/10/lib/libc/stdio/fputwc.c	Sat Aug 27 10:34:01 2016	(r304893)
@@ -53,19 +53,9 @@ __fputwc(wchar_t wc, FILE *fp, locale_t 
 	size_t i, len;
 	struct xlocale_ctype *l = XLOCALE_CTYPE(locale);
 
-	if (MB_CUR_MAX == 1 && wc > 0 && wc <= UCHAR_MAX) {
-		/*
-		 * Assume single-byte locale with no special encoding.
-		 * A more careful test would be to check
-		 * _CurrentRuneLocale->encoding.
-		 */
-		*buf = (unsigned char)wc;
-		len = 1;
-	} else {
-		if ((len = l->__wcrtomb(buf, wc, &fp->_mbstate)) == (size_t)-1) {
-			fp->_flags |= __SERR;
-			return (WEOF);
-		}
+	if ((len = l->__wcrtomb(buf, wc, &fp->_mbstate)) == (size_t)-1) {
+		fp->_flags |= __SERR;
+		return (WEOF);
 	}
 
 	for (i = 0; i < len; i++)



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201608271034.u7RAY1X1097431>