; perl-mode, cperl-mode: Fix $\" in strings (Bug#69604)
* lisp/progmodes/perl-mode.el (perl-syntax-propertize-function): Add to syntax-propertize-rules that $ is punctuation in strings. * lisp/progmodes/cperl-mode.el (cperl-find-pods-heres): capture $\ to catch the edge case of "$\"". Make $ a punctuation char in strings and comments. * test/lisp/progmodes/cperl-mode-tests.el (cperl-test-bug-69604): New testcases with various combinations of $ " \
This commit is contained in:
parent
e42f14f0e0
commit
00f86833ac
3 changed files with 39 additions and 3 deletions
|
@ -4014,7 +4014,10 @@ recursive calls in starting lines of here-documents."
|
|||
;; 1+6+2+1+1+6+1+1+1=20 extra () before this:
|
||||
"\\|"
|
||||
;; -------- backslash-escaped stuff, don't interpret it
|
||||
"\\\\\\(['`\"($]\\)") ; BACKWACKED something-hairy
|
||||
"\\\\\\(['`\"($]\\)" ; BACKWACKED something-hairy
|
||||
"\\|"
|
||||
;; -------- $\ is a variable in code, but not in a string
|
||||
"\\(\\$\\\\\\)")
|
||||
"")))
|
||||
warning-message)
|
||||
(unwind-protect
|
||||
|
@ -4068,7 +4071,12 @@ recursive calls in starting lines of here-documents."
|
|||
(cperl-modify-syntax-type bb cperl-st-punct)))
|
||||
;; No processing in strings/comments beyond this point:
|
||||
((or (nth 3 state) (nth 4 state))
|
||||
t) ; Do nothing in comment/string
|
||||
;; Edge case: In a double-quoted string, $\ is not the
|
||||
;; punctuation variable, $ must not quote \ here. We
|
||||
;; generally make $ a punctuation character in strings
|
||||
;; and comments (Bug#69604).
|
||||
(when (match-beginning 22)
|
||||
(cperl-modify-syntax-type (match-beginning 22) cperl-st-punct)))
|
||||
((match-beginning 1) ; POD section
|
||||
;; "\\(\\`\n?\\|^\n\\)="
|
||||
(setq b (match-beginning 0)
|
||||
|
|
|
@ -251,7 +251,16 @@
|
|||
;; correctly the \() construct (Bug#11996) as well as references
|
||||
;; to string values.
|
||||
("\\(\\\\\\)['`\"($]" (1 (unless (nth 3 (syntax-ppss))
|
||||
(string-to-syntax "."))))
|
||||
(string-to-syntax "."))))
|
||||
;; A "$" in Perl code must escape the next char to protect against
|
||||
;; misinterpreting Perl's punctuation variables as unbalanced
|
||||
;; quotes or parens. This is not needed in strings and broken in
|
||||
;; the special case of "$\"" (Bug#69604). Make "$" a punctuation
|
||||
;; char in strings.
|
||||
("\\$" (0 (if (save-excursion
|
||||
(nth 3 (syntax-ppss (match-beginning 0))))
|
||||
(string-to-syntax ".")
|
||||
(string-to-syntax "/"))))
|
||||
;; Handle funny names like $DB'stop.
|
||||
("\\$ ?{?\\^?[_[:alpha:]][_[:alnum:]]*\\('\\)[_[:alpha:]]" (1 "_"))
|
||||
;; format statements
|
||||
|
|
|
@ -1431,6 +1431,25 @@ cperl-mode fontifies text after the delimiter as Perl code."
|
|||
(should (equal (get-text-property (point) 'face)
|
||||
font-lock-comment-face))))
|
||||
|
||||
(ert-deftest cperl-test-bug-69604 ()
|
||||
"Verify that $\" in a double-quoted string does not end the string.
|
||||
Both `perl-mode' and `cperl-mode' treat ?$ as a quoting/escaping char to
|
||||
avoid issues with punctuation variables. In a string, however, this is
|
||||
not appropriate."
|
||||
(let ((strings
|
||||
'("\"$\\\" in string ---\"; # \"" ; $ must not quote \
|
||||
"$\" . \" in string ---\"; # \"" ; $ must quote \
|
||||
"\"\\$\" . \" in string ---\"; # \""))) ; \$ must not quote
|
||||
(dolist (string strings)
|
||||
(with-temp-buffer
|
||||
(insert string)
|
||||
(funcall cperl-test-mode)
|
||||
(font-lock-ensure)
|
||||
(goto-char (point-min))
|
||||
(search-forward "in string")
|
||||
(should (equal (get-text-property (point) 'face)
|
||||
font-lock-string-face))))))
|
||||
|
||||
(ert-deftest test-indentation ()
|
||||
(ert-test-erts-file (ert-resource-file "cperl-indents.erts")))
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue