Re: q and escaping paired delimiters
Kenneth Albanowski [Sun, 27 Jul 1997 06:49:26 +0000 (18:49 +1200)]
On Sun, 27 Jul 1997 chrisn@rock.petersons.com wrote:

> $\ = "\n";
> print '\'this\'';
> print q{'this'};
> print q{{this}};
> print q{\{this\}};
>
> I would expect the output to be:
>
> 'this'
> 'this'
> {this}
> {this}

That this should be fixed makes perfect sense to me. You can view easily
view backwhacking both sides as a generalization of backwhacking the quote
for an unbalanced q''.

In fact, the code in toke.c looks a little suspicious, as if a cut'n'paste
error happened, and the balanced branch didn't get the cleanup it
deserved. There's a "if term != '\\'" statement that does nothing, for
example.

Here'a patch over 5.004_01 (although I'd expect it to work with most
versions) to allow you to escape both the starting and end quotes for q
(unbalanced and qq is unchanged), and the obligatory addition to the
tests. If nobody has any complaints, I expect this will be in _02.

Credited: Gurusamy Sarathy <gsar@engin.umich.edu>

p5p-msgid: Pine.LNX.3.93.970727172201.350K-100000@kjahds.com

t/base/lex.t
toke.c

index 7e0ca70..6d03b9e 100755 (executable)
@@ -2,7 +2,7 @@
 
 # $RCSfile: lex.t,v $$Revision: 4.1 $$Date: 92/08/07 18:27:04 $
 
-print "1..26\n";
+print "1..27\n";
 
 $x = 'x';
 
@@ -103,3 +103,5 @@ print "${foo{$bar}}" eq "BAZ" ? "ok 23\n" : "not ok 23\n";
 print "FOO:" =~ /$foo[:]/ ? "ok 24\n" : "not ok 24\n";
 print "ABC" =~ /^$ary[$A]$/ ? "ok 25\n" : "not ok 25\n";
 print "FOOZ" =~ /^$foo[$A-Z]$/ ? "ok 26\n" : "not ok 26\n";
+
+print (((q{{\{\(}} . q{{\)\}}}) eq '{{\(}{\)}}') ? "ok 27\n" : "not ok 27\n");
diff --git a/toke.c b/toke.c
index f443af7..ff3be0d 100644 (file)
--- a/toke.c
+++ b/toke.c
@@ -4953,8 +4953,8 @@ char *start;
            for (; s < bufend; s++,to++) {
                if (*s == '\n' && !rsfp)
                    curcop->cop_line++;
-               if (*s == '\\' && s+1 < bufend && term != '\\') {
-                   if (s[1] == term)
+               if (*s == '\\' && s+1 < bufend) {
+                   if ((s[1] == multi_open) || (s[1] == term))
                        s++;
                    else
                        *to++ = *s++;