[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[elpa] externals/javaimp ed09795: Improve decl-suffix handling
From: |
Filipp Gunbin |
Subject: |
[elpa] externals/javaimp ed09795: Improve decl-suffix handling |
Date: |
Thu, 29 Jul 2021 21:47:57 -0400 (EDT) |
branch: externals/javaimp
commit ed09795175cb728a5da6cb52e5ca491b3f10c4eb
Author: Filipp Gunbin <fgunbin@okko.tv>
Commit: Filipp Gunbin <fgunbin@okko.tv>
Improve decl-suffix handling
---
javaimp-parse.el | 129 +++++++++++++++++++++++++++++--------------------------
javaimp-tests.el | 5 +++
2 files changed, 72 insertions(+), 62 deletions(-)
diff --git a/javaimp-parse.el b/javaimp-parse.el
index 009bbc4..e123c2a 100644
--- a/javaimp-parse.el
+++ b/javaimp-parse.el
@@ -57,6 +57,15 @@ present."
st)
"Enables parsing angle brackets as lists")
+(defmacro javaimp--parse-with-arglist-syntax (beg &rest body)
+ (declare (debug t))
+ (let ((begin (make-symbol "begin")))
+ `(let ((,begin ,beg))
+ (syntax-ppss-flush-cache ,begin)
+ (unwind-protect
+ (with-syntax-table javaimp--arglist-syntax-table
+ ,@body)
+ (syntax-ppss-flush-cache ,begin)))))
(defsubst javaimp--parse-substr-before-< (str)
(let ((end (string-search "<" str)))
@@ -68,27 +77,24 @@ present."
"Parse arg list between BEG and END, of the form 'TYPE NAME,
...'. Return list of conses (TYPE . NAME). If ONLY-TYPE is
non-nil, then name parsing is skipped."
- (save-excursion
- (save-restriction
- (syntax-ppss-flush-cache beg)
- (narrow-to-region beg end)
- (prog1
- (with-syntax-table javaimp--arglist-syntax-table
- (goto-char (point-max))
- (ignore-errors
- (let (res)
- (while (progn
- (javaimp--parse-skip-back-until)
- (not (bobp)))
- (push (javaimp--parse-arglist-one-arg only-type) res)
- ;; move back to the previous argument, if any
- (when (javaimp--parse-skip-back-until
- (lambda (_last-what _last-pos)
- (and (not (bobp))
- (= (char-before) ?,))))
- (backward-char))) ; skip comma
- res)))
- (syntax-ppss-flush-cache beg)))))
+ (javaimp--parse-with-arglist-syntax beg
+ (save-excursion
+ (save-restriction
+ (narrow-to-region beg end)
+ (goto-char (point-max))
+ (ignore-errors
+ (let (res)
+ (while (progn
+ (javaimp--parse-skip-back-until)
+ (not (bobp)))
+ (push (javaimp--parse-arglist-one-arg only-type) res)
+ ;; move back to the previous argument, if any
+ (when (javaimp--parse-skip-back-until
+ (lambda (_last-what _last-pos)
+ (and (not (bobp))
+ (= (char-before) ?,))))
+ (backward-char))) ; skip comma
+ res))))))
(defun javaimp--parse-arglist-one-arg (only-type)
"Parse one argument as type and name backwards starting from
@@ -179,28 +185,28 @@ as for `re-search-backward'."
(1+ scope-start)))))
(defun javaimp--parse-decl-suffix (regexp state &optional bound)
- "Subroutine of scope parsers. Attempts to parse declaration
-suffix backwards (but not farther than BOUND), returning ARGS in
-the same format as `javaimp--parse-arglist' (but here, only TYPE
-element component will be present). Point is left at the
-position from where scope parsing may be continued. Returns t if
-parsing failed and should not be continued."
+ "Attempts to parse declaration suffix backwards from point (but
+not farther than BOUND), returning non-nil on success. More
+precisely, the value is the end of the match for REGEXP. Point
+is left before the match. Otherwise, the result is nil and point
+is unchanged."
(let ((pos (point)))
- (when (javaimp--rsb-outside-context regexp bound t)
- (if (ignore-errors ;As in javaimp--parse-preceding
- (= (scan-lists (match-end 0) 1 -1)
- (1+ (nth 1 state))))
- (let ((res (save-match-data
- (javaimp--parse-arglist (match-end 0) pos t))))
- (if res
- (goto-char (match-beginning 0))
- ;; Something's wrong here: tell the caller to stop
- ;; parsing
- (setq res t))
- res)
- ;; just return to where we started
- (goto-char pos)
- nil))))
+ (catch 'found
+ (while (javaimp--rsb-outside-context regexp bound t)
+ (let ((scan-pos (match-end 0)))
+ (javaimp--parse-with-arglist-syntax scan-pos
+ (while (and scan-pos (<= scan-pos (nth 1 state)))
+ (if (ignore-errors
+ (= (scan-lists scan-pos 1 -1) ;As in
javaimp--parse-preceding
+ (1+ (nth 1 state))))
+ (progn
+ (goto-char (match-beginning 0))
+ (throw 'found (match-end 0)))
+ (setq scan-pos (ignore-errors
+ (scan-lists scan-pos 1 0))))))))
+ ;; just return to start
+ (goto-char pos)
+ nil)))
@@ -250,26 +256,21 @@ those may later become 'local-class' (see
`javaimp--parse-scopes')."
(nth 1 state))
(let* ((keyword-start (match-beginning 1))
(keyword-end (match-end 1))
- (decl-suffix (progn
- (goto-char (nth 1 state))
- (or (javaimp--parse-decl-suffix "\\<extends\\>"
- state
keyword-end)
- (javaimp--parse-decl-suffix
"\\<implements\\>"
- state
keyword-end)
- (javaimp--parse-decl-suffix "\\<permits\\>"
- state
keyword-end))))
arglist)
- (unless (eq decl-suffix t)
- ;; we either skipped back over the valid declaration
- ;; suffix(-es), or there isn't any
- (setq arglist (javaimp--parse-arglist keyword-end (point) t))
- (when (= (length arglist) 1)
- (make-javaimp-scope :type (intern
- (buffer-substring-no-properties
- keyword-start keyword-end))
- :name (javaimp--parse-substr-before-< (caar
arglist))
- :start keyword-start
- :open-brace (nth 1 state))))))))
+ (goto-char (nth 1 state))
+ (or (javaimp--parse-decl-suffix "\\<extends\\>" state keyword-end)
+ (javaimp--parse-decl-suffix "\\<implements\\>" state keyword-end)
+ (javaimp--parse-decl-suffix "\\<permits\\>" state keyword-end))
+ ;; we either skipped back over the valid declaration
+ ;; suffix(-es), or there wasn't any
+ (setq arglist (javaimp--parse-arglist keyword-end (point) t))
+ (when (= (length arglist) 1)
+ (make-javaimp-scope :type (intern
+ (buffer-substring-no-properties
+ keyword-start keyword-end))
+ :name (javaimp--parse-substr-before-< (caar
arglist))
+ :start keyword-start
+ :open-brace (nth 1 state)))))))
(defun javaimp--parse-scope-simple-stmt (state)
"Attempts to parse `simple-statement' scope."
@@ -311,7 +312,11 @@ those may later become 'local-class' (see
`javaimp--parse-scopes')."
(defun javaimp--parse-scope-method-or-stmt (state)
"Attempts to parse `method' or `statement' scope."
(save-excursion
- (let ((throws-args (javaimp--parse-decl-suffix "\\<throws\\>" state)))
+ (let ((throws-args
+ (let ((pos (javaimp--parse-decl-suffix "\\<throws\\>" state)))
+ (when pos
+ (or (javaimp--parse-arglist pos (nth 1 state) t)
+ t)))))
(when (and (not (eq throws-args t))
(progn
(javaimp--parse-skip-back-until)
diff --git a/javaimp-tests.el b/javaimp-tests.el
index 55bcbc0..d46ee37 100644
--- a/javaimp-tests.el
+++ b/javaimp-tests.el
@@ -56,6 +56,11 @@
'("class Foo<Bar, Baz> extends FooSuper<Bar, Baz> \
implements Interface1<Bar, Baz>, Interface2 {"
class "Foo")
+ '("class Foo<E extends Bar> {"
+ class "Foo")
+ '("class Foo<T extends Baz<? extends Baz2>> \
+extends Bar<? extends Baz<? extends Baz2>> {"
+ class "Foo")
'("interface Foo<Bar, Baz> {"
interface "Foo")
'("private enum Foo {"
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [elpa] externals/javaimp ed09795: Improve decl-suffix handling,
Filipp Gunbin <=