Annotation of OpenXM_contrib2/windows/post-msg-asirgui/asir-mode.el, Revision 1.9
1.1 takayama 1: ;; -*- mode: emacs-lisp -*-
2: ;;
3: ;; asir-mode.el -- asir mode
4: ;;
5:
6: ;; This program is free software: you can redistribute it and/or modify
7: ;; it under the terms of the GNU General Public License as published by
8: ;; the Free Software Foundation, either version 3 of the License, or
9: ;; (at your option) any later version.
10:
1.9 ! takayama 11: ;;;; AsirGUI for Windows
! 12: (defconst asir-exec-path-default '("~/Desktop/asir/bin" "c:/Program Files/asir/bin" "c:/Program Files (x64)/asir/bin" "c:/asir/bin")
! 13: "Default Search path for asir binary in Windows")
1.7 ohara 14:
1.9 ! takayama 15: (defvar asir-exec-path asir-exec-path-default
! 16: "Search path for asir binary")
1.1 takayama 17:
1.9 ! takayama 18: (defun asir-effective-exec-path ()
1.1 takayama 19: "Search path for command"
20: (let* ((dir (getenv "ASIR_ROOTDIR"))
1.9 ! takayama 21: (path (append asir-exec-path exec-path)))
! 22: (if dir (cons (concat dir "/bin") path) path)))
1.1 takayama 23:
1.9 ! takayama 24: (defun asir-executable-find (command)
1.1 takayama 25: "Search for command"
26: (let* ((exec-path (asir-effective-exec-path)))
1.9 ! takayama 27: (executable-find command)))
1.1 takayama 28:
1.9 ! takayama 29: (defun asir-start-asirgui ()
! 30: "Run asirgui"
1.1 takayama 31: (interactive)
1.9 ! takayama 32: (let ((exec-path (asir-effective-exec-path)))
! 33: (start-process "asir-proc-asirgui" nil "asirgui")))
1.1 takayama 34:
1.9 ! takayama 35: (defun asir-terminate-asirgui ()
! 36: "Execute the current buffer on asir"
1.1 takayama 37: (interactive)
1.9 ! takayama 38: (let ((exec-path (asir-effective-exec-path)))
! 39: (start-process "asir-proc-cmdasir" nil "cmdasir" "--quit")))
1.1 takayama 40:
1.9 ! takayama 41: (defun asir-execute-current-buffer-on-asir ()
! 42: "Execute the current buffer on asir"
1.1 takayama 43: (interactive)
44: (let ((exec-path (asir-effective-exec-path)))
1.9 ! takayama 45: (start-process "asir-proc-cmdasir" nil "cmdasir" (buffer-file-name))))
1.1 takayama 46:
1.9 ! takayama 47: (defun asir-execute-region-on-asir ()
! 48: "Execute the region on asir"
1.1 takayama 49: (interactive)
1.9 ! takayama 50: (save-excursion
! 51: (if mark-active
! 52: (let ((exec-path (asir-effective-exec-path))
! 53: (temp-file (make-temp-file (format "%s/cmdasir-" (getenv "TEMP")))))
! 54: (write-region (region-beginning) (region-end) temp-file)
! 55: (start-process "asir-proc-cmdasir" nil "cmdasir" temp-file)))))
1.4 ohara 56:
1.1 takayama 57: ;;;; Extension for CC-mode.
58:
59: (require 'cc-mode)
60:
61: (eval-when-compile
62: (require 'cc-langs)
63: (require 'cc-engine)
64: (require 'cc-fonts))
65:
66: (eval-and-compile
67: ;; Make our mode known to the language constant system. Use Java
68: ;; mode as the fallback for the constants we don't change here.
69: ;; This needs to be done also at compile time since the language
70: ;; constants are evaluated then.
71: (c-add-language 'asir-mode 'c++-mode))
72:
73: (c-lang-defconst c-stmt-delim-chars asir "^;${}?:")
74: (c-lang-defconst c-stmt-delim-chars-with-comma asir "^;$,{}?:")
75: (c-lang-defconst c-other-op-syntax-tokens
76: asir (cons "$" (c-lang-const c-other-op-syntax-tokens c)))
77: (c-lang-defconst c-identifier-syntax-modifications
78: asir (remove '(?$ . "w") (c-lang-const c-identifier-syntax-modifications c)))
79: (c-lang-defconst c-symbol-chars asir (concat c-alnum "_"))
80:
81: (c-lang-defconst c-primitive-type-kwds asir '("def" "extern" "static" "localf" "function"))
82: (c-lang-defconst c-primitive-type-prefix-kwds asir nil)
83: (c-lang-defconst c-type-list-kwds asir nil)
84: (c-lang-defconst c-class-decl-kwds asir '("module"))
85: (c-lang-defconst c-othe-decl-kwds asir '("endmodule" "end"))
86: (c-lang-defconst c-type-modifier-kwds asir nil)
87: (c-lang-defconst c-modifier-kwds asir nil)
88:
89: (c-lang-defconst c-mode-menu
90: asir
91: (append (c-lang-const c-mode-menu c)
92: '("----"
1.9 ! takayama 93: ["Start asirgui" asir-start-asirgui (eq system-type 'windows-nt)]
! 94: ["Terminate asirgui" asir-terminate-asirgui (eq system-type 'windows-nt)]
! 95: ["Execute the current buffer on asir" asir-execute-current-buffer-on-asir
! 96: (and (eq system-type 'windows-nt) (buffer-file-name))]
! 97: ["Execute the region on asir" asir-execute-region-on-asir
! 98: (and (eq system-type 'windows-nt) mark-active)]
1.1 takayama 99: )))
100:
101: (defvar asir-font-lock-extra-types nil
102: "*List of extra types (aside from the type keywords) to recognize in asir mode.
103: Each list item should be a regexp matching a single identifier.")
104:
105: (defconst asir-font-lock-keywords-1 (c-lang-const c-matchers-1 asir)
106: "Minimal highlighting for asir mode.")
107:
108: (defconst asir-font-lock-keywords-2 (c-lang-const c-matchers-2 asir)
109: "Fast normal highlighting for asir mode.")
110:
111: (defconst asir-font-lock-keywords-3 (c-lang-const c-matchers-3 asir)
112: "Accurate normal highlighting for asir mode.")
113:
114: (defvar asir-font-lock-keywords asir-font-lock-keywords-3
115: "Default expressions to highlight in asir mode.")
116:
117: (defvar asir-mode-syntax-table nil
118: "Syntax table used in asir-mode buffers.")
119: (or asir-mode-syntax-table
120: (setq asir-mode-syntax-table
121: (funcall (c-lang-const c-make-mode-syntax-table asir))))
122:
123: (defvar asir-mode-abbrev-table nil
124: "Abbreviation table used in asir-mode buffers.")
125:
126: (defvar asir-mode-map (let ((map (c-make-inherited-keymap)))
127: ;; Add bindings which are only useful for asir
128: map)
129: "Keymap used in asir-mode buffers.")
130:
131: (easy-menu-define asir-menu asir-mode-map "asir Mode Commands"
132: ;; Can use `asir' as the language for `c-mode-menu'
133: ;; since its definition covers any language. In
134: ;; this case the language is used to adapt to the
135: ;; nonexistence of a cpp pass and thus removing some
136: ;; irrelevant menu alternatives.
137: (cons "Asir" (c-lang-const c-mode-menu asir)))
138:
139: (defun asir-mode ()
140: "Major mode for editing asir code.
141: This is a simple example of a separate mode derived from CC Mode to
142: support a language with syntax similar to C/C++/ObjC/Java/IDL/Pike.
143:
144: The hook `c-mode-common-hook' is run with no args at mode
145: initialization, then `asir-mode-hook'.
146:
147: Key bindings:
148: \\{asir-mode-map}"
149: (interactive)
150: (kill-all-local-variables)
151: (c-initialize-cc-mode t)
152: (set-syntax-table asir-mode-syntax-table)
153: (setq major-mode 'asir-mode
154: mode-name "asir"
155: local-abbrev-table asir-mode-abbrev-table
156: abbrev-mode t)
157: (use-local-map asir-mode-map)
158: ;; `c-init-language-vars' is a macro that is expanded at compile
159: ;; time to a large `setq' with all the language variables and their
160: ;; customized values for our language.
161: (c-init-language-vars asir-mode)
162: ;; `c-common-init' initializes most of the components of a CC Mode
163: ;; buffer, including setup of the mode menu, font-lock, etc.
164: ;; There's also a lower level routine `c-basic-common-init' that
165: ;; only makes the necessary initialization to get the syntactic
166: ;; analysis and similar things working.
167: (c-common-init 'asir-mode)
168: ;;(easy-menu-add asir-menu)
169: (run-hooks 'c-mode-common-hook)
170: (run-hooks 'asir-mode-hook)
171: (c-update-modeline))
172:
173: (if (fboundp 'asir-backup:c-guess-basic-syntax)
174: nil
175: (fset 'asir-backup:c-guess-basic-syntax (symbol-function 'c-guess-basic-syntax))
176: (defun c-guess-basic-syntax ()
177: "A modified c-guess-basic-syntax for asir-mode"
178: (if (eq major-mode 'asir-mode)
179: (asir-c-guess-basic-syntax)
180: (asir-backup:c-guess-basic-syntax))))
181:
182: ;; Meadow 3 does not have `c-brace-anchor-point'
183: ;; This function was copied from cc-engine.el of Emacs 23.4
184: (if (and (featurep 'meadow) (not (fboundp 'c-brace-anchor-point)))
185: (defun c-brace-anchor-point (bracepos)
186: ;; BRACEPOS is the position of a brace in a construct like "namespace
187: ;; Bar {". Return the anchor point in this construct; this is the
188: ;; earliest symbol on the brace's line which isn't earlier than
189: ;; "namespace".
190: ;;
191: ;; Currently (2007-08-17), "like namespace" means "matches
192: ;; c-other-block-decl-kwds". It doesn't work with "class" or "struct"
193: ;; or anything like that.
194: (save-excursion
195: (let ((boi (c-point 'boi bracepos)))
196: (goto-char bracepos)
197: (while (and (> (point) boi)
198: (not (looking-at c-other-decl-block-key)))
199: (c-backward-token-2))
200: (if (> (point) boi) (point) boi))))
201: )
202:
203: ;; The function `c-guess-basic-syntax' was copied from cc-engine.el of Emacs 23.4 and
204: ;; was modified for Risa/Asir.
205: ;; CASE 5D, 5J, 18 are corrected.
206:
207: ;;;; Beginning of `asir-c-guess-basic-syntax'
208: (defun asir-c-guess-basic-syntax ()
209: "Return the syntactic context of the current line."
210: (save-excursion
211: (beginning-of-line)
212: (c-save-buffer-state
213: ((indent-point (point))
214: (case-fold-search nil)
215: ;; A whole ugly bunch of various temporary variables. Have
216: ;; to declare them here since it's not possible to declare
217: ;; a variable with only the scope of a cond test and the
218: ;; following result clauses, and most of this function is a
219: ;; single gigantic cond. :P
220: literal char-before-ip before-ws-ip char-after-ip macro-start
221: in-macro-expr c-syntactic-context placeholder c-in-literal-cache
222: step-type tmpsymbol keyword injava-inher special-brace-list tmp-pos
223: containing-<
224: ;; The following record some positions for the containing
225: ;; declaration block if we're directly within one:
226: ;; `containing-decl-open' is the position of the open
227: ;; brace. `containing-decl-start' is the start of the
228: ;; declaration. `containing-decl-kwd' is the keyword
229: ;; symbol of the keyword that tells what kind of block it
230: ;; is.
231: containing-decl-open
232: containing-decl-start
233: containing-decl-kwd
234: ;; The open paren of the closest surrounding sexp or nil if
235: ;; there is none.
236: containing-sexp
237: ;; The position after the closest preceding brace sexp
238: ;; (nested sexps are ignored), or the position after
239: ;; `containing-sexp' if there is none, or (point-min) if
240: ;; `containing-sexp' is nil.
241: lim
242: ;; The paren state outside `containing-sexp', or at
243: ;; `indent-point' if `containing-sexp' is nil.
244: (paren-state (c-parse-state))
245: ;; There's always at most one syntactic element which got
246: ;; an anchor pos. It's stored in syntactic-relpos.
247: syntactic-relpos
248: (c-stmt-delim-chars c-stmt-delim-chars))
249:
250: ;; Check if we're directly inside an enclosing declaration
251: ;; level block.
252: (when (and (setq containing-sexp
253: (c-most-enclosing-brace paren-state))
254: (progn
255: (goto-char containing-sexp)
256: (eq (char-after) ?{))
257: (setq placeholder
258: (c-looking-at-decl-block
259: (c-most-enclosing-brace paren-state
260: containing-sexp)
261: t)))
262: (setq containing-decl-open containing-sexp
263: containing-decl-start (point)
264: containing-sexp nil)
265: (goto-char placeholder)
266: (setq containing-decl-kwd (and (looking-at c-keywords-regexp)
267: (c-keyword-sym (match-string 1)))))
268:
269: ;; Init some position variables.
270: (if c-state-cache
271: (progn
272: (setq containing-sexp (car paren-state)
273: paren-state (cdr paren-state))
274: (if (consp containing-sexp)
275: (progn
276: (setq lim (cdr containing-sexp))
277: (if (cdr c-state-cache)
278: ;; Ignore balanced paren. The next entry
279: ;; can't be another one.
280: (setq containing-sexp (car (cdr c-state-cache))
281: paren-state (cdr paren-state))
282: ;; If there is no surrounding open paren then
283: ;; put the last balanced pair back on paren-state.
284: (setq paren-state (cons containing-sexp paren-state)
285: containing-sexp nil)))
286: (setq lim (1+ containing-sexp))))
287: (setq lim (point-min)))
288:
289: ;; If we're in a parenthesis list then ',' delimits the
290: ;; "statements" rather than being an operator (with the
291: ;; exception of the "for" clause). This difference is
292: ;; typically only noticeable when statements are used in macro
293: ;; arglists.
294: (when (and containing-sexp
295: (eq (char-after containing-sexp) ?\())
296: (setq c-stmt-delim-chars c-stmt-delim-chars-with-comma))
297:
298: ;; cache char before and after indent point, and move point to
299: ;; the most likely position to perform the majority of tests
300: (goto-char indent-point)
301: (c-backward-syntactic-ws lim)
302: (setq before-ws-ip (point)
303: char-before-ip (char-before))
304: (goto-char indent-point)
305: (skip-chars-forward " \t")
306: (setq char-after-ip (char-after))
307:
308: ;; are we in a literal?
309: (setq literal (c-in-literal lim))
310:
311: ;; now figure out syntactic qualities of the current line
312: (cond
313:
314: ;; CASE 1: in a string.
315: ((eq literal 'string)
316: (c-add-syntax 'string (c-point 'bopl)))
317:
318: ;; CASE 2: in a C or C++ style comment.
319: ((and (memq literal '(c c++))
320: ;; This is a kludge for XEmacs where we use
321: ;; `buffer-syntactic-context', which doesn't correctly
322: ;; recognize "\*/" to end a block comment.
323: ;; `parse-partial-sexp' which is used by
324: ;; `c-literal-limits' will however do that in most
325: ;; versions, which results in that we get nil from
326: ;; `c-literal-limits' even when `c-in-literal' claims
327: ;; we're inside a comment.
328: (setq placeholder (c-literal-limits lim)))
329: (c-add-syntax literal (car placeholder)))
330:
331: ;; CASE 3: in a cpp preprocessor macro continuation.
332: ((and (save-excursion
333: (when (c-beginning-of-macro)
334: (setq macro-start (point))))
335: (/= macro-start (c-point 'boi))
336: (progn
337: (setq tmpsymbol 'cpp-macro-cont)
338: (or (not c-syntactic-indentation-in-macros)
339: (save-excursion
340: (goto-char macro-start)
341: ;; If at the beginning of the body of a #define
342: ;; directive then analyze as cpp-define-intro
343: ;; only. Go on with the syntactic analysis
344: ;; otherwise. in-macro-expr is set if we're in a
345: ;; cpp expression, i.e. before the #define body
346: ;; or anywhere in a non-#define directive.
347: (if (c-forward-to-cpp-define-body)
348: (let ((indent-boi (c-point 'boi indent-point)))
349: (setq in-macro-expr (> (point) indent-boi)
350: tmpsymbol 'cpp-define-intro)
351: (= (point) indent-boi))
352: (setq in-macro-expr t)
353: nil)))))
354: (c-add-syntax tmpsymbol macro-start)
355: (setq macro-start nil))
356:
357: ;; CASE 11: an else clause?
358: ((looking-at "else\\>[^_]")
359: (c-beginning-of-statement-1 containing-sexp)
360: (c-add-stmt-syntax 'else-clause nil t
361: containing-sexp paren-state))
362:
363: ;; CASE 12: while closure of a do/while construct?
364: ((and (looking-at "while\\>[^_]")
365: (save-excursion
366: (prog1 (eq (c-beginning-of-statement-1 containing-sexp)
367: 'beginning)
368: (setq placeholder (point)))))
369: (goto-char placeholder)
370: (c-add-stmt-syntax 'do-while-closure nil t
371: containing-sexp paren-state))
372:
373: ;; CASE 13: A catch or finally clause? This case is simpler
374: ;; than if-else and do-while, because a block is required
375: ;; after every try, catch and finally.
376: ((save-excursion
377: (and (cond ((c-major-mode-is 'c++-mode)
378: (looking-at "catch\\>[^_]"))
379: ((c-major-mode-is 'java-mode)
380: (looking-at "\\(catch\\|finally\\)\\>[^_]")))
381: (and (c-safe (c-backward-syntactic-ws)
382: (c-backward-sexp)
383: t)
384: (eq (char-after) ?{)
385: (c-safe (c-backward-syntactic-ws)
386: (c-backward-sexp)
387: t)
388: (if (eq (char-after) ?\()
389: (c-safe (c-backward-sexp) t)
390: t))
391: (looking-at "\\(try\\|catch\\)\\>[^_]")
392: (setq placeholder (point))))
393: (goto-char placeholder)
394: (c-add-stmt-syntax 'catch-clause nil t
395: containing-sexp paren-state))
396:
397: ;; CASE 18: A substatement we can recognize by keyword.
398: ((save-excursion
399: (and c-opt-block-stmt-key
400: (not (eq char-before-ip ?\;))
401: (not (c-at-vsemi-p before-ws-ip))
402: (not (memq char-after-ip '(?\) ?\] ?,)))
403: (or (not (eq char-before-ip ?}))
404: (c-looking-at-inexpr-block-backward c-state-cache))
405: (> (point)
406: (progn
407: ;; Ought to cache the result from the
408: ;; c-beginning-of-statement-1 calls here.
409: (setq placeholder (point))
410: (while (eq (setq step-type
411: (c-beginning-of-statement-1 lim))
412: 'label))
413: (if (eq step-type 'previous)
414: (goto-char placeholder)
415: (setq placeholder (point))
416: (if (and (eq step-type 'same)
417: (not (looking-at c-opt-block-stmt-key)))
418: ;; Step up to the containing statement if we
419: ;; stayed in the same one.
420: (let (step)
421: (while (eq
422: (setq step
423: (c-beginning-of-statement-1 lim))
424: 'label))
425: (if (eq step 'up)
426: (setq placeholder (point))
427: ;; There was no containing statement after all.
428: (goto-char placeholder)))))
429: placeholder))
430: (if (looking-at c-block-stmt-2-key)
431: ;; Require a parenthesis after these keywords.
432: ;; Necessary to catch e.g. synchronized in Java,
433: ;; which can be used both as statement and
434: ;; modifier.
435: (and (zerop (c-forward-token-2 1 nil))
436: (eq (char-after) ?\())
437: (looking-at c-opt-block-stmt-key))))
438:
439: (if (eq step-type 'up)
440: ;; CASE 18A: Simple substatement.
441: (progn
442: (goto-char placeholder)
443: (cond
444: ((eq char-after-ip ?{)
445: (c-add-stmt-syntax 'substatement-open nil nil
446: containing-sexp paren-state))
447: ((save-excursion
448: (goto-char indent-point)
449: (back-to-indentation)
450: (c-forward-label))
451: (c-add-stmt-syntax 'substatement-label nil nil
452: containing-sexp paren-state))
453: (t
454: (c-add-stmt-syntax 'substatement nil nil
455: containing-sexp paren-state))))
456:
457: ;; CASE 18B: Some other substatement. This is shared
458: ;; with case 10.
459: (c-guess-continued-construct indent-point
460: char-after-ip
461: placeholder
462: lim
463: paren-state)))
464:
465: ;; CASE 14: A case or default label
466: ((looking-at c-label-kwds-regexp)
467: (if containing-sexp
468: (progn
469: (goto-char containing-sexp)
470: (setq lim (c-most-enclosing-brace c-state-cache
471: containing-sexp))
472: (c-backward-to-block-anchor lim)
473: (c-add-stmt-syntax 'case-label nil t lim paren-state))
474: ;; Got a bogus label at the top level. In lack of better
475: ;; alternatives, anchor it on (point-min).
476: (c-add-syntax 'case-label (point-min))))
477:
478: ;; CASE 15: any other label
479: ((save-excursion
480: (back-to-indentation)
481: (and (not (looking-at c-syntactic-ws-start))
482: (c-forward-label)))
483: (cond (containing-decl-open
484: (setq placeholder (c-add-class-syntax 'inclass
485: containing-decl-open
486: containing-decl-start
487: containing-decl-kwd
488: paren-state))
489: ;; Append access-label with the same anchor point as
490: ;; inclass gets.
491: (c-append-syntax 'access-label placeholder))
492:
493: (containing-sexp
494: (goto-char containing-sexp)
495: (setq lim (c-most-enclosing-brace c-state-cache
496: containing-sexp))
497: (save-excursion
498: (setq tmpsymbol
499: (if (and (eq (c-beginning-of-statement-1 lim) 'up)
500: (looking-at "switch\\>[^_]"))
501: ;; If the surrounding statement is a switch then
502: ;; let's analyze all labels as switch labels, so
503: ;; that they get lined up consistently.
504: 'case-label
505: 'label)))
506: (c-backward-to-block-anchor lim)
507: (c-add-stmt-syntax tmpsymbol nil t lim paren-state))
508:
509: (t
510: ;; A label on the top level. Treat it as a class
511: ;; context. (point-min) is the closest we get to the
512: ;; class open brace.
513: (c-add-syntax 'access-label (point-min)))))
514:
515: ;; CASE 4: In-expression statement. C.f. cases 7B, 16A and
516: ;; 17E.
517: ((setq placeholder (c-looking-at-inexpr-block
518: (c-safe-position containing-sexp paren-state)
519: containing-sexp
520: ;; Have to turn on the heuristics after
521: ;; the point even though it doesn't work
522: ;; very well. C.f. test case class-16.pike.
523: t))
524: (setq tmpsymbol (assq (car placeholder)
525: '((inexpr-class . class-open)
526: (inexpr-statement . block-open))))
527: (if tmpsymbol
528: ;; It's a statement block or an anonymous class.
529: (setq tmpsymbol (cdr tmpsymbol))
530: ;; It's a Pike lambda. Check whether we are between the
531: ;; lambda keyword and the argument list or at the defun
532: ;; opener.
533: (setq tmpsymbol (if (eq char-after-ip ?{)
534: 'inline-open
535: 'lambda-intro-cont)))
536: (goto-char (cdr placeholder))
537: (back-to-indentation)
538: (c-add-stmt-syntax tmpsymbol nil t
539: (c-most-enclosing-brace c-state-cache (point))
540: paren-state)
541: (unless (eq (point) (cdr placeholder))
542: (c-add-syntax (car placeholder))))
543:
544: ;; CASE 5: Line is inside a declaration level block or at top level.
545: ((or containing-decl-open (null containing-sexp))
546: (cond
547:
548: ;; CASE 5A: we are looking at a defun, brace list, class,
549: ;; or inline-inclass method opening brace
550: ((setq special-brace-list
551: (or (and c-special-brace-lists
552: (c-looking-at-special-brace-list))
553: (eq char-after-ip ?{)))
554: (cond
555:
556: ;; CASE 5A.1: Non-class declaration block open.
557: ((save-excursion
558: (let (tmp)
559: (and (eq char-after-ip ?{)
560: (setq tmp (c-looking-at-decl-block containing-sexp t))
561: (progn
562: (setq placeholder (point))
563: (goto-char tmp)
564: (looking-at c-symbol-key))
565: (c-keyword-member
566: (c-keyword-sym (setq keyword (match-string 0)))
567: 'c-other-block-decl-kwds))))
568: (goto-char placeholder)
569: (c-add-stmt-syntax
570: (if (string-equal keyword "extern")
571: ;; Special case for extern-lang-open.
572: 'extern-lang-open
573: (intern (concat keyword "-open")))
574: nil t containing-sexp paren-state))
575:
576: ;; CASE 5A.2: we are looking at a class opening brace
577: ((save-excursion
578: (goto-char indent-point)
579: (skip-chars-forward " \t")
580: (and (eq (char-after) ?{)
581: (c-looking-at-decl-block containing-sexp t)
582: (setq placeholder (point))))
583: (c-add-syntax 'class-open placeholder))
584:
585: ;; CASE 5A.3: brace list open
586: ((save-excursion
587: (c-beginning-of-decl-1 lim)
588: (while (looking-at c-specifier-key)
589: (goto-char (match-end 1))
590: (c-forward-syntactic-ws indent-point))
591: (setq placeholder (c-point 'boi))
592: (or (consp special-brace-list)
593: (and (or (save-excursion
594: (goto-char indent-point)
595: (setq tmpsymbol nil)
596: (while (and (> (point) placeholder)
597: (zerop (c-backward-token-2 1 t))
598: (/= (char-after) ?=))
599: (and c-opt-inexpr-brace-list-key
600: (not tmpsymbol)
601: (looking-at c-opt-inexpr-brace-list-key)
602: (setq tmpsymbol 'topmost-intro-cont)))
603: (eq (char-after) ?=))
604: (looking-at c-brace-list-key))
605: (save-excursion
606: (while (and (< (point) indent-point)
607: (zerop (c-forward-token-2 1 t))
608: (not (memq (char-after) '(?\; ?\()))))
609: (not (memq (char-after) '(?\; ?\()))
610: ))))
611: (if (and (not c-auto-newline-analysis)
612: (c-major-mode-is 'java-mode)
613: (eq tmpsymbol 'topmost-intro-cont))
614: ;; We're in Java and have found that the open brace
615: ;; belongs to a "new Foo[]" initialization list,
616: ;; which means the brace list is part of an
617: ;; expression and not a top level definition. We
618: ;; therefore treat it as any topmost continuation
619: ;; even though the semantically correct symbol still
620: ;; is brace-list-open, on the same grounds as in
621: ;; case B.2.
622: (progn
623: (c-beginning-of-statement-1 lim)
624: (c-add-syntax 'topmost-intro-cont (c-point 'boi)))
625: (c-add-syntax 'brace-list-open placeholder)))
626:
627: ;; CASE 5A.4: inline defun open
628: ((and containing-decl-open
629: (not (c-keyword-member containing-decl-kwd
630: 'c-other-block-decl-kwds)))
631: (c-add-syntax 'inline-open)
632: (c-add-class-syntax 'inclass
633: containing-decl-open
634: containing-decl-start
635: containing-decl-kwd
636: paren-state))
637:
638: ;; CASE 5A.5: ordinary defun open
639: (t
640: (save-excursion
641: (c-beginning-of-decl-1 lim)
642: (while (looking-at c-specifier-key)
643: (goto-char (match-end 1))
644: (c-forward-syntactic-ws indent-point))
645: (c-add-syntax 'defun-open (c-point 'boi))
646: ;; Bogus to use bol here, but it's the legacy. (Resolved,
647: ;; 2007-11-09)
648: ))))
649:
650: ;; CASE 5B: After a function header but before the body (or
651: ;; the ending semicolon if there's no body).
652: ((save-excursion
653: (when (setq placeholder (c-just-after-func-arglist-p lim))
654: (setq tmp-pos (point))))
655: (cond
656:
657: ;; CASE 5B.1: Member init list.
658: ((eq (char-after tmp-pos) ?:)
659: (if (or (> tmp-pos indent-point)
660: (= (c-point 'bosws) (1+ tmp-pos)))
661: (progn
662: ;; There is no preceding member init clause.
663: ;; Indent relative to the beginning of indentation
664: ;; for the topmost-intro line that contains the
665: ;; prototype's open paren.
666: (goto-char placeholder)
667: (c-add-syntax 'member-init-intro (c-point 'boi)))
668: ;; Indent relative to the first member init clause.
669: (goto-char (1+ tmp-pos))
670: (c-forward-syntactic-ws)
671: (c-add-syntax 'member-init-cont (point))))
672:
673: ;; CASE 5B.2: K&R arg decl intro
674: ((and c-recognize-knr-p
675: (c-in-knr-argdecl lim))
676: (c-beginning-of-statement-1 lim)
677: (c-add-syntax 'knr-argdecl-intro (c-point 'boi))
678: (if containing-decl-open
679: (c-add-class-syntax 'inclass
680: containing-decl-open
681: containing-decl-start
682: containing-decl-kwd
683: paren-state)))
684:
685: ;; CASE 5B.4: Nether region after a C++ or Java func
686: ;; decl, which could include a `throws' declaration.
687: (t
688: (c-beginning-of-statement-1 lim)
689: (c-add-syntax 'func-decl-cont (c-point 'boi))
690: )))
691:
692: ;; CASE 5C: inheritance line. could be first inheritance
693: ;; line, or continuation of a multiple inheritance
694: ((or (and (c-major-mode-is 'c++-mode)
695: (progn
696: (when (eq char-after-ip ?,)
697: (skip-chars-forward " \t")
698: (forward-char))
699: (looking-at c-opt-postfix-decl-spec-key)))
700: (and (or (eq char-before-ip ?:)
701: ;; watch out for scope operator
702: (save-excursion
703: (and (eq char-after-ip ?:)
704: (c-safe (forward-char 1) t)
705: (not (eq (char-after) ?:))
706: )))
707: (save-excursion
708: (c-backward-syntactic-ws lim)
709: (if (eq char-before-ip ?:)
710: (progn
711: (forward-char -1)
712: (c-backward-syntactic-ws lim)))
713: (back-to-indentation)
714: (looking-at c-class-key)))
715: ;; for Java
716: (and (c-major-mode-is 'java-mode)
717: (let ((fence (save-excursion
718: (c-beginning-of-statement-1 lim)
719: (point)))
720: cont done)
721: (save-excursion
722: (while (not done)
723: (cond ((looking-at c-opt-postfix-decl-spec-key)
724: (setq injava-inher (cons cont (point))
725: done t))
726: ((or (not (c-safe (c-forward-sexp -1) t))
727: (<= (point) fence))
728: (setq done t))
729: )
730: (setq cont t)))
731: injava-inher)
732: (not (c-crosses-statement-barrier-p (cdr injava-inher)
733: (point)))
734: ))
735: (cond
736:
737: ;; CASE 5C.1: non-hanging colon on an inher intro
738: ((eq char-after-ip ?:)
739: (c-beginning-of-statement-1 lim)
740: (c-add-syntax 'inher-intro (c-point 'boi))
741: ;; don't add inclass symbol since relative point already
742: ;; contains any class offset
743: )
744:
745: ;; CASE 5C.2: hanging colon on an inher intro
746: ((eq char-before-ip ?:)
747: (c-beginning-of-statement-1 lim)
748: (c-add-syntax 'inher-intro (c-point 'boi))
749: (if containing-decl-open
750: (c-add-class-syntax 'inclass
751: containing-decl-open
752: containing-decl-start
753: containing-decl-kwd
754: paren-state)))
755:
756: ;; CASE 5C.3: in a Java implements/extends
757: (injava-inher
758: (let ((where (cdr injava-inher))
759: (cont (car injava-inher)))
760: (goto-char where)
761: (cond ((looking-at "throws\\>[^_]")
762: (c-add-syntax 'func-decl-cont
763: (progn (c-beginning-of-statement-1 lim)
764: (c-point 'boi))))
765: (cont (c-add-syntax 'inher-cont where))
766: (t (c-add-syntax 'inher-intro
767: (progn (goto-char (cdr injava-inher))
768: (c-beginning-of-statement-1 lim)
769: (point))))
770: )))
771:
772: ;; CASE 5C.4: a continued inheritance line
773: (t
774: (c-beginning-of-inheritance-list lim)
775: (c-add-syntax 'inher-cont (point))
776: ;; don't add inclass symbol since relative point already
777: ;; contains any class offset
778: )))
779:
780: ;; CASE 5D: this could be a top-level initialization, a
781: ;; member init list continuation, or a template argument
782: ;; list continuation.
783: ((save-excursion
784: ;; Note: We use the fact that lim is always after any
785: ;; preceding brace sexp.
786: (if c-recognize-<>-arglists
787: (while (and
788: (progn
789: (c-syntactic-skip-backward "^;$,=<>" lim t)
790: (> (point) lim))
791: (or
792: (when c-overloadable-operators-regexp
793: (when (setq placeholder (c-after-special-operator-id lim))
794: (goto-char placeholder)
795: t))
796: (cond
797: ((eq (char-before) ?>)
798: (or (c-backward-<>-arglist nil lim)
799: (backward-char))
800: t)
801: ((eq (char-before) ?<)
802: (backward-char)
803: (if (save-excursion
804: (c-forward-<>-arglist nil))
805: (progn (forward-char)
806: nil)
807: t))
808: (t nil)))))
809: ;; NB: No c-after-special-operator-id stuff in this
810: ;; clause - we assume only C++ needs it.
811: (c-syntactic-skip-backward "^;$,=" lim t))
812: (memq (char-before) '(?, ?= ?<)))
813: (cond
814:
815: ;; CASE 5D.3: perhaps a template list continuation?
816: ((and (c-major-mode-is 'c++-mode)
817: (save-excursion
818: (save-restriction
819: (c-with-syntax-table c++-template-syntax-table
820: (goto-char indent-point)
821: (setq placeholder (c-up-list-backward))
822: (and placeholder
823: (eq (char-after placeholder) ?<))))))
824: (c-with-syntax-table c++-template-syntax-table
825: (goto-char placeholder)
826: (c-beginning-of-statement-1 lim t)
827: (if (save-excursion
828: (c-backward-syntactic-ws lim)
829: (eq (char-before) ?<))
830: ;; In a nested template arglist.
831: (progn
832: (goto-char placeholder)
833: (c-syntactic-skip-backward "^,;" lim t)
834: (c-forward-syntactic-ws))
835: (back-to-indentation)))
836: ;; FIXME: Should use c-add-stmt-syntax, but it's not yet
837: ;; template aware.
838: (c-add-syntax 'template-args-cont (point) placeholder))
839:
840: ;; CASE 5D.4: perhaps a multiple inheritance line?
841: ((and (c-major-mode-is 'c++-mode)
842: (save-excursion
843: (c-beginning-of-statement-1 lim)
844: (setq placeholder (point))
845: (if (looking-at "static\\>[^_]")
846: (c-forward-token-2 1 nil indent-point))
847: (and (looking-at c-class-key)
848: (zerop (c-forward-token-2 2 nil indent-point))
849: (if (eq (char-after) ?<)
850: (c-with-syntax-table c++-template-syntax-table
851: (zerop (c-forward-token-2 1 t indent-point)))
852: t)
853: (eq (char-after) ?:))))
854: (goto-char placeholder)
855: (c-add-syntax 'inher-cont (c-point 'boi)))
856:
857: ;; CASE 5D.5: Continuation of the "expression part" of a
858: ;; top level construct. Or, perhaps, an unrecognized construct.
859: (t
860: (while (and (setq placeholder (point))
861: (eq (car (c-beginning-of-decl-1 containing-sexp))
862: 'same)
863: (save-excursion
864: (c-backward-syntactic-ws)
865: (eq (char-before) ?}))
866: (< (point) placeholder)))
867: (c-add-stmt-syntax
868: (cond
869: ((eq (point) placeholder) 'statement) ; unrecognized construct
870: ;; A preceding comma at the top level means that a
871: ;; new variable declaration starts here. Use
872: ;; topmost-intro-cont for it, for consistency with
873: ;; the first variable declaration. C.f. case 5N.
874: ((eq char-before-ip ?,) 'topmost-intro-cont)
875: (t 'statement-cont))
876: nil nil containing-sexp paren-state))
877: ))
878:
879: ;; CASE 5F: Close of a non-class declaration level block.
880: ((and (eq char-after-ip ?})
881: (c-keyword-member containing-decl-kwd
882: 'c-other-block-decl-kwds))
883: ;; This is inconsistent: Should use `containing-decl-open'
884: ;; here if it's at boi, like in case 5J.
885: (goto-char containing-decl-start)
886: (c-add-stmt-syntax
887: (if (string-equal (symbol-name containing-decl-kwd) "extern")
888: ;; Special case for compatibility with the
889: ;; extern-lang syntactic symbols.
890: 'extern-lang-close
891: (intern (concat (symbol-name containing-decl-kwd)
892: "-close")))
893: nil t
894: (c-most-enclosing-brace paren-state (point))
895: paren-state))
896:
897: ;; CASE 5G: we are looking at the brace which closes the
898: ;; enclosing nested class decl
899: ((and containing-sexp
900: (eq char-after-ip ?})
901: (eq containing-decl-open containing-sexp))
902: (c-add-class-syntax 'class-close
903: containing-decl-open
904: containing-decl-start
905: containing-decl-kwd
906: paren-state))
907:
908: ;; CASE 5H: we could be looking at subsequent knr-argdecls
909: ((and c-recognize-knr-p
910: (not containing-sexp) ; can't be knr inside braces.
911: (not (eq char-before-ip ?}))
912: (save-excursion
913: (setq placeholder (cdr (c-beginning-of-decl-1 lim)))
914: (and placeholder
915: ;; Do an extra check to avoid tripping up on
916: ;; statements that occur in invalid contexts
917: ;; (e.g. in macro bodies where we don't really
918: ;; know the context of what we're looking at).
919: (not (and c-opt-block-stmt-key
920: (looking-at c-opt-block-stmt-key)))))
921: (< placeholder indent-point))
922: (goto-char placeholder)
923: (c-add-syntax 'knr-argdecl (point)))
924:
925: ;; CASE 5I: ObjC method definition.
926: ((and c-opt-method-key
927: (looking-at c-opt-method-key))
928: (c-beginning-of-statement-1 nil t)
929: (if (= (point) indent-point)
930: ;; Handle the case when it's the first (non-comment)
931: ;; thing in the buffer. Can't look for a 'same return
932: ;; value from cbos1 since ObjC directives currently
933: ;; aren't recognized fully, so that we get 'same
934: ;; instead of 'previous if it moved over a preceding
935: ;; directive.
936: (goto-char (point-min)))
937: (c-add-syntax 'objc-method-intro (c-point 'boi)))
938:
939: ;; CASE 5P: AWK pattern or function or continuation
940: ;; thereof.
941: ((c-major-mode-is 'awk-mode)
942: (setq placeholder (point))
943: (c-add-stmt-syntax
944: (if (and (eq (c-beginning-of-statement-1) 'same)
945: (/= (point) placeholder))
946: 'topmost-intro-cont
947: 'topmost-intro)
948: nil nil
949: containing-sexp paren-state))
950:
951: ;; CASE 5N: At a variable declaration that follows a class
952: ;; definition or some other block declaration that doesn't
953: ;; end at the closing '}'. C.f. case 5D.5.
954: ((progn
955: (c-backward-syntactic-ws lim)
956: (and (eq (char-before) ?})
957: (save-excursion
958: (let ((start (point)))
959: (if (and c-state-cache
960: (consp (car c-state-cache))
961: (eq (cdar c-state-cache) (point)))
962: ;; Speed up the backward search a bit.
963: (goto-char (caar c-state-cache)))
964: (c-beginning-of-decl-1 containing-sexp)
965: (setq placeholder (point))
966: (if (= start (point))
967: ;; The '}' is unbalanced.
968: nil
969: (c-end-of-decl-1)
970: (>= (point) indent-point))))))
971: (goto-char placeholder)
972: (c-add-stmt-syntax 'topmost-intro-cont nil nil
973: containing-sexp paren-state))
974:
975: ;; NOTE: The point is at the end of the previous token here.
976:
977: ;; CASE 5J: we are at the topmost level, make
978: ;; sure we skip back past any access specifiers
979: ((and
980: ;; A macro continuation line is never at top level.
981: (not (and macro-start
982: (> indent-point macro-start)))
983: (save-excursion
984: (setq placeholder (point))
985: (or (memq char-before-ip '(?\; ?$ ?{ ?} nil))
986: (c-at-vsemi-p before-ws-ip)
987: (when (and (eq char-before-ip ?:)
988: (eq (c-beginning-of-statement-1 lim)
989: 'label))
990: (c-backward-syntactic-ws lim)
991: (setq placeholder (point)))
992: (and (c-major-mode-is 'objc-mode)
993: (catch 'not-in-directive
994: (c-beginning-of-statement-1 lim)
995: (setq placeholder (point))
996: (while (and (c-forward-objc-directive)
997: (< (point) indent-point))
998: (c-forward-syntactic-ws)
999: (if (>= (point) indent-point)
1000: (throw 'not-in-directive t))
1001: (setq placeholder (point)))
1002: nil)))))
1003: ;; For historic reasons we anchor at bol of the last
1004: ;; line of the previous declaration. That's clearly
1005: ;; highly bogus and useless, and it makes our lives hard
1006: ;; to remain compatible. :P
1007: (goto-char placeholder)
1008: (c-add-syntax 'topmost-intro (c-point 'bol))
1009: (if containing-decl-open
1010: (if (c-keyword-member containing-decl-kwd
1011: 'c-other-block-decl-kwds)
1012: (progn
1013: (goto-char (c-brace-anchor-point containing-decl-open))
1014: (c-add-stmt-syntax
1015: (if (string-equal (symbol-name containing-decl-kwd)
1016: "extern")
1017: ;; Special case for compatibility with the
1018: ;; extern-lang syntactic symbols.
1019: 'inextern-lang
1020: (intern (concat "in"
1021: (symbol-name containing-decl-kwd))))
1022: nil t
1023: (c-most-enclosing-brace paren-state (point))
1024: paren-state))
1025: (c-add-class-syntax 'inclass
1026: containing-decl-open
1027: containing-decl-start
1028: containing-decl-kwd
1029: paren-state)))
1030: (when (and c-syntactic-indentation-in-macros
1031: macro-start
1032: (/= macro-start (c-point 'boi indent-point)))
1033: (c-add-syntax 'cpp-define-intro)
1034: (setq macro-start nil)))
1035:
1036: ;; CASE 5K: we are at an ObjC method definition
1037: ;; continuation line.
1038: ((and c-opt-method-key
1039: (save-excursion
1040: (c-beginning-of-statement-1 lim)
1041: (beginning-of-line)
1042: (when (looking-at c-opt-method-key)
1043: (setq placeholder (point)))))
1044: (c-add-syntax 'objc-method-args-cont placeholder))
1045:
1046: ;; CASE 5L: we are at the first argument of a template
1047: ;; arglist that begins on the previous line.
1048: ((and c-recognize-<>-arglists
1049: (eq (char-before) ?<)
1050: (setq placeholder (1- (point)))
1051: (not (and c-overloadable-operators-regexp
1052: (c-after-special-operator-id lim))))
1053: (c-beginning-of-statement-1 (c-safe-position (point) paren-state))
1054: (c-add-syntax 'template-args-cont (c-point 'boi) placeholder))
1055:
1056: ;; CASE 5Q: we are at a statement within a macro.
1057: (macro-start
1058: (c-beginning-of-statement-1 containing-sexp)
1059: (c-add-stmt-syntax 'statement nil t containing-sexp paren-state))
1060:
1061: ;; CASE 5M: we are at a topmost continuation line
1062: (t
1063: (c-beginning-of-statement-1 (c-safe-position (point) paren-state))
1064: (when (c-major-mode-is 'objc-mode)
1065: (setq placeholder (point))
1066: (while (and (c-forward-objc-directive)
1067: (< (point) indent-point))
1068: (c-forward-syntactic-ws)
1069: (setq placeholder (point)))
1070: (goto-char placeholder))
1071: (c-add-syntax 'topmost-intro-cont (c-point 'boi)))
1072: ))
1073:
1074: ;; (CASE 6 has been removed.)
1075:
1076: ;; CASE 19: line is an expression, not a statement, and is directly
1077: ;; contained by a template delimiter. Most likely, we are in a
1078: ;; template arglist within a statement. This case is based on CASE
1079: ;; 7. At some point in the future, we may wish to create more
1080: ;; syntactic symbols such as `template-intro',
1081: ;; `template-cont-nonempty', etc., and distinguish between them as we
1082: ;; do for `arglist-intro' etc. (2009-12-07).
1083: ((and c-recognize-<>-arglists
1084: (setq containing-< (c-up-list-backward indent-point containing-sexp))
1085: (eq (char-after containing-<) ?\<))
1086: (setq placeholder (c-point 'boi containing-<))
1087: (goto-char containing-sexp) ; Most nested Lbrace/Lparen (but not
1088: ; '<') before indent-point.
1089: (if (>= (point) placeholder)
1090: (progn
1091: (forward-char)
1092: (skip-chars-forward " \t"))
1093: (goto-char placeholder))
1094: (c-add-stmt-syntax 'template-args-cont (list containing-<) t
1095: (c-most-enclosing-brace c-state-cache (point))
1096: paren-state))
1097:
1098:
1099: ;; CASE 7: line is an expression, not a statement. Most
1100: ;; likely we are either in a function prototype or a function
1101: ;; call argument list, or a template argument list.
1102: ((not (or (and c-special-brace-lists
1103: (save-excursion
1104: (goto-char containing-sexp)
1105: (c-looking-at-special-brace-list)))
1106: (eq (char-after containing-sexp) ?{)
1107: (eq (char-after containing-sexp) ?<)))
1108: (cond
1109:
1110: ;; CASE 7A: we are looking at the arglist closing paren.
1111: ;; C.f. case 7F.
1112: ((memq char-after-ip '(?\) ?\]))
1113: (goto-char containing-sexp)
1114: (setq placeholder (c-point 'boi))
1115: (if (and (c-safe (backward-up-list 1) t)
1116: (>= (point) placeholder))
1117: (progn
1118: (forward-char)
1119: (skip-chars-forward " \t"))
1120: (goto-char placeholder))
1121: (c-add-stmt-syntax 'arglist-close (list containing-sexp) t
1122: (c-most-enclosing-brace paren-state (point))
1123: paren-state))
1124:
1125: ;; CASE 7B: Looking at the opening brace of an
1126: ;; in-expression block or brace list. C.f. cases 4, 16A
1127: ;; and 17E.
1128: ((and (eq char-after-ip ?{)
1129: (progn
1130: (setq placeholder (c-inside-bracelist-p (point)
1131: paren-state))
1132: (if placeholder
1133: (setq tmpsymbol '(brace-list-open . inexpr-class))
1134: (setq tmpsymbol '(block-open . inexpr-statement)
1135: placeholder
1136: (cdr-safe (c-looking-at-inexpr-block
1137: (c-safe-position containing-sexp
1138: paren-state)
1139: containing-sexp)))
1140: ;; placeholder is nil if it's a block directly in
1141: ;; a function arglist. That makes us skip out of
1142: ;; this case.
1143: )))
1144: (goto-char placeholder)
1145: (back-to-indentation)
1146: (c-add-stmt-syntax (car tmpsymbol) nil t
1147: (c-most-enclosing-brace paren-state (point))
1148: paren-state)
1149: (if (/= (point) placeholder)
1150: (c-add-syntax (cdr tmpsymbol))))
1151:
1152: ;; CASE 7C: we are looking at the first argument in an empty
1153: ;; argument list. Use arglist-close if we're actually
1154: ;; looking at a close paren or bracket.
1155: ((memq char-before-ip '(?\( ?\[))
1156: (goto-char containing-sexp)
1157: (setq placeholder (c-point 'boi))
1158: (if (and (c-safe (backward-up-list 1) t)
1159: (>= (point) placeholder))
1160: (progn
1161: (forward-char)
1162: (skip-chars-forward " \t"))
1163: (goto-char placeholder))
1164: (c-add-stmt-syntax 'arglist-intro (list containing-sexp) t
1165: (c-most-enclosing-brace paren-state (point))
1166: paren-state))
1167:
1168: ;; CASE 7D: we are inside a conditional test clause. treat
1169: ;; these things as statements
1170: ((progn
1171: (goto-char containing-sexp)
1172: (and (c-safe (c-forward-sexp -1) t)
1173: (looking-at "\\<for\\>[^_]")))
1174: (goto-char (1+ containing-sexp))
1175: (c-forward-syntactic-ws indent-point)
1176: (if (eq char-before-ip ?\;)
1177: (c-add-syntax 'statement (point))
1178: (c-add-syntax 'statement-cont (point))
1179: ))
1180:
1181: ;; CASE 7E: maybe a continued ObjC method call. This is the
1182: ;; case when we are inside a [] bracketed exp, and what
1183: ;; precede the opening bracket is not an identifier.
1184: ((and c-opt-method-key
1185: (eq (char-after containing-sexp) ?\[)
1186: (progn
1187: (goto-char (1- containing-sexp))
1188: (c-backward-syntactic-ws (c-point 'bod))
1189: (if (not (looking-at c-symbol-key))
1190: (c-add-syntax 'objc-method-call-cont containing-sexp))
1191: )))
1192:
1193: ;; CASE 7F: we are looking at an arglist continuation line,
1194: ;; but the preceding argument is on the same line as the
1195: ;; opening paren. This case includes multi-line
1196: ;; mathematical paren groupings, but we could be on a
1197: ;; for-list continuation line. C.f. case 7A.
1198: ((progn
1199: (goto-char (1+ containing-sexp))
1200: (< (save-excursion
1201: (c-forward-syntactic-ws)
1202: (point))
1203: (c-point 'bonl)))
1204: (goto-char containing-sexp) ; paren opening the arglist
1205: (setq placeholder (c-point 'boi))
1206: (if (and (c-safe (backward-up-list 1) t)
1207: (>= (point) placeholder))
1208: (progn
1209: (forward-char)
1210: (skip-chars-forward " \t"))
1211: (goto-char placeholder))
1212: (c-add-stmt-syntax 'arglist-cont-nonempty (list containing-sexp) t
1213: (c-most-enclosing-brace c-state-cache (point))
1214: paren-state))
1215:
1216: ;; CASE 7G: we are looking at just a normal arglist
1217: ;; continuation line
1218: (t (c-forward-syntactic-ws indent-point)
1219: (c-add-syntax 'arglist-cont (c-point 'boi)))
1220: ))
1221:
1222: ;; CASE 8: func-local multi-inheritance line
1223: ((and (c-major-mode-is 'c++-mode)
1224: (save-excursion
1225: (goto-char indent-point)
1226: (skip-chars-forward " \t")
1227: (looking-at c-opt-postfix-decl-spec-key)))
1228: (goto-char indent-point)
1229: (skip-chars-forward " \t")
1230: (cond
1231:
1232: ;; CASE 8A: non-hanging colon on an inher intro
1233: ((eq char-after-ip ?:)
1234: (c-backward-syntactic-ws lim)
1235: (c-add-syntax 'inher-intro (c-point 'boi)))
1236:
1237: ;; CASE 8B: hanging colon on an inher intro
1238: ((eq char-before-ip ?:)
1239: (c-add-syntax 'inher-intro (c-point 'boi)))
1240:
1241: ;; CASE 8C: a continued inheritance line
1242: (t
1243: (c-beginning-of-inheritance-list lim)
1244: (c-add-syntax 'inher-cont (point))
1245: )))
1246:
1247: ;; CASE 9: we are inside a brace-list
1248: ((and (not (c-major-mode-is 'awk-mode)) ; Maybe this isn't needed (ACM, 2002/3/29)
1249: (setq special-brace-list
1250: (or (and c-special-brace-lists ;;;; ALWAYS NIL FOR AWK!!
1251: (save-excursion
1252: (goto-char containing-sexp)
1253: (c-looking-at-special-brace-list)))
1254: (c-inside-bracelist-p containing-sexp paren-state))))
1255: (cond
1256:
1257: ;; CASE 9A: In the middle of a special brace list opener.
1258: ((and (consp special-brace-list)
1259: (save-excursion
1260: (goto-char containing-sexp)
1261: (eq (char-after) ?\())
1262: (eq char-after-ip (car (cdr special-brace-list))))
1263: (goto-char (car (car special-brace-list)))
1264: (skip-chars-backward " \t")
1265: (if (and (bolp)
1266: (assoc 'statement-cont
1267: (setq placeholder (c-guess-basic-syntax))))
1268: (setq c-syntactic-context placeholder)
1269: (c-beginning-of-statement-1
1270: (c-safe-position (1- containing-sexp) paren-state))
1271: (c-forward-token-2 0)
1272: (while (looking-at c-specifier-key)
1273: (goto-char (match-end 1))
1274: (c-forward-syntactic-ws))
1275: (c-add-syntax 'brace-list-open (c-point 'boi))))
1276:
1277: ;; CASE 9B: brace-list-close brace
1278: ((if (consp special-brace-list)
1279: ;; Check special brace list closer.
1280: (progn
1281: (goto-char (car (car special-brace-list)))
1282: (save-excursion
1283: (goto-char indent-point)
1284: (back-to-indentation)
1285: (or
1286: ;; We were between the special close char and the `)'.
1287: (and (eq (char-after) ?\))
1288: (eq (1+ (point)) (cdr (car special-brace-list))))
1289: ;; We were before the special close char.
1290: (and (eq (char-after) (cdr (cdr special-brace-list)))
1291: (zerop (c-forward-token-2))
1292: (eq (1+ (point)) (cdr (car special-brace-list)))))))
1293: ;; Normal brace list check.
1294: (and (eq char-after-ip ?})
1295: (c-safe (goto-char (c-up-list-backward (point))) t)
1296: (= (point) containing-sexp)))
1297: (if (eq (point) (c-point 'boi))
1298: (c-add-syntax 'brace-list-close (point))
1299: (setq lim (c-most-enclosing-brace c-state-cache (point)))
1300: (c-beginning-of-statement-1 lim)
1301: (c-add-stmt-syntax 'brace-list-close nil t lim paren-state)))
1302:
1303: (t
1304: ;; Prepare for the rest of the cases below by going to the
1305: ;; token following the opening brace
1306: (if (consp special-brace-list)
1307: (progn
1308: (goto-char (car (car special-brace-list)))
1309: (c-forward-token-2 1 nil indent-point))
1310: (goto-char containing-sexp))
1311: (forward-char)
1312: (let ((start (point)))
1313: (c-forward-syntactic-ws indent-point)
1314: (goto-char (max start (c-point 'bol))))
1315: (c-skip-ws-forward indent-point)
1316: (cond
1317:
1318: ;; CASE 9C: we're looking at the first line in a brace-list
1319: ((= (point) indent-point)
1320: (if (consp special-brace-list)
1321: (goto-char (car (car special-brace-list)))
1322: (goto-char containing-sexp))
1323: (if (eq (point) (c-point 'boi))
1324: (c-add-syntax 'brace-list-intro (point))
1325: (setq lim (c-most-enclosing-brace c-state-cache (point)))
1326: (c-beginning-of-statement-1 lim)
1327: (c-add-stmt-syntax 'brace-list-intro nil t lim paren-state)))
1328:
1329: ;; CASE 9D: this is just a later brace-list-entry or
1330: ;; brace-entry-open
1331: (t (if (or (eq char-after-ip ?{)
1332: (and c-special-brace-lists
1333: (save-excursion
1334: (goto-char indent-point)
1335: (c-forward-syntactic-ws (c-point 'eol))
1336: (c-looking-at-special-brace-list (point)))))
1337: (c-add-syntax 'brace-entry-open (point))
1338: (c-add-syntax 'brace-list-entry (point))
1339: ))
1340: ))))
1341:
1342: ;; CASE 10: A continued statement or top level construct.
1343: ((and (not (memq char-before-ip '(?\; ?:)))
1344: (not (c-at-vsemi-p before-ws-ip))
1345: (or (not (eq char-before-ip ?}))
1346: (c-looking-at-inexpr-block-backward c-state-cache))
1347: (> (point)
1348: (save-excursion
1349: (c-beginning-of-statement-1 containing-sexp)
1350: (setq placeholder (point))))
1351: (/= placeholder containing-sexp))
1352: ;; This is shared with case 18.
1353: (c-guess-continued-construct indent-point
1354: char-after-ip
1355: placeholder
1356: containing-sexp
1357: paren-state))
1358:
1359: ;; CASE 16: block close brace, possibly closing the defun or
1360: ;; the class
1361: ((eq char-after-ip ?})
1362: ;; From here on we have the next containing sexp in lim.
1363: (setq lim (c-most-enclosing-brace paren-state))
1364: (goto-char containing-sexp)
1365: (cond
1366:
1367: ;; CASE 16E: Closing a statement block? This catches
1368: ;; cases where it's preceded by a statement keyword,
1369: ;; which works even when used in an "invalid" context,
1370: ;; e.g. a macro argument.
1371: ((c-after-conditional)
1372: (c-backward-to-block-anchor lim)
1373: (c-add-stmt-syntax 'block-close nil t lim paren-state))
1374:
1375: ;; CASE 16A: closing a lambda defun or an in-expression
1376: ;; block? C.f. cases 4, 7B and 17E.
1377: ((setq placeholder (c-looking-at-inexpr-block
1378: (c-safe-position containing-sexp paren-state)
1379: nil))
1380: (setq tmpsymbol (if (eq (car placeholder) 'inlambda)
1381: 'inline-close
1382: 'block-close))
1383: (goto-char containing-sexp)
1384: (back-to-indentation)
1385: (if (= containing-sexp (point))
1386: (c-add-syntax tmpsymbol (point))
1387: (goto-char (cdr placeholder))
1388: (back-to-indentation)
1389: (c-add-stmt-syntax tmpsymbol nil t
1390: (c-most-enclosing-brace paren-state (point))
1391: paren-state)
1392: (if (/= (point) (cdr placeholder))
1393: (c-add-syntax (car placeholder)))))
1394:
1395: ;; CASE 16B: does this close an inline or a function in
1396: ;; a non-class declaration level block?
1397: ((save-excursion
1398: (and lim
1399: (progn
1400: (goto-char lim)
1401: (c-looking-at-decl-block
1402: (c-most-enclosing-brace paren-state lim)
1403: nil))
1404: (setq placeholder (point))))
1405: (c-backward-to-decl-anchor lim)
1406: (back-to-indentation)
1407: (if (save-excursion
1408: (goto-char placeholder)
1409: (looking-at c-other-decl-block-key))
1410: (c-add-syntax 'defun-close (point))
1411: (c-add-syntax 'inline-close (point))))
1412:
1413: ;; CASE 16F: Can be a defun-close of a function declared
1414: ;; in a statement block, e.g. in Pike or when using gcc
1415: ;; extensions, but watch out for macros followed by
1416: ;; blocks. Let it through to be handled below.
1417: ;; C.f. cases B.3 and 17G.
1418: ((save-excursion
1419: (and (not (c-at-statement-start-p))
1420: (eq (c-beginning-of-statement-1 lim nil nil t) 'same)
1421: (setq placeholder (point))
1422: (let ((c-recognize-typeless-decls nil))
1423: ;; Turn off recognition of constructs that
1424: ;; lacks a type in this case, since that's more
1425: ;; likely to be a macro followed by a block.
1426: (c-forward-decl-or-cast-1 (c-point 'bosws) nil nil))))
1427: (back-to-indentation)
1428: (if (/= (point) containing-sexp)
1429: (goto-char placeholder))
1430: (c-add-stmt-syntax 'defun-close nil t lim paren-state))
1431:
1432: ;; CASE 16C: If there is an enclosing brace then this is
1433: ;; a block close since defun closes inside declaration
1434: ;; level blocks have been handled above.
1435: (lim
1436: ;; If the block is preceded by a case/switch label on
1437: ;; the same line, we anchor at the first preceding label
1438: ;; at boi. The default handling in c-add-stmt-syntax
1439: ;; really fixes it better, but we do like this to keep
1440: ;; the indentation compatible with version 5.28 and
1441: ;; earlier. C.f. case 17H.
1442: (while (and (/= (setq placeholder (point)) (c-point 'boi))
1443: (eq (c-beginning-of-statement-1 lim) 'label)))
1444: (goto-char placeholder)
1445: (if (looking-at c-label-kwds-regexp)
1446: (c-add-syntax 'block-close (point))
1447: (goto-char containing-sexp)
1448: ;; c-backward-to-block-anchor not necessary here; those
1449: ;; situations are handled in case 16E above.
1450: (c-add-stmt-syntax 'block-close nil t lim paren-state)))
1451:
1452: ;; CASE 16D: Only top level defun close left.
1453: (t
1454: (goto-char containing-sexp)
1455: (c-backward-to-decl-anchor lim)
1456: (c-add-stmt-syntax 'defun-close nil nil
1457: (c-most-enclosing-brace paren-state)
1458: paren-state))
1459: ))
1460:
1461: ;; CASE 17: Statement or defun catchall.
1462: (t
1463: (goto-char indent-point)
1464: ;; Back up statements until we find one that starts at boi.
1465: (while (let* ((prev-point (point))
1466: (last-step-type (c-beginning-of-statement-1
1467: containing-sexp)))
1468: (if (= (point) prev-point)
1469: (progn
1470: (setq step-type (or step-type last-step-type))
1471: nil)
1472: (setq step-type last-step-type)
1473: (/= (point) (c-point 'boi)))))
1474: (cond
1475:
1476: ;; CASE 17B: continued statement
1477: ((and (eq step-type 'same)
1478: (/= (point) indent-point))
1479: (c-add-stmt-syntax 'statement-cont nil nil
1480: containing-sexp paren-state))
1481:
1482: ;; CASE 17A: After a case/default label?
1483: ((progn
1484: (while (and (eq step-type 'label)
1485: (not (looking-at c-label-kwds-regexp)))
1486: (setq step-type
1487: (c-beginning-of-statement-1 containing-sexp)))
1488: (eq step-type 'label))
1489: (c-add-stmt-syntax (if (eq char-after-ip ?{)
1490: 'statement-case-open
1491: 'statement-case-intro)
1492: nil t containing-sexp paren-state))
1493:
1494: ;; CASE 17D: any old statement
1495: ((progn
1496: (while (eq step-type 'label)
1497: (setq step-type
1498: (c-beginning-of-statement-1 containing-sexp)))
1499: (eq step-type 'previous))
1500: (c-add-stmt-syntax 'statement nil t
1501: containing-sexp paren-state)
1502: (if (eq char-after-ip ?{)
1503: (c-add-syntax 'block-open)))
1504:
1505: ;; CASE 17I: Inside a substatement block.
1506: ((progn
1507: ;; The following tests are all based on containing-sexp.
1508: (goto-char containing-sexp)
1509: ;; From here on we have the next containing sexp in lim.
1510: (setq lim (c-most-enclosing-brace paren-state containing-sexp))
1511: (c-after-conditional))
1512: (c-backward-to-block-anchor lim)
1513: (c-add-stmt-syntax 'statement-block-intro nil t
1514: lim paren-state)
1515: (if (eq char-after-ip ?{)
1516: (c-add-syntax 'block-open)))
1517:
1518: ;; CASE 17E: first statement in an in-expression block.
1519: ;; C.f. cases 4, 7B and 16A.
1520: ((setq placeholder (c-looking-at-inexpr-block
1521: (c-safe-position containing-sexp paren-state)
1522: nil))
1523: (setq tmpsymbol (if (eq (car placeholder) 'inlambda)
1524: 'defun-block-intro
1525: 'statement-block-intro))
1526: (back-to-indentation)
1527: (if (= containing-sexp (point))
1528: (c-add-syntax tmpsymbol (point))
1529: (goto-char (cdr placeholder))
1530: (back-to-indentation)
1531: (c-add-stmt-syntax tmpsymbol nil t
1532: (c-most-enclosing-brace c-state-cache (point))
1533: paren-state)
1534: (if (/= (point) (cdr placeholder))
1535: (c-add-syntax (car placeholder))))
1536: (if (eq char-after-ip ?{)
1537: (c-add-syntax 'block-open)))
1538:
1539: ;; CASE 17F: first statement in an inline, or first
1540: ;; statement in a top-level defun. we can tell this is it
1541: ;; if there are no enclosing braces that haven't been
1542: ;; narrowed out by a class (i.e. don't use bod here).
1543: ((save-excursion
1544: (or (not (setq placeholder (c-most-enclosing-brace
1545: paren-state)))
1546: (and (progn
1547: (goto-char placeholder)
1548: (eq (char-after) ?{))
1549: (c-looking-at-decl-block (c-most-enclosing-brace
1550: paren-state (point))
1551: nil))))
1552: (c-backward-to-decl-anchor lim)
1553: (back-to-indentation)
1554: (c-add-syntax 'defun-block-intro (point)))
1555:
1556: ;; CASE 17G: First statement in a function declared inside
1557: ;; a normal block. This can occur in Pike and with
1558: ;; e.g. the gcc extensions, but watch out for macros
1559: ;; followed by blocks. C.f. cases B.3 and 16F.
1560: ((save-excursion
1561: (and (not (c-at-statement-start-p))
1562: (eq (c-beginning-of-statement-1 lim nil nil t) 'same)
1563: (setq placeholder (point))
1564: (let ((c-recognize-typeless-decls nil))
1565: ;; Turn off recognition of constructs that lacks
1566: ;; a type in this case, since that's more likely
1567: ;; to be a macro followed by a block.
1568: (c-forward-decl-or-cast-1 (c-point 'bosws) nil nil))))
1569: (back-to-indentation)
1570: (if (/= (point) containing-sexp)
1571: (goto-char placeholder))
1572: (c-add-stmt-syntax 'defun-block-intro nil t
1573: lim paren-state))
1574:
1575: ;; CASE 17H: First statement in a block.
1576: (t
1577: ;; If the block is preceded by a case/switch label on the
1578: ;; same line, we anchor at the first preceding label at
1579: ;; boi. The default handling in c-add-stmt-syntax is
1580: ;; really fixes it better, but we do like this to keep the
1581: ;; indentation compatible with version 5.28 and earlier.
1582: ;; C.f. case 16C.
1583: (while (and (/= (setq placeholder (point)) (c-point 'boi))
1584: (eq (c-beginning-of-statement-1 lim) 'label)))
1585: (goto-char placeholder)
1586: (if (looking-at c-label-kwds-regexp)
1587: (c-add-syntax 'statement-block-intro (point))
1588: (goto-char containing-sexp)
1589: ;; c-backward-to-block-anchor not necessary here; those
1590: ;; situations are handled in case 17I above.
1591: (c-add-stmt-syntax 'statement-block-intro nil t
1592: lim paren-state))
1593: (if (eq char-after-ip ?{)
1594: (c-add-syntax 'block-open)))
1595: ))
1596: )
1597:
1598: ;; now we need to look at any modifiers
1599: (goto-char indent-point)
1600: (skip-chars-forward " \t")
1601:
1602: ;; are we looking at a comment only line?
1603: (when (and (looking-at c-comment-start-regexp)
1604: (/= (c-forward-token-2 0 nil (c-point 'eol)) 0))
1605: (c-append-syntax 'comment-intro))
1606:
1607: ;; we might want to give additional offset to friends (in C++).
1608: (when (and c-opt-friend-key
1609: (looking-at c-opt-friend-key))
1610: (c-append-syntax 'friend))
1611:
1612: ;; Set syntactic-relpos.
1613: (let ((p c-syntactic-context))
1614: (while (and p
1615: (if (integerp (c-langelem-pos (car p)))
1616: (progn
1617: (setq syntactic-relpos (c-langelem-pos (car p)))
1618: nil)
1619: t))
1620: (setq p (cdr p))))
1621:
1622: ;; Start of or a continuation of a preprocessor directive?
1623: (if (and macro-start
1624: (eq macro-start (c-point 'boi))
1625: (not (and (c-major-mode-is 'pike-mode)
1626: (eq (char-after (1+ macro-start)) ?\"))))
1627: (c-append-syntax 'cpp-macro)
1628: (when (and c-syntactic-indentation-in-macros macro-start)
1629: (if in-macro-expr
1630: (when (or
1631: (< syntactic-relpos macro-start)
1632: (not (or
1633: (assq 'arglist-intro c-syntactic-context)
1634: (assq 'arglist-cont c-syntactic-context)
1635: (assq 'arglist-cont-nonempty c-syntactic-context)
1636: (assq 'arglist-close c-syntactic-context))))
1637: ;; If inside a cpp expression, i.e. anywhere in a
1638: ;; cpp directive except a #define body, we only let
1639: ;; through the syntactic analysis that is internal
1640: ;; in the expression. That means the arglist
1641: ;; elements, if they are anchored inside the cpp
1642: ;; expression.
1643: (setq c-syntactic-context nil)
1644: (c-add-syntax 'cpp-macro-cont macro-start))
1645: (when (and (eq macro-start syntactic-relpos)
1646: (not (assq 'cpp-define-intro c-syntactic-context))
1647: (save-excursion
1648: (goto-char macro-start)
1649: (or (not (c-forward-to-cpp-define-body))
1650: (<= (point) (c-point 'boi indent-point)))))
1651: ;; Inside a #define body and the syntactic analysis is
1652: ;; anchored on the start of the #define. In this case
1653: ;; we add cpp-define-intro to get the extra
1654: ;; indentation of the #define body.
1655: (c-add-syntax 'cpp-define-intro)))))
1656:
1657: ;; return the syntax
1658: c-syntactic-context)))
1659:
1660: ;;;; End of `asir-c-guess-basic-syntax'
1661:
1662: (provide 'asir-mode)
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>