mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
* misc/ruby-mode.el: fix here-doc strings with inner quotes. patches
by Nathan Weizenbaum <nex342 AT gmail.com> from [ruby-core:17615] through [ruby-core:17910]. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@18150 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
56e28fcf98
commit
1bcbc29d95
2 changed files with 102 additions and 46 deletions
|
@ -1,3 +1,9 @@
|
||||||
|
Tue Jul 22 09:51:32 2008 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
|
* misc/ruby-mode.el: fix here-doc strings with inner quotes. patches
|
||||||
|
by Nathan Weizenbaum <nex342 AT gmail.com> from [ruby-core:17615]
|
||||||
|
through [ruby-core:17910].
|
||||||
|
|
||||||
Tue Jul 22 04:26:16 2008 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
Tue Jul 22 04:26:16 2008 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
* include/ruby/intern.h (rb_str_buf_new2): optimization for literals.
|
* include/ruby/intern.h (rb_str_buf_new2): optimization for literals.
|
||||||
|
|
|
@ -49,15 +49,27 @@
|
||||||
(defconst ruby-block-end-re "\\<end\\>")
|
(defconst ruby-block-end-re "\\<end\\>")
|
||||||
|
|
||||||
(defconst ruby-here-doc-beg-re
|
(defconst ruby-here-doc-beg-re
|
||||||
"<<\\(-\\)?\\(\\([a-zA-Z0-9_]+\\)\\|[\"]\\([^\"]+\\)[\"]\\|[']\\([^']+\\)[']\\)")
|
"\\(<\\)<\\(-\\)?\\(\\([a-zA-Z0-9_]+\\)\\|[\"]\\([^\"]+\\)[\"]\\|[']\\([^']+\\)[']\\)")
|
||||||
|
|
||||||
|
(defconst ruby-here-doc-end-re
|
||||||
|
"^\\([ \t]+\\)?\\(.*\\)\\(.\\)$")
|
||||||
|
|
||||||
(defun ruby-here-doc-end-match ()
|
(defun ruby-here-doc-end-match ()
|
||||||
(concat "^"
|
(concat "^"
|
||||||
(if (match-string 1) "[ \t]*" nil)
|
(if (match-string 2) "[ \t]*" nil)
|
||||||
(regexp-quote
|
(regexp-quote
|
||||||
(or (match-string 3)
|
(or (match-string 4)
|
||||||
(match-string 4)
|
(match-string 5)
|
||||||
(match-string 5)))))
|
(match-string 6)))))
|
||||||
|
|
||||||
|
(defun ruby-here-doc-beg-match ()
|
||||||
|
(let ((contents (regexp-quote (concat (match-string 2) (match-string 3)))))
|
||||||
|
(concat "<<"
|
||||||
|
(let ((match (match-string 1)))
|
||||||
|
(if (and match (> (length match) 0))
|
||||||
|
(concat "\\(?:-\\([\"']?\\)\\|\\([\"']\\)" (match-string 1) "\\)"
|
||||||
|
contents "\\(\\1\\|\\2\\)")
|
||||||
|
(concat "-?\\([\"']\\|\\)" contents "\\1"))))))
|
||||||
|
|
||||||
(defconst ruby-delimiter
|
(defconst ruby-delimiter
|
||||||
(concat "[?$/%(){}#\"'`.:]\\|<<\\|\\[\\|\\]\\|\\<\\("
|
(concat "[?$/%(){}#\"'`.:]\\|<<\\|\\[\\|\\]\\|\\<\\("
|
||||||
|
@ -172,7 +184,7 @@ Also ignores spaces after parenthesis when 'space."
|
||||||
|
|
||||||
(eval-when-compile (require 'cl))
|
(eval-when-compile (require 'cl))
|
||||||
(defun ruby-imenu-create-index-in-block (prefix beg end)
|
(defun ruby-imenu-create-index-in-block (prefix beg end)
|
||||||
(let ((index-alist '()) (case-fold-search nil)
|
(let ((index-alist '())
|
||||||
name next pos decl sing)
|
name next pos decl sing)
|
||||||
(goto-char beg)
|
(goto-char beg)
|
||||||
(while (re-search-forward "^\\s *\\(\\(class\\>\\(\\s *<<\\)?\\|module\\>\\)\\s *\\([^\(<\n ]+\\)\\|\\(def\\|alias\\)\\>\\s *\\([^\(\n ]+\\)\\)" end t)
|
(while (re-search-forward "^\\s *\\(\\(class\\>\\(\\s *<<\\)?\\|module\\>\\)\\s *\\([^\(<\n ]+\\)\\|\\(def\\|alias\\)\\>\\s *\\([^\(\n ]+\\)\\)" end t)
|
||||||
|
@ -220,6 +232,7 @@ Also ignores spaces after parenthesis when 'space."
|
||||||
(defun ruby-mode-variables ()
|
(defun ruby-mode-variables ()
|
||||||
(set-syntax-table ruby-mode-syntax-table)
|
(set-syntax-table ruby-mode-syntax-table)
|
||||||
(setq local-abbrev-table ruby-mode-abbrev-table)
|
(setq local-abbrev-table ruby-mode-abbrev-table)
|
||||||
|
(setq case-fold-search nil)
|
||||||
(make-local-variable 'indent-line-function)
|
(make-local-variable 'indent-line-function)
|
||||||
(setq indent-line-function 'ruby-indent-line)
|
(setq indent-line-function 'ruby-indent-line)
|
||||||
(make-local-variable 'require-final-newline)
|
(make-local-variable 'require-final-newline)
|
||||||
|
@ -235,6 +248,8 @@ Also ignores spaces after parenthesis when 'space."
|
||||||
(setq indent-tabs-mode ruby-indent-tabs-mode)
|
(setq indent-tabs-mode ruby-indent-tabs-mode)
|
||||||
(make-local-variable 'parse-sexp-ignore-comments)
|
(make-local-variable 'parse-sexp-ignore-comments)
|
||||||
(setq parse-sexp-ignore-comments t)
|
(setq parse-sexp-ignore-comments t)
|
||||||
|
(make-local-variable 'parse-sexp-lookup-properties)
|
||||||
|
(setq parse-sexp-lookup-properties t)
|
||||||
(make-local-variable 'paragraph-start)
|
(make-local-variable 'paragraph-start)
|
||||||
(setq paragraph-start (concat "$\\|" page-delimiter))
|
(setq paragraph-start (concat "$\\|" page-delimiter))
|
||||||
(make-local-variable 'paragraph-separate)
|
(make-local-variable 'paragraph-separate)
|
||||||
|
@ -645,7 +660,6 @@ The variable ruby-indent-level controls the amount of indentation.
|
||||||
(save-excursion
|
(save-excursion
|
||||||
(beginning-of-line)
|
(beginning-of-line)
|
||||||
(let ((indent-point (point))
|
(let ((indent-point (point))
|
||||||
(case-fold-search nil)
|
|
||||||
state bol eol begin op-end
|
state bol eol begin op-end
|
||||||
(paren (progn (skip-syntax-forward " ")
|
(paren (progn (skip-syntax-forward " ")
|
||||||
(and (char-after) (matching-paren (char-after)))))
|
(and (char-after) (matching-paren (char-after)))))
|
||||||
|
@ -1090,7 +1104,7 @@ balanced expression is found."
|
||||||
(setq font-lock-variable-name-face font-lock-type-face))
|
(setq font-lock-variable-name-face font-lock-type-face))
|
||||||
|
|
||||||
(setq ruby-font-lock-syntactic-keywords
|
(setq ruby-font-lock-syntactic-keywords
|
||||||
'(
|
`(
|
||||||
;; #{ }, #$hoge, #@foo are not comments
|
;; #{ }, #$hoge, #@foo are not comments
|
||||||
("\\(#\\)[{$@]" 1 (1 . nil))
|
("\\(#\\)[{$@]" 1 (1 . nil))
|
||||||
;; the last $', $", $` in the respective string is not variable
|
;; the last $', $", $` in the respective string is not variable
|
||||||
|
@ -1106,7 +1120,76 @@ balanced expression is found."
|
||||||
(4 (7 . ?/))
|
(4 (7 . ?/))
|
||||||
(6 (7 . ?/)))
|
(6 (7 . ?/)))
|
||||||
("^\\(=\\)begin\\(\\s \\|$\\)" 1 (7 . nil))
|
("^\\(=\\)begin\\(\\s \\|$\\)" 1 (7 . nil))
|
||||||
("^\\(=\\)end\\(\\s \\|$\\)" 1 (7 . nil))))
|
("^\\(=\\)end\\(\\s \\|$\\)" 1 (7 . nil))
|
||||||
|
(,(concat ruby-here-doc-beg-re ".*\\(\n\\)")
|
||||||
|
,(+ 1 (regexp-opt-depth ruby-here-doc-beg-re))
|
||||||
|
(ruby-here-doc-beg-syntax))
|
||||||
|
(,ruby-here-doc-end-re 3 (ruby-here-doc-end-syntax))))
|
||||||
|
|
||||||
|
(defun ruby-in-non-here-doc-string-p ()
|
||||||
|
(let ((syntax (syntax-ppss)))
|
||||||
|
(or (nth 4 syntax)
|
||||||
|
;; In a string *without* a generic delimiter
|
||||||
|
;; If it's generic, it's a heredoc and we don't care
|
||||||
|
;; See `parse-partial-sexp'
|
||||||
|
(numberp (nth 3 syntax)))))
|
||||||
|
|
||||||
|
(defun ruby-in-here-doc-p ()
|
||||||
|
(save-excursion
|
||||||
|
(let ((old-point (point)))
|
||||||
|
(beginning-of-line)
|
||||||
|
(catch 'found-beg
|
||||||
|
(while (re-search-backward ruby-here-doc-beg-re nil t)
|
||||||
|
(if (not (or (syntax-ppss-context (syntax-ppss))
|
||||||
|
(ruby-here-doc-find-end old-point)))
|
||||||
|
(throw 'found-beg t)))))))
|
||||||
|
|
||||||
|
(defun ruby-here-doc-find-end (&optional limit)
|
||||||
|
"Expects the point to be on a line with one or more heredoc
|
||||||
|
openers. Returns the buffer position at which all heredocs on the
|
||||||
|
line are terminated, or nil if they aren't terminated before the
|
||||||
|
buffer position `limit' or the end of the buffer."
|
||||||
|
(save-excursion
|
||||||
|
(beginning-of-line)
|
||||||
|
(catch 'done
|
||||||
|
(let ((eol (save-excursion (end-of-line) (point)))
|
||||||
|
;; Fake match data such that (match-end 0) is at eol
|
||||||
|
(end-match-data (progn (looking-at ".*$") (match-data)))
|
||||||
|
beg-match-data end-re)
|
||||||
|
(while (re-search-forward ruby-here-doc-beg-re eol t)
|
||||||
|
(setq beg-match-data (match-data))
|
||||||
|
(setq end-re (ruby-here-doc-end-match))
|
||||||
|
|
||||||
|
(set-match-data end-match-data)
|
||||||
|
(goto-char (match-end 0))
|
||||||
|
(unless (re-search-forward end-re limit t) (throw 'done nil))
|
||||||
|
(setq end-match-data (match-data))
|
||||||
|
|
||||||
|
(set-match-data beg-match-data)
|
||||||
|
(goto-char (match-end 0)))
|
||||||
|
(set-match-data end-match-data)
|
||||||
|
(goto-char (match-end 0))
|
||||||
|
(point)))))
|
||||||
|
|
||||||
|
(defun ruby-here-doc-beg-syntax ()
|
||||||
|
(save-excursion
|
||||||
|
(goto-char (match-beginning 0))
|
||||||
|
(unless (or (ruby-in-non-here-doc-string-p)
|
||||||
|
(ruby-in-here-doc-p))
|
||||||
|
(string-to-syntax "|"))))
|
||||||
|
|
||||||
|
(defun ruby-here-doc-end-syntax ()
|
||||||
|
(save-excursion
|
||||||
|
(goto-char (match-end 0))
|
||||||
|
(let ((old-point (point))
|
||||||
|
(beg-exists (re-search-backward (ruby-here-doc-beg-match) nil t))
|
||||||
|
(eol (save-excursion (end-of-line) (point))))
|
||||||
|
(if (and beg-exists ; If there is a heredoc that matches this line...
|
||||||
|
(null (syntax-ppss-context (syntax-ppss))) ; And that's not inside a heredoc/string/comment...
|
||||||
|
(progn (goto-char (match-end 0)) ; And it's the last heredoc on its line...
|
||||||
|
(not (re-search-forward ruby-here-doc-beg-re eol t)))
|
||||||
|
(eq old-point (ruby-here-doc-find-end old-point))) ; And it ends at this point...
|
||||||
|
(string-to-syntax "|")))))
|
||||||
|
|
||||||
(if (featurep 'xemacs)
|
(if (featurep 'xemacs)
|
||||||
(put 'ruby-mode 'font-lock-defaults
|
(put 'ruby-mode 'font-lock-defaults
|
||||||
|
@ -1147,35 +1230,7 @@ balanced expression is found."
|
||||||
(modify-syntax-entry ?_ "w" tbl)
|
(modify-syntax-entry ?_ "w" tbl)
|
||||||
tbl))
|
tbl))
|
||||||
|
|
||||||
(defun ruby-font-lock-here-docs (limit)
|
(defconst ruby-font-lock-keywords
|
||||||
(if (re-search-forward ruby-here-doc-beg-re limit t)
|
|
||||||
(let (beg)
|
|
||||||
(beginning-of-line)
|
|
||||||
(forward-line)
|
|
||||||
(setq beg (point))
|
|
||||||
(if (re-search-forward (ruby-here-doc-end-match) nil t)
|
|
||||||
(progn
|
|
||||||
(set-match-data (list beg (point)))
|
|
||||||
t)))))
|
|
||||||
|
|
||||||
(defun ruby-font-lock-maybe-here-docs (limit)
|
|
||||||
(let (beg)
|
|
||||||
(save-excursion
|
|
||||||
(if (re-search-backward ruby-here-doc-beg-re nil t)
|
|
||||||
(progn
|
|
||||||
(beginning-of-line)
|
|
||||||
(forward-line)
|
|
||||||
(setq beg (point)))))
|
|
||||||
(if (and beg
|
|
||||||
(let ((end-match (ruby-here-doc-end-match)))
|
|
||||||
(and (not (re-search-backward end-match beg t))
|
|
||||||
(re-search-forward end-match nil t))))
|
|
||||||
(progn
|
|
||||||
(set-match-data (list beg (point)))
|
|
||||||
t)
|
|
||||||
nil)))
|
|
||||||
|
|
||||||
(defvar ruby-font-lock-keywords
|
|
||||||
(list
|
(list
|
||||||
;; functions
|
;; functions
|
||||||
'("^\\s *def\\s +\\([^( \t\n]+\\)"
|
'("^\\s *def\\s +\\([^( \t\n]+\\)"
|
||||||
|
@ -1224,6 +1279,8 @@ balanced expression is found."
|
||||||
"\\|")
|
"\\|")
|
||||||
"\\)\\>\\)")
|
"\\)\\>\\)")
|
||||||
2)
|
2)
|
||||||
|
;; here-doc beginnings
|
||||||
|
(list ruby-here-doc-beg-re 0 'font-lock-string-face)
|
||||||
;; variables
|
;; variables
|
||||||
'("\\(^\\|[^_:.@$]\\|\\.\\.\\)\\b\\(nil\\|self\\|true\\|false\\)\\>"
|
'("\\(^\\|[^_:.@$]\\|\\.\\.\\)\\b\\(nil\\|self\\|true\\|false\\)\\>"
|
||||||
2 font-lock-variable-name-face)
|
2 font-lock-variable-name-face)
|
||||||
|
@ -1237,13 +1294,6 @@ balanced expression is found."
|
||||||
0 font-lock-comment-face t)
|
0 font-lock-comment-face t)
|
||||||
'(ruby-font-lock-maybe-docs
|
'(ruby-font-lock-maybe-docs
|
||||||
0 font-lock-comment-face t)
|
0 font-lock-comment-face t)
|
||||||
;; "here" document
|
|
||||||
'(ruby-font-lock-here-docs
|
|
||||||
0 font-lock-string-face t)
|
|
||||||
'(ruby-font-lock-maybe-here-docs
|
|
||||||
0 font-lock-string-face t)
|
|
||||||
`(,ruby-here-doc-beg-re
|
|
||||||
0 font-lock-string-face t)
|
|
||||||
;; general delimited string
|
;; general delimited string
|
||||||
'("\\(^\\|[[ \t\n<+(,=]\\)\\(%[xrqQwW]?\\([^<[{(a-zA-Z0-9 \n]\\)[^\n\\\\]*\\(\\\\.[^\n\\\\]*\\)*\\(\\3\\)\\)"
|
'("\\(^\\|[[ \t\n<+(,=]\\)\\(%[xrqQwW]?\\([^<[{(a-zA-Z0-9 \n]\\)[^\n\\\\]*\\(\\\\.[^\n\\\\]*\\)*\\(\\3\\)\\)"
|
||||||
(2 font-lock-string-face))
|
(2 font-lock-string-face))
|
||||||
|
|
Loading…
Reference in a new issue