Skip to content

Commit 311cfd0

Browse files
committed
Protect against symbols with unsafe chars
Fixes bug#648. * lispy.el lispy--symbol-safe-chars: define list of safe chars. (lispy--read): protect against unsafe chars in a symbol. (lispy--replace-regexp-in-code): add predicate to only replace on match data.
1 parent 8175e9a commit 311cfd0

File tree

1 file changed

+33
-15
lines changed

1 file changed

+33
-15
lines changed

lispy.el

+33-15
Original file line numberDiff line numberDiff line change
@@ -7200,13 +7200,21 @@ For example, a `setq' statement is amended with variable name that it uses."
72007200
(insert char)
72017201
(lispy--indent-region (point) pt))))
72027202

7203-
(defun lispy--replace-regexp-in-code (regexp to-string)
7203+
(defun lispy--replace-regexp-in-code
7204+
(regexp to-string &optional pred)
72047205
"Replace text matching REGEXP with TO-STRING in whole buffer.
7205-
Ignore the matches in strings and comments."
7206-
(goto-char (point-min))
7207-
(while (re-search-forward regexp nil t)
7208-
(unless (lispy--in-string-or-comment-p)
7209-
(replace-match to-string))))
7206+
Ignore the matches in strings and comments.
7207+
7208+
PRED should be a 0-arg predicate with access to the regexp match
7209+
data. PRED defaults to `always', and should return non-nil when
7210+
a specific match data should be replaced."
7211+
(save-excursion
7212+
(goto-char (point-min))
7213+
(save-match-data
7214+
(while (re-search-forward regexp nil t)
7215+
(unless (lispy--in-string-or-comment-p)
7216+
(when (funcall (or pred #'always))
7217+
(replace-match to-string)))))))
72107218

72117219
;;* Utilities: source transformation
72127220
(defvar lispy--braces-table
@@ -7286,6 +7294,18 @@ See https://clojure.org/guides/weird_characters#_character_literal.")
72867294
(match-string subexp)))
72877295
t t nil subexp)))))
72887296

7297+
(defconst lispy--symbol-safe-chars
7298+
(seq-concatenate 'list "+-*/:="
7299+
(number-sequence ?a ?z)
7300+
(number-sequence ?A ?Z))
7301+
"List of known \"safe\" characters.
7302+
Safe characters are those which are suitable for a symbol and
7303+
which have no special reader syntax.
7304+
7305+
Missing a few safe characters would not be a serious problem. It
7306+
would only produce a slightly larger internal representation when
7307+
lispy tries to parse a given sexp.")
7308+
72897309
;; TODO: Make the read test pass on string with semi-colon
72907310
(defun lispy--read (str)
72917311
"Read STR including comments and newlines."
@@ -7524,15 +7544,13 @@ See https://clojure.org/guides/weird_characters#_character_literal.")
75247544
(unless (lispy--in-string-or-comment-p)
75257545
(replace-match (format "(ly-raw racket-option %s)"
75267546
(match-string 1)))))
7527-
;; Clojure # in a symbol
7528-
(goto-char (point-min))
7529-
(while (re-search-forward "\\_<\\(?:\\sw\\|\\s_\\)+\\_>" nil t)
7530-
(unless (lispy--in-string-p)
7531-
(when (cl-position ?# (match-string 0))
7532-
(let* ((bnd (lispy--bounds-dwim))
7533-
(str (lispy--string-dwim bnd)))
7534-
(delete-region (car bnd) (cdr bnd))
7535-
(insert (format "(ly-raw symbol %S)" str))))))
7547+
;; Protect symbols containing unsafe characters
7548+
(lispy--replace-regexp-in-code
7549+
"\\_<\\(?:\\sw\\|\\s_\\)+\\_>"
7550+
"(ly-raw symbol \"\\&\")"
7551+
(lambda ()
7552+
(seq-difference
7553+
(match-string 0) lispy--symbol-safe-chars)))
75367554
;; Clojure (. object method)
75377555
(goto-char (point-min))
75387556
(while (re-search-forward "(\\.[\t\n ]" nil t)

0 commit comments

Comments
 (0)