Fix freopen handling of ,ccs= (bug 23675)

As reported in bug 23675 and shown up in the recently added tests of
different cases of freopen (relevant part of the test currently
conditioned under #if 0 to avoid a failure resulting from this bug),
freopen wrongly forces the stream to unoriented even when a mode with
,ccs= is specified, though such a mode is supposed to result in a
wide-oriented stream.  Move the clearing of _mode to before the actual
reopening occurs, so that the main fopen implementation can leave a
wide-oriented stream in the ,ccs= case.

Tested for x86_64.
This commit is contained in:
Joseph Myers 2024-09-05 20:08:10 +00:00
parent cc3e743fc0
commit e44ca1c085
3 changed files with 3 additions and 11 deletions

View File

@ -66,6 +66,7 @@ freopen (const char *filename, const char *mode, FILE *fp)
fp->_flags2 &= ~(_IO_FLAGS2_MMAP fp->_flags2 &= ~(_IO_FLAGS2_MMAP
| _IO_FLAGS2_NOTCANCEL | _IO_FLAGS2_NOTCANCEL
| _IO_FLAGS2_CLOEXEC); | _IO_FLAGS2_CLOEXEC);
fp->_mode = 0;
result = _IO_old_file_fopen (fp, gfilename, mode); result = _IO_old_file_fopen (fp, gfilename, mode);
} }
else else
@ -78,6 +79,7 @@ freopen (const char *filename, const char *mode, FILE *fp)
fp->_flags2 &= ~(_IO_FLAGS2_MMAP fp->_flags2 &= ~(_IO_FLAGS2_MMAP
| _IO_FLAGS2_NOTCANCEL | _IO_FLAGS2_NOTCANCEL
| _IO_FLAGS2_CLOEXEC); | _IO_FLAGS2_CLOEXEC);
fp->_mode = 0;
result = _IO_file_fopen (fp, gfilename, mode, 1); result = _IO_file_fopen (fp, gfilename, mode, 1);
if (result != NULL) if (result != NULL)
result = __fopen_maybe_mmap (result); result = __fopen_maybe_mmap (result);
@ -85,9 +87,6 @@ freopen (const char *filename, const char *mode, FILE *fp)
fp->_flags2 &= ~_IO_FLAGS2_NOCLOSE; fp->_flags2 &= ~_IO_FLAGS2_NOCLOSE;
if (result != NULL) if (result != NULL)
{ {
/* unbound stream orientation */
result->_mode = 0;
if (fd != -1 && _IO_fileno (result) != fd) if (fd != -1 && _IO_fileno (result) != fd)
{ {
/* At this point we have both file descriptors already allocated, /* At this point we have both file descriptors already allocated,

View File

@ -59,15 +59,13 @@ freopen64 (const char *filename, const char *mode, FILE *fp)
fp->_flags2 &= ~(_IO_FLAGS2_MMAP fp->_flags2 &= ~(_IO_FLAGS2_MMAP
| _IO_FLAGS2_NOTCANCEL | _IO_FLAGS2_NOTCANCEL
| _IO_FLAGS2_CLOEXEC); | _IO_FLAGS2_CLOEXEC);
fp->_mode = 0;
result = _IO_file_fopen (fp, gfilename, mode, 0); result = _IO_file_fopen (fp, gfilename, mode, 0);
fp->_flags2 &= ~_IO_FLAGS2_NOCLOSE; fp->_flags2 &= ~_IO_FLAGS2_NOCLOSE;
if (result != NULL) if (result != NULL)
result = __fopen_maybe_mmap (result); result = __fopen_maybe_mmap (result);
if (result != NULL) if (result != NULL)
{ {
/* unbound stream orientation */
result->_mode = 0;
if (fd != -1 && _IO_fileno (result) != fd) if (fd != -1 && _IO_fileno (result) != fd)
{ {
/* At this point we have both file descriptors already allocated, /* At this point we have both file descriptors already allocated,

View File

@ -386,13 +386,8 @@ do_test (void)
fp = xfopen (file2, "w,ccs=iso-8859-1"); fp = xfopen (file2, "w,ccs=iso-8859-1");
ret = fputws (L"\xc0\xc1", fp); ret = fputws (L"\xc0\xc1", fp);
TEST_VERIFY (ret >= 0); TEST_VERIFY (ret >= 0);
#if 0 /* Doesn't work (bug 23675). */
fp = FREOPEN (file1, "r,ccs=utf-8", fp); fp = FREOPEN (file1, "r,ccs=utf-8", fp);
TEST_VERIFY_EXIT (fp != NULL); TEST_VERIFY_EXIT (fp != NULL);
#else /* Works instead. */
xfclose (fp);
fp = xfopen (file1, "r,ccs=utf-8");
#endif
wc = fgetwc (fp); wc = fgetwc (fp);
TEST_COMPARE (wc, (wint_t) 0xc0); TEST_COMPARE (wc, (wint_t) 0xc0);
wc = fgetwc (fp); wc = fgetwc (fp);