[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: $(( )): binary/unary VAR/NUM inconsistency

From: Steffen Nurpmeso
Subject: Re: $(( )): binary/unary VAR/NUM inconsistency
Date: Sat, 09 Jul 2022 18:14:31 +0200
User-agent: s-nail v14.9.24-268-g937248580b

Well i considered this one done upstream.

Martin D Kealey wrote in
 |On Sat, 9 Jul 2022, 02:08 Chet Ramey, <chet.ramey@case.edu> wrote:
 |> On 7/8/22 11:03 AM, Steffen Nurpmeso wrote:
 |>> So you seem to use your own itoa, and here is (another) bash bug.
 |>> In this hindsight bash should bail with syntax error due to 0x:
 |I would urge extreme caution in removing functionality like this. I've had

Yeah!! ..but the thing is that all libraries and programs agreed
in changing (at least to the best of my knowledge).
So except for possibly missing backports the thing is in the world
since, when it was, i think 2017 or 2018.

 |the nightmare of finding that Bash removed functionality that I relied on,
 |because a group collectively lacked the imagination to see how it might be
 |used in ways that were neither bugs nor impediments to maintenance.
 |Some might think that changing the expression parser so that a bare "0x" is
 |rejected would be harmless at worst, and helpful against writing bugs. They
 |would be wrong. Writing "0x$var" is an established if uncommon idiom that

Not for me. :)  Not for many standard developers (the called kre
even?), who push set -u.

 |currently exhibits the same "empty is zero" behaviour as we get when
 |writing "var" without a radix prefix.

You are really wrong here, and sit on non-portable code!  You
need "#!/usr/bin/env bash" for it.  (I do not know about zsh.)
Or condomize via ": ${var:=0}" maybe?

 |But my real point is that I shouldn't have to come here and make that
 |point; rather, avoiding breaking changes, even "in the name of making
 |scripts less buggy", should be the standing policy.

Oh the first part is what i must have thought by then, but "they
changed interpretation" of the ISO C standard from one day to
another, and many jumped on this train and agreed with it, so you
(i, that is) really could only follow suit.

Sigh.  Now i am looking for half an hour and cannot find the
discussion(s).  (I thought oss-security, but .. no.)  So i looked
around in the code repositories i track (mostly BSDs), and i see
for example on OpenBSD

  Commit:     millert <millert@openbsd.org>
  CommitDate: 2017-07-06 16:23:11 +0000

      The 0x (or 0X) prefix in base 16 is optional so only skip over the
      prefix if the character following it is a valid hex char.  The C99
      standard is clear that given the string "0xy" zero should be returned
      and endptr set to point to the "x".  OK deraadt@ espie@

FreeBSD was fixed in 2005 already.  NetBSD also on 2017-07-06:

  CommitDate: 2017-07-06 21:08:44 +0000

      Fix ISO C compliance: strtol of "0xX" should give the largest valid
      numeric prefix, which is 0.

DragonFly is not yet fixed.  Hm.

It also had to be quick i think; i thought a bit about it and
later added a special flags for my "integer codec":

 /*! Relaxed \a{base} 0 convenience: if the input used \c{BASE#number} number
  * sign syntax, then the scan will be restarted anew with the base given.
  * Like this an UI can be permissive and support \c{s='  -008'; eval 10#\$s}
  * out of the box (it would require a lot of logic otherwise). */

Documented as "The number sign notation uses a permissive parse
mode and as such supports complicated conditions out of the box:",
followed by the practically same example.  But not 0x.

 |PS: For those who wonder what change I'm referring to…
 |The change to "break" and "continue" so that they would refuse to act on a
 |loop outside the current function being a case in point. Apparently
 |"nobody" could see how the previous behaviour might be useful, other than
 |"to write bugs", and "everyone" thought that all possible uses must
 |necessarily be inadvertent bugs, and so the feature was removed.
 |But that change broke all my my "break_when_xxx" functions, and with them
 |my tab completion function for "ip", which of necessity comprises a fairly
 |complex stateful parser. In particular, its core is a case statement with
 |hundreds of cases and they all need the same conditional break when
 |reaching the word being expanded, so it made sense to encapsulate that in a
 |well-named function.
 |And I didn't find out until my OS updated its version of Bash several years
 |after that change to Bash itself, by which time it was way too late to
 |unwind the change to Bash and I had to rewrite large swathes of code to
 |cope with the installed base of Bash.

|Der Kragenbaer,                The moon bear,
|der holt sich munter           he cheerfully and one by one
|einen nach dem anderen runter  wa.ks himself off
|(By Robert Gernhardt)

reply via email to

[Prev in Thread] Current Thread [Next in Thread]