dash.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] expand: Recognize '^' as a negation character in BE
@ 2021-07-16  9:42 Dimitar Yurukov
  2021-07-16 10:00 ` Harald van Dijk
  2021-07-16 12:50 ` [PATCH v2] " Dimitar Yurukov
  0 siblings, 2 replies; 5+ messages in thread
From: Dimitar Yurukov @ 2021-07-16  9:42 UTC (permalink / raw)
  To: dash; +Cc: Dimitar Yurukov

While parsing bracket expression ('[...]'), DASH recognizes only '!' as
a special character for negation/inversion, but POSIX specifies '^'.

The POSIX specification (2018 edition) states:

  ^ The <circumflex> shall signify a non-matching list expression when
    it occurs first in a list, immediately following a
    <left-square-bracket> (see RE Bracket Expression).

DASH:
    $ i='123 asd' && printf "%s\n" "${i##*[!a-z]}"
    asd
    $ i='123 asd' && printf "%s\n" "${i##*[^a-z]}"
    <empty expansion>

BASH (with --posix):
    $ i='123 asd' && printf "%s\n" "${i##*[!a-z]}"
    asd
    $ i='123 asd' && printf "%s\n" "${i##*[^a-z]}"
    asd

Make <circumflex> ('^') a special character used to specify
negation/inversion in bracket expressions:

    $ i='123 asd' && printf "%s\n" "${i##*[^a-z]}"
    asd

Signed-off-by: Dimitar Yurukov <mscalindt@gmail.com>
---
 src/expand.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/src/expand.c b/src/expand.c
index 1730670..06392ff 100644
--- a/src/expand.c
+++ b/src/expand.c
@@ -1565,7 +1565,7 @@ pmatch(const char *pattern, const char *string)
 
 			startp = p;
 			invert = 0;
-			if (*p == '!') {
+			if (*p == '!' || *p == '^') {
 				invert++;
 				p++;
 			}
-- 
2.32.0


^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] expand: Recognize '^' as a negation character in BE
  2021-07-16  9:42 [PATCH] expand: Recognize '^' as a negation character in BE Dimitar Yurukov
@ 2021-07-16 10:00 ` Harald van Dijk
  2021-07-16 12:46   ` Dimitar Yurukov
  2021-07-16 12:50 ` [PATCH v2] " Dimitar Yurukov
  1 sibling, 1 reply; 5+ messages in thread
From: Harald van Dijk @ 2021-07-16 10:00 UTC (permalink / raw)
  To: Dimitar Yurukov, dash

On 16/07/2021 10:42, Dimitar Yurukov wrote:
> While parsing bracket expression ('[...]'), DASH recognizes only '!' as
> a special character for negation/inversion, but POSIX specifies '^'.
> 
> The POSIX specification (2018 edition) states:
> 
>    ^ The <circumflex> shall signify a non-matching list expression when
>      it occurs first in a list, immediately following a
>      <left-square-bracket> (see RE Bracket Expression).

It also states:

   the <exclamation-mark> character ( '!' ) shall replace the 
<circumflex> character ( '^' ) in its role in a non-matching list in the 
regular expression notation

and

   A bracket expression starting with an unquoted <circumflex> character 
produces unspecified results.

See 2.13.1 Patterns Matching a Single Character.

So both the dash and the bash behaviour are permitted and this patch 
does not address a correctness issue. Scripts that rely on ^ for 
negation should be modified to use !.

The patch may still be worthwhile to increase compatibility, but in that 
case the same change also needs to be made to expmeta().

Cheers,
Harald van Dijk

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] expand: Recognize '^' as a negation character in BE
  2021-07-16 10:00 ` Harald van Dijk
