[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: understanding the T command
From: |
Assaf Gordon |
Subject: |
Re: understanding the T command |
Date: |
Fri, 15 May 2020 07:38:17 -0600 |
User-agent: |
Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101 Thunderbird/68.8.0 |
Hello,
On 2020-05-15 5:13 a.m., Nora Platiel wrote:
I'm confused about conditional branching, especially the T command. Consider
this script:
s/x/X/; #1
T ; #2
s/y/Y/; #3
T ; #4
s/^/Z/; #5
Input line "x" produces output line "X", why not "ZX"?
This is what I would expect to happen for line "x":
- replacement #1 is successful
- conditional branch #2 is not taken
- replacement #3 is not successful
- conditional branch #4 is not taken
- replacement #5 is successful
Conditional branch #4 should not be taken because replacement #1 succeeded, and
no line is read nor conditional branch taken between #1 and #4.
I hope someone here can clarify.
Thanks.
From the docs:
T label: (test) Branch to label only if there have been no successful
substitutions since the last input line was read or conditional branch was
taken. The label may be omitted, in which case the next cycle is started.
Thank you for providing a clear way to reproduce the issue - makes it so
much easier to answer.
Since the "T" command is a gnu extension,
it's not immediately clear to me if the code is right and the
documentation should be fixed, or the documentation is right and the
code should be fixed...
What is clear: sed behaves in the way you observed
because the code for 'T' resets the "replaced" flag
if the branch is *not* taken (line 1564):
https://git.savannah.gnu.org/cgit/sed.git/tree/sed/execute.c#n1548
To illustrate, see:
$ echo x | sed 's/x/X/ ; T ; aHELLO'
X
HELLO
$ echo x | sed 's/x/X/ ; T ; T ; aHELLO'
X
In the second example, the first "T" is not taken, but it resets
the state of the "replaced" flag, and then the second "T" is taken (and
HELLO is not printed).
---
Removing this line (execute.c:1564) makes sed behave in the way
you expected, and does not cause any test failures - indicating
this is quite an obscure scenario that wasn't officially tested.
But since this behavior has been in place since at least
sed 4.06 (from 2003), it might not be wise to change it
in backward-incompatible way.
I welcome others to chime in about this.
regards,
- assaf