Hi/2. Bruno Haible wrote: >> +#ifdef __KLIBC__ >> + FILE *result = freopen (filename, mode, stream); >> + >> + /* On OS/2 kLIBC, freopen() returns NULL even if it is successful >> + if filename is NULL. */ >> + if (!result && !errno) >> + result = stream; > > 1) In the comment you say 'if filename is NULL' but in the code you use > the (hacky) workaround code also if filename != NULL. Why? >
If filename != NULL, it is not possible that result is NULL and errno is 0. Anyway fixed. > 2) When freopen returns NULL for success, does it set errno = 0, or does > it leave errno untouched? Can you find out, please, by using a test program > like > > errno = 42; > FILE *result = freopen (NULL, mode, stream); > printf ("errno = %d\n", errno); > > If it's the latter case (it leaves errno untouched), you need to add an > 'errno = 0;' statement before the freopen call. > I thought testing this. But it was wrong. Thanks for pointing this. Fixed. -- KO Myung-Hun Using Mozilla SeaMonkey 2.7.2 Under OS/2 Warp 4 for Korean with FixPak #15 In VirtualBox v4.1.32 on Intel Core i7-3615QM 2.30GHz with 8GB RAM Korean OS/2 User Community : http://www.ecomstation.co.kr
>From e6db5cbcc2edcc514aef10eaf63d108d1448f5df Mon Sep 17 00:00:00 2001 From: KO Myung-Hun <k...@chollian.net> Date: Wed, 3 Sep 2014 20:47:02 +0900 Subject: [PATCH] freopen: workaround freopen() on OS/2 kLIBC On OS/2 kLIBC, freopen() returns NULL even if it is successful if filename is NULL. * lib/freopen-safer.c (klibc_freopen): New. * lib/freopen.c (orig_freopen): Workaround. --- lib/freopen-safer.c | 24 ++++++++++++++++++++++++ lib/freopen.c | 16 +++++++++++++++- 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/lib/freopen-safer.c b/lib/freopen-safer.c index 714dc1d..b889123 100644 --- a/lib/freopen-safer.c +++ b/lib/freopen-safer.c @@ -44,6 +44,30 @@ protect_fd (int fd) return true; } +#ifdef __KLIBC__ +/* Workaround for freopen() on OS/2 kLIBC */ +static FILE * +klibc_freopen (const char *filename, const char *mode, FILE *stream) +{ + FILE *result; + + /* Clear errno to check the success of freopen() with it */ + errno = 0; + + result = freopen (filename, mode, stream); + + /* On OS/2 kLIBC, freopen() returns NULL even if it is successful + if filename is NULL. */ + if (!filename && !result && !errno) + result = stream; + + return result; +} + +# undef freopen +# define freopen klibc_freopen +#endif + /* Like freopen, but guarantee that reopening stdin, stdout, or stderr preserves the invariant that STDxxx_FILENO==fileno(stdxxx), and that no other stream will interfere with the standard streams. diff --git a/lib/freopen.c b/lib/freopen.c index 384eba6..4669773 100644 --- a/lib/freopen.c +++ b/lib/freopen.c @@ -29,7 +29,21 @@ static FILE * orig_freopen (const char *filename, const char *mode, FILE *stream) { - return freopen (filename, mode, stream); + FILE *result; + + /* Clear errno to check the success of freopen() with it */ + errno = 0; + + result = freopen (filename, mode, stream); + +#ifdef __KLIBC__ + /* On OS/2 kLIBC, freopen() returns NULL even if it is successful + if filename is NULL. */ + if (!filename && !result && !errno) + result = stream; +#endif + + return result; } /* Specification. */ -- 1.8.5.2