@ 2021-07-16 12:46   ` Dimitar Yurukov
  0 siblings, 0 replies; 5+ messages in thread
From: Dimitar Yurukov @ 2021-07-16 12:46 UTC (permalink / raw)
  To: harald; +Cc: dash, mscalindt

On 16/07/2021 11:00, Harald van Dijk wrote:
> On 16/07/2021 10:42, Dimitar Yurukov wrote:
> > While parsing bracket expression ('[...]'), DASH recognizes only '!' as
> > a special character for negation/inversion, but POSIX specifies '^'.
> > 
> > The POSIX specification (2018 edition) states:
> > 
> >    ^ The <circumflex> shall signify a non-matching list expression when
> >      it occurs first in a list, immediately following a
> >      <left-square-bracket> (see RE Bracket Expression).
> 
> It also states:
> 
>    the <exclamation-mark> character ( '!' ) shall replace the
> <circumflex> character ( '^' ) in its role in a non-matching list in the
> regular expression notation
> 
> and
> 
>    A bracket expression starting with an unquoted <circumflex> character
> produces unspecified results.
> 
> See 2.13.1 Patterns Matching a Single Character.

Oh, my bad, sorry for the noise.

> The patch may still be worthwhile to increase compatibility, but in that
> case the same change also needs to be made to expmeta().

Oops, you are right. Will attach v2.

^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH v2] expand: Recognize '^' as a negation character in BE
  2021-07-16  9:42 [PATCH] expand: Recognize '^' as a negation character in BE Dimitar Yurukov
  2021-07-16 10:00 ` Harald van Dijk
@ 2021-07-16 12:50 ` Dimitar Yurukov
  2021-07-19  5:13   ` Herbert Xu
  1 sibling, 1 reply; 5+ messages in thread
From: Dimitar Yurukov @ 2021-07-16 12:50 UTC (permalink / raw)
  To: mscalindt; +Cc: dash, harald

While performing bracket expression ('[...]'), DASH recognizes only '!'
as a special character for negation/inversion, but POSIX specifies '^'.

The specification (2018 edition):
"
9.3.3 BRE Special Characters

^ The <circumflex> shall signify a non-matching list expression when it
  occurs first in a list, immediately following a <left-square-bracket>
  (see RE Bracket Expression).
"

DASH:
  $ i='123 asd' && printf "%s\n" "${i##*[!a-z]}"
  asd
  $ i='123 asd' && printf "%s\n" "${i##*[^a-z]}"

  $

BASH (with --posix):
  $ i='123 asd' && printf "%s\n" "${i##*[!a-z]}"
  asd
  $ i='123 asd' && printf "%s\n" "${i##*[^a-z]}"
  asd
  $

This patch makes <circumflex> ('^') a special character used to specify
negation/inversion.

Signed-off-by: Dimitar Yurukov <mscalindt@gmail.com>
---
Changes in v2:
  - Fixed the patch (patched expmeta())

 src/expand.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/src/expand.c b/src/expand.c
index 1730670..32a1b5a 100644
--- a/src/expand.c
+++ b/src/expand.c
@@ -1296,7 +1296,7 @@ expmeta(char *name, unsigned name_len, unsigned expdir_len)
 			metaflag = 1;
 		else if (*p == '[') {
 			char *q = p + 1;
-			if (*q == '!')
+			if (*q == '!' || *q == '^')
 				q++;
 			for (;;) {
 				if (*q == '\\')
@@ -1565,7 +1565,7 @@ pmatch(const char *pattern, const char *string)
 
 			startp = p;
 			invert = 0;
-			if (*p == '!') {
+			if (*p == '!' || *p == '^') {
 				invert++;
 				p++;
 			}
-- 
2.32.0


^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH v2] expand: Recognize '^' as a negation character in BE
  2021-07-16 12:50 ` [PATCH v2] " Dimitar Yurukov
@ 2021-07-19  5:13   ` Herbert Xu
  0 siblings, 0 replies; 5+ messages in thread
From: Herbert Xu @ 2021-07-19  5:13 UTC (permalink / raw)
  To: Dimitar Yurukov; +Cc: mscalindt, dash, harald

Dimitar Yurukov <mscalindt@gmail.com> wrote:
> While performing bracket expression ('[...]'), DASH recognizes only '!'
> as a special character for negation/inversion, but POSIX specifies '^'.
> 
> The specification (2018 edition):
> "
> 9.3.3 BRE Special Characters
> 
> ^ The <circumflex> shall signify a non-matching list expression when it
>  occurs first in a list, immediately following a <left-square-bracket>
>  (see RE Bracket Expression).
> "

This is incorrect and ^ cannot be used in a portable script.

Cheers,
-- 
Email: Herbert Xu <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2021-07-19  5:13 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-07-16  9:42 [PATCH] expand: Recognize '^' as a negation character in BE Dimitar Yurukov
2021-07-16 10:00 ` Harald van Dijk
2021-07-16 12:46   ` Dimitar Yurukov
2021-07-16 12:50 ` [PATCH v2] " Dimitar Yurukov
2021-07-19  5:13   ` Herbert Xu

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).