-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1 According to Paul Eggert on 5/30/2007 4:46 PM: > Eric Blake <[EMAIL PROTECTED]> writes: > >> I'm wondering how many of the other coreutils that use this freopen trick >> are >> affected, > > Five more: head, tac, tail, tee, and tr.
The full list: cat, cksum, head, md5sum (and thus sha*sum), tac, tail, tee, tr > >> and whether we should use a wrapper function rather than duplicating >> all the logic. > > My kneejerk reaction is to duplicate the logic. > > Most likely we'll run into further problems like this, no? E.g., > suppose stdout is open for both read and write, and we use "wb" on it? > Won't we screw it up? Nope. Cygwin's freopen is smart enough to allow any subset of permissions in the mode argument which are compatible with the underlying permissions of the fd. POSIX states that stdout is only open for writing on program startup, even if the fd is open O_RDWR, so coreutils' existing use of "wb" is correct modulo append flag. But even if you do freopen("file","w+",stdout), a later freopen(NULL,"wb",stdout) is not a problem. However, it is a bummer that POSIX states that freopen(NULL) is implementation defined, so I can only guarantee cygwin's behavior. I'm wondering if we could just add something like this to the binary-io module, which we can then update as needed to compensate for any other irregularities discovered in swapping stdio to binary mode: /* Make sure FP is in binary mode. Return FP on success, NULL on failure. */ FILE * fsetbinary (FILE *fp) { #ifdef __CYGWIN__ int mode = fcntl (fileno (fp), F_GETFL); char *str; switch (mode & (O_ACCMODE | O_APPEND)) { case O_RDONLY: str = "rb"; break; case O_WRONLY: str = "wb"; break; case O_RDWR: str = "r+b"; break; case O_WRONLY | O_APPEND: str = "ab"; break; case O_RDWR | O_APPEND: str = "a+b"; break; default: str = NULL; } if (!str) { fclose (fp); errno = EBADF; return NULL; } # ifdef simple return freopen (NULL, str, fp); # else fp = freopen (NULL, str, fp); if (fp) { fcntl (fileno (fp), F_SETFL, mode); } return result; # endif #else /* I'm not sure how mingw behaves with freopen(NULL,...). */ SET_BINARY (fileno (fp)); return fp; #endif } - -- Don't work too hard, make some time for fun as well! Eric Blake [EMAIL PROTECTED] -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.5 (Cygwin) Comment: Public key at home.comcast.net/~ericblake/eblake.gpg Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org iD8DBQFGXhZn84KuGfSFAYARAuh8AJ9t5fgfL3wSIivp+4SIHzxna59a8gCgxO1D acSJCXRmeDRJCaxoFyTly1Q= =z78R -----END PGP SIGNATURE----- _______________________________________________ Bug-coreutils mailing list Bug-coreutils@gnu.org http://lists.gnu.org/mailman/listinfo/bug-coreutils