7 ms·
Bug: true and false are not Posix (2016)
- jiveturkey 8y ago2016
- kgwxd 8y agoOT but, I've always thought the true and false summaries would make great t-shirts and inspirational posters. "do nothing, successfully" sounds zen, and "do nothing, unsuccessfully" sounds like a sportswear slogan.
- anyfoo 8y agoThe authors of the utilities seem to make a pretty good case on how GNU’s ‘true’ and ‘false’ are POSIX compliant, because their extensions to them are covered where POSIX leaves the behavior as undefined, and in fact it seems to be the invocation of ‘true’ with any arguments itself that is not in accordance to POSIX. Whether it’s “not common sense” is not very apparent when “common sense” is pretty difficult to define here (as often the case).
- jancsika 8y ago> The authors of the utilities seem to make a pretty good case on how GNU’s ‘true’ and ‘false’ are POSIX compliant, because their extensions to them are covered where POSIX leaves the behavior as undefined, and in fact it seems to be the invocation of ‘true’ with any arguments itself that is not in accordance to POSIX. Ok, so undefined behavior is seen an escape valve through which the devs can change longstanding behavior in the interest of consistency with a newer set of interface standards they've devised. Fine. But then this response from a dev on that mailinglist[1]: > Note that it is a high bar to change the behavior of something like 'true'. Hm... now I'm slightly intrigued. Did the change that introduced the standard "--help" flag and addition of locale-related code flow directly from the "escape valve" of undefined behavior in POSIX? Or was the undefined behavior merely a starting point for a much more involved discussion about whether to change a long-standing interface that could introduce subtle bugs in old scripts/programs that relied on implementation details of undefined behavior? Edit: clarification. Also if someone can point me to a mailing list discussion that shows evidence of the latter I would be much obliged. [1] https://lists.gnu.org/archive/html/bug-coreutils/2016-03/msg00050.html https://lists.gnu.org/archive/html/bug-coreutils/2016-03/msg...
- gizmo686 8y agoThe behavior of --help in GNU's true is not undefined, it is clearly defined in its manpage. Implemenations conforming to the GNU spec are a strict subset of those conforming to the POSIX spec. Changing thr behaviour is a braking change because they are no longer conforming to their old spec. Adding the flag is not a breaking change, as they stayed consistent with the old spec
- pdw 8y agoYou're talking as if this were a recent change. GNU true --help has existed for about 28 years now (it was introduced in sh-utils 1.7). That's more than half of Unix's existence.
- burfog 8y agoYes, this is a very very old bug. I doubt anything depends on that bug.
- JdeBP 8y agoThat was only 3 and a bit years after the publication of POSIX 1003.1:1988 itself.
- jancsika 8y agoI don't see the relevance, but maybe I'm confused about the development history of this command. Was there a time when GNU existed without the "--help" flag? Or was it originally committed with the "--help" flag present?
- anyfoo 8y agoCareful: If you go by "longstanding behavior" instead of standards, you quickly get to the point where you have to ask yourself the question which longstanding behavior you want to honor for "consistency". This may not universally be true, but in the case of the shell(s) and everything that surrounds it, I'm pretty sure it is. Shells are pretty much the wild west out there. I wouldn't be too surprised if some AIX shell variant or something came along and consistently bails out with an error when any argument is given to 'true', including --version. It might not be a common shell variant for you, but it might for other people. Hence, standards. I'm not really arguing in favor of --help and --version to 'true'. I just don't see much of a problem with it.
- temac 8y agotrue once was, and IMO should be again, implemented as a 0 bytes executable. Since then, it has infinitely bloated on most systems. It actually began at AT&T, where they apparently decided to copyright the trueness. From there it went downhill, ever and ever. http://trillian.mit.edu/~jc/humor/ATT_Copyright_true.html http://trillian.mit.edu/~jc/humor/ATT_Copyright_true.html
- gizmo686 8y agoDoesn't the 0 byte executable involve spawning a shell to run it? Better would be a tiny elf executable that just returns 0 (maybe hand written to avoid the compiler adding bloat)
- pcwalton 8y agoCorrect. true being a 0 byte shell script is a good example of classic Unix's bad habit of doing the overly-cute thing instead of the sensible thing.
- temac 8y agoIt would be a valid approach but it is less elegant and harder to maintain. Probably the kernel could special case 0 bytes executables, if you really want to optimize the scripted truth.
- gizmo686 8y agoIf you want maintainable, you should just compile "return 0" with your standard toolchain. A 0 byte file risks confusing developers who might see it and think their install is corrupted (surely the program just got truncated). If you want to use an empty program, the maintainable solution would be to comment it; but then it is not empty.
- anyfoo 8y agoSpecial casing 0-byte executables is not necessarily the best solution, either. It's a special case after all, and one that's essentially only there to support /bin/true. This may create security gotchas or inadvertent bugs resulting from the "codeless" address space that gets created (or not created if you implement it that way, with its own set of potential gotchas). I'm not saying it necessarily does create problems, but it can.
- kps 8y agoThe first and best /bin/true was an empty file — possibly the only bug-free program ever written. The worst may be the System V version, which added a copyright notice.
- m45t3r 8y agoThat is, considering that your shell interpreter is bug free.
- Wowfunhappy 8y ago> possibly the only bug-free program ever written. Oh come now. I'm quite sure my hello world program is bug free. It prints "Hello World" successfully, and there are zero other cases that could exist.
- AlotOfReading 8y agoYou're obviously joking, but for those who aren't aware, even a naive "hello world" can have bugs. https://www.gnu.org/ghm/2011/paris/slides/jim-meyering-goodbye-world.pdf https://www.gnu.org/ghm/2011/paris/slides/jim-meyering-goodb...
- deleted 8y ago[deleted]
- Wowfunhappy 8y agoI actually wasn't joking, but that link made me rethink, so thanks for that!
- geofft 8y agoThis is a textbook example of a bikeshed: http://bikeshed.com http://bikeshed.com Nobody is calling true or false in a script with options/arguments. Nobody hss ever seen true/false fail because they crashed in setlocale. Nobody's highest, second-highest, or 1000th-highest risk to their code is the performance of their true/false implementation. But it's a really easy thing to have opinions about. You use UNIX for one week and suddenly you're exactly as qualified as Dennis Ritchie to have opinions on the matter.
- rrauenza 8y agoI've seen... (ok, actually I recommended)... someone do the following: if [ -x /usr/bin/blah ] then BLAH=/usr/bin/blah else BLAH=/bin/true fi $BLAH foo bar baz They wanted BLAH to be a noop if blah didn't exist. I could only think of /bin/true as a noop at the time, but I needed it to ignore parameters. The man page defines that it does. (in retrospect, we could have defined an sh function noop {} )
- geofft 8y agoYeah, options include a noop function (which is nice because you can change it to noop () { echo "Skipping $@" >&2 ; }) or the shell builtin :, which definitely ignores its arguments.
- JdeBP 8y agoI was going to mention that it came up just days ago on Unix and Linux StackExchange. (-: * https://unix.stackexchange.com/a/497561/5132 https://unix.stackexchange.com/a/497561/5132 The conditionally defined shell function in one of the other answers is a more appealing approach, especially given the native behaviours of some shells with respect to variable expansion. But also given that /bin/true is not necessarily the pathname. % export BLAH='/bin/true too' % dash -c '$BLAH 1 2 3' % dash: 1: /bin/true: not found % sh -c '$BLAH 1 2 3' /bin/true: not found % ksh -c '$BLAH 1 2 3' ksh: /bin/true: not found % zsh -c '$BLAH 1 2 3' zsh:1: no such file or directory: /bin/true too % bash -c '$BLAH 1 2 3' bash: /bin/true: No such file or directory % % export BLAH='/usr/bin/true too' % zsh -c '$BLAH 1 2 3' zsh:1: no such file or directory: /usr/bin/true too % bash -c '$BLAH 1 2 3' % ksh -c '$BLAH 1 2 3' % dash -c '$BLAH 1 2 3' %
- kazinator 8y ago2017 POSIX, Section 2.1.1, paragraph 4: "The system may provide non-standard extensions. These are features not required by POSIX.1-2017 and may include, but are not limited to: Additional functions [ ... ] Additional options for standard utilities" [ ... ]" http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap02.html#tag_02_01_01 http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_... A standard utility that takes no options can be extended locally to take options. "Some options" constitutes "additional options" relative to "no options". Since the descriptions of true and false say they take no options; therefore POSIX-conforming scripts don't pass any. A POSIX-conforming script has no way of finding out whether true or false take implementation-defined options (i.e. any options whatsoever).