1 ;;; semantic/bovine/c.el --- Semantic details for C
3 ;; Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
4 ;; 2008, 2009, 2010 Free Software Foundation, Inc.
6 ;; Author: Eric M. Ludlam <zappo@gnu.org>
8 ;; This file is part of GNU Emacs.
10 ;; GNU Emacs is free software: you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation, either version 3 of the License, or
13 ;; (at your option) any later version.
15 ;; GNU Emacs is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
25 ;; Support for the C/C++ bovine parser for Semantic.
27 ;; @todo - can I support c++-font-lock-extra-types ?
30 (require 'semantic
/analyze
)
31 (require 'semantic
/bovine
/gcc
)
32 (require 'semantic
/idle
)
33 (require 'semantic
/lex-spp
)
34 (require 'semantic
/bovine
/c-by
)
37 (require 'semantic
/find
))
39 (declare-function semantic-brute-find-tag-by-attribute
"semantic/find")
40 (declare-function semanticdb-minor-mode-p
"semantic/db-mode")
41 (declare-function semanticdb-needs-refresh-p
"semantic/db")
42 (declare-function c-forward-conditional
"cc-cmds")
43 (declare-function ede-system-include-path
"ede")
47 (eval-when-compile (require 'cc-mode
))
49 (if (fboundp 'c-end-of-macro
)
51 (defalias 'semantic-c-end-of-macro
'c-end-of-macro
))
53 (defun semantic-c-end-of-macro ()
54 "Go to the end of a preprocessor directive.
55 More accurately, move point to the end of the closest following line
56 that doesn't end with a line continuation backslash.
58 This function does not do any hidden buffer changes."
61 (when (and (eq (char-before) ?
\\)
68 (define-child-mode c
++-mode c-mode
69 "`c++-mode' uses the same parser as `c-mode'.")
74 (defcustom-mode-local-semantic-dependency-system-include-path
75 c-mode semantic-c-dependency-system-include-path
77 "The system include path used by the C language.")
79 (defcustom semantic-default-c-path nil
80 "Default set of include paths for C code.
81 Used by `semantic-dep' to define an include path.
82 NOTE: In process of obsoleting this."
85 :type
'(repeat (string :tag
"Path")))
87 (defvar-mode-local c-mode semantic-dependency-include-path
88 semantic-default-c-path
89 "System path to search for include files.")
93 ;; Compiler options need to show up after path setup, but before
94 ;; the preprocessor section.
96 (when (member system-type
'(gnu gnu
/linux darwin cygwin
))
99 ;;; Pre-processor maps
102 (defvar semantic-lex-c-preprocessor-symbol-map-builtin
104 ("__const" .
"const")
106 ("__declspec" .
((spp-arg-list ("foo") 1 .
2)))
107 ("__attribute__" .
((spp-arg-list ("foo") 1 .
2)))
109 "List of symbols to include by default.")
111 (defvar semantic-c-in-reset-preprocessor-table nil
112 "Non-nil while resetting the preprocessor symbol map.
113 Used to prevent a reset while trying to parse files that are
114 part of the preprocessor map.")
116 (defvar semantic-lex-c-preprocessor-symbol-file
)
117 (defvar semantic-lex-c-preprocessor-symbol-map
)
119 (defun semantic-c-reset-preprocessor-symbol-map ()
120 "Reset the C preprocessor symbol map based on all input variables."
121 (when (featurep 'semantic
/bovine
/c
)
124 (when (and (not semantic-c-in-reset-preprocessor-table
)
125 (featurep 'semantic
/db-mode
)
126 (semanticdb-minor-mode-p))
127 (let ( ;; Don't use external parsers. We need the internal one.
128 (semanticdb-out-of-buffer-create-table-fcn nil
)
129 ;; Don't recurse while parsing these files the first time.
130 (semantic-c-in-reset-preprocessor-table t
)
132 (dolist (sf semantic-lex-c-preprocessor-symbol-file
)
133 ;; Global map entries
134 (let* ((table (semanticdb-file-table-object sf t
)))
136 (when (semanticdb-needs-refresh-p table
)
138 ;; Call with FORCE, as the file is very likely to
139 ;; not be in a buffer.
140 (semanticdb-refresh-table table t
)
141 (error (message "Error updating tables for %S"
142 (object-name table
)))))
143 (setq filemap
(append filemap
(oref table lexical-table
)))
147 (setq-mode-local c-mode
148 semantic-lex-spp-macro-symbol-obarray
149 (semantic-lex-make-spp-table
150 (append semantic-lex-c-preprocessor-symbol-map-builtin
151 semantic-lex-c-preprocessor-symbol-map
156 (defcustom semantic-lex-c-preprocessor-symbol-map nil
157 "Table of C Preprocessor keywords used by the Semantic C lexer.
158 Each entry is a cons cell like this:
159 ( \"KEYWORD\" . \"REPLACEMENT\" )
160 Where KEYWORD is the macro that gets replaced in the lexical phase,
161 and REPLACEMENT is a string that is inserted in it's place. Empty string
162 implies that the lexical analyzer will discard KEYWORD when it is encountered.
164 Alternately, it can be of the form:
165 ( \"KEYWORD\" ( LEXSYM1 \"str\" 1 1 ) ... ( LEXSYMN \"str\" 1 1 ) )
166 where LEXSYM is a symbol that would normally be produced by the
167 lexical analyzer, such as `symbol' or `string'. The string in the
168 second position is the text that makes up the replacement. This is
169 the way to have multiple lexical symbols in a replacement. Using the
170 first way to specify text like \"foo::bar\" would not work, because :
171 is a separate lexical symbol.
173 A quick way to see what you would need to insert is to place a
176 #define MYSYM foo::bar
178 into a C file, and do this:
179 \\[semantic-lex-spp-describe]
181 The output table will describe the symbols needed."
183 :type
'(repeat (cons (string :tag
"Keyword")
184 (sexp :tag
"Replacement")))
185 :set
(lambda (sym value
)
186 (set-default sym value
)
188 (semantic-c-reset-preprocessor-symbol-map)
193 (defcustom semantic-lex-c-preprocessor-symbol-file nil
194 "List of C/C++ files that contain preprocessor macros for the C lexer.
195 Each entry is a filename and each file is parsed, and those macros
196 are included in every C/C++ file parsed by semantic.
197 You can use this variable instead of `semantic-lex-c-preprocessor-symbol-map'
198 to store your global macros in a more natural way."
200 :type
'(repeat (file :tag
"File"))
201 :set
(lambda (sym value
)
202 (set-default sym value
)
204 (semantic-c-reset-preprocessor-symbol-map)
209 (defcustom semantic-c-member-of-autocast
't
210 "Non-nil means classes with a '->' operator will cast to its return type.
220 if `semantic-c-member-of-autocast' is non-nil :
221 foo->[here completion will list method of Bar]
223 if `semantic-c-member-of-autocast' is nil :
224 foo->[here completion will list method of Foo]"
228 (define-lex-spp-macro-declaration-analyzer semantic-lex-cpp-define
229 "A #define of a symbol with some value.
230 Record the symbol in the semantic preprocessor.
231 Return the defined symbol as a special spp lex token."
232 "^\\s-*#\\s-*define\\s-+\\(\\(\\sw\\|\\s_\\)+\\)" 1
233 (goto-char (match-end 0))
234 (skip-chars-forward " \t")
237 (let* ((name (buffer-substring-no-properties
238 (match-beginning 1) (match-end 1)))
239 (with-args (save-excursion
240 (goto-char (match-end 0))
242 (semantic-lex-spp-replacements-enabled nil
)
243 ;; Temporarilly override the lexer to include
244 ;; special items needed inside a macro
245 (semantic-lex-analyzer #'semantic-cpp-lexer
)
247 (semantic-lex-spp-stream-for-macro (save-excursion
248 (semantic-c-end-of-macro)
252 ;; Only do argument checking if the paren was immediatly after
255 (semantic-lex-spp-first-token-arg-list (car raw-stream
)))
257 ;; Magical spp variable for end point.
258 (setq semantic-lex-end-point
(point))
260 ;; Handled nested macro streams.
261 (semantic-lex-spp-merge-streams raw-stream
)
264 (define-lex-spp-macro-undeclaration-analyzer semantic-lex-cpp-undef
265 "A #undef of a symbol.
266 Remove the symbol from the semantic preprocessor.
267 Return the defined symbol as a special spp lex token."
268 "^\\s-*#\\s-*undef\\s-+\\(\\(\\sw\\|\\s_\\)+\\)" 1)
271 ;;; Conditional Skipping
273 (defcustom semantic-c-obey-conditional-section-parsing-flag t
274 "*Non-nil means to interpret preprocessor #if sections.
275 This implies that some blocks of code will not be parsed based on the
276 values of the conditions in the #if blocks."
280 (defun semantic-c-skip-conditional-section ()
281 "Skip one section of a conditional.
282 Moves forward to a matching #elif, #else, or #endif.
283 Moves completely over balanced #if blocks."
286 ;; (if (looking-at "^\\s-*#if")
287 ;; (semantic-lex-spp-push-if (point))
289 (while (and semantic-c-obey-conditional-section-parsing-flag
292 "^\\s-*#\\s-*\\(if\\(n?def\\)?\\|el\\(if\\|se\\)\\|endif\\)\\>"
294 (goto-char (match-beginning 0))
296 ((looking-at "^\\s-*#\\s-*if")
297 ;; We found a nested if. Skip it.
298 (c-forward-conditional 1))
299 ((looking-at "^\\s-*#\\s-*elif")
300 ;; We need to let the preprocessor analize this one.
304 ((looking-at "^\\s-*#\\s-*\\(endif\\|else\\)\\>")
305 ;; We are at the end. Pop our state.
306 ;; (semantic-lex-spp-pop-if)
307 ;; Note: We include ELSE and ENDIF the same. If skip some previous
308 ;; section, then we should do the else by default, making it much
314 ;; We found an elif. Stop here.
317 (define-lex-regex-analyzer semantic-lex-c-if
318 "Code blocks wrapped up in #if, or #ifdef.
319 Uses known macro tables in SPP to determine what block to skip."
320 "^\\s-*#\\s-*\\(if\\|ifndef\\|ifdef\\|elif\\)\\s-+\\(!?defined(\\|\\)\\s-*\\(\\(\\sw\\|\\s_\\)+\\)\\(\\s-*)\\)?\\s-*$"
321 (semantic-c-do-lex-if))
323 (defun semantic-c-do-lex-if ()
324 "Handle lexical CPP if statements."
325 (let* ((sym (buffer-substring-no-properties
326 (match-beginning 3) (match-end 3)))
327 (defstr (buffer-substring-no-properties
328 (match-beginning 2) (match-end 2)))
329 (defined (string= defstr
"defined("))
330 (notdefined (string= defstr
"!defined("))
331 (ift (buffer-substring-no-properties
332 (match-beginning 1) (match-end 1)))
333 (ifdef (or (string= ift
"ifdef")
334 (and (string= ift
"if") defined
)
335 (and (string= ift
"elif") defined
)
337 (ifndef (or (string= ift
"ifndef")
338 (and (string= ift
"if") notdefined
)
339 (and (string= ift
"elif") notdefined
)
342 (if (or (and (or (string= ift
"if") (string= ift
"elif"))
344 (and ifdef
(not (semantic-lex-spp-symbol-p sym
)))
345 (and ifndef
(semantic-lex-spp-symbol-p sym
)))
346 ;; The if indecates to skip this preprocessor section
348 ;; (message "%s %s yes" ift sym)
351 ;;(c-forward-conditional 1)
352 ;; This skips only a section of a conditional. Once that section
353 ;; is opened, encountering any new #else or related conditional
354 ;; should be skipped.
355 (semantic-c-skip-conditional-section)
356 (setq semantic-lex-end-point
(point))
357 (semantic-push-parser-warning (format "Skip #%s %s" ift sym
)
359 ;; (semantic-lex-push-token
360 ;; (semantic-lex-token 'c-preprocessor-skip pt (point)))
362 ;; Else, don't ignore it, but do handle the internals.
363 ;;(message "%s %s no" ift sym)
365 (setq semantic-lex-end-point
(point))
368 (define-lex-regex-analyzer semantic-lex-c-macro-else
369 "Ignore an #else block.
370 We won't see the #else due to the macro skip section block
371 unless we are actively parsing an open #if statement. In that
372 case, we must skip it since it is the ELSE part."
373 "^\\s-*#\\s-*\\(else\\)"
375 (semantic-c-skip-conditional-section)
376 (setq semantic-lex-end-point
(point))
377 (semantic-push-parser-warning "Skip #else" pt
(point))
378 ;; (semantic-lex-push-token
379 ;; (semantic-lex-token 'c-preprocessor-skip pt (point)))
382 (define-lex-regex-analyzer semantic-lex-c-macrobits
383 "Ignore various forms of #if/#else/#endif conditionals."
384 "^\\s-*#\\s-*\\(if\\(n?def\\)?\\|endif\\|elif\\|else\\)"
385 (semantic-c-end-of-macro)
386 (setq semantic-lex-end-point
(point))
389 (define-lex-spp-include-analyzer semantic-lex-c-include-system
390 "Identify include strings, and return special tokens."
391 "^\\s-*#\\s-*include\\s-*<\\([^ \t\n>]+\\)>" 0
392 ;; Hit 1 is the name of the include.
393 (goto-char (match-end 0))
394 (setq semantic-lex-end-point
(point))
395 (cons (buffer-substring-no-properties (match-beginning 1)
399 (define-lex-spp-include-analyzer semantic-lex-c-include
400 "Identify include strings, and return special tokens."
401 "^\\s-*#\\s-*include\\s-*\"\\([^ \t\n>]+\\)\"" 0
402 ;; Hit 1 is the name of the include.
403 (goto-char (match-end 0))
404 (setq semantic-lex-end-point
(point))
405 (cons (buffer-substring-no-properties (match-beginning 1)
410 (define-lex-regex-analyzer semantic-lex-c-ignore-ending-backslash
411 "Skip backslash ending a line.
412 Go to the next line."
414 (setq semantic-lex-end-point
(match-end 0)))
416 (define-lex-regex-analyzer semantic-lex-c-namespace-begin-macro
417 "Handle G++'s namespace macros which the pre-processor can't handle."
418 "\\(_GLIBCXX_BEGIN_NAMESPACE\\)(\\s-*\\(\\(?:\\w\\|\\s_\\)+\\)\\s-*)"
419 (let* ((nsend (match-end 1))
420 (sym-start (match-beginning 2))
421 (sym-end (match-end 2))
422 (ms (buffer-substring-no-properties sym-start sym-end
)))
423 ;; Push the namespace keyword.
424 (semantic-lex-push-token
425 (semantic-lex-token 'NAMESPACE
(match-beginning 0) nsend
"namespace"))
427 (semantic-lex-push-token
428 (semantic-lex-token 'symbol sym-start sym-end ms
))
430 (goto-char (match-end 0))
431 (let ((start (point))
433 ;; If we can't find a matching end, then create the fake list.
434 (when (re-search-forward "_GLIBCXX_END_NAMESPACE" nil t
)
436 (semantic-lex-push-token
437 (semantic-lex-token 'semantic-list start end
438 (list 'prefix-fake
)))))
439 (setq semantic-lex-end-point
(point)))
441 (defcustom semantic-lex-c-nested-namespace-ignore-second t
442 "Should _GLIBCXX_BEGIN_NESTED_NAMESPACE ignore the second namespace?
443 It is really there, but if a majority of uses is to squeeze out
444 the second namespace in use, then it should not be included.
446 If you are having problems with smart completion and STL templates,
447 it may be that this is set incorrectly. After changing the value
448 of this flag, you will need to delete any semanticdb cache files
449 that may have been incorrectly parsed."
453 (define-lex-regex-analyzer semantic-lex-c-VC
++-begin-std-namespace
454 "Handle VC++'s definition of the std namespace."
456 (semantic-lex-push-token
457 (semantic-lex-token 'NAMESPACE
(match-beginning 0) (match-end 0) "namespace"))
458 (semantic-lex-push-token
459 (semantic-lex-token 'symbol
(match-beginning 0) (match-end 0) "std"))
460 (goto-char (match-end 0))
461 (let ((start (point))
463 (when (re-search-forward "_STD_END" nil t
)
465 (semantic-lex-push-token
466 (semantic-lex-token 'semantic-list start end
467 (list 'prefix-fake
)))))
468 (setq semantic-lex-end-point
(point)))
470 (define-lex-regex-analyzer semantic-lex-c-VC
++-end-std-namespace
471 "Handle VC++'s definition of the std namespace."
473 (goto-char (match-end 0))
474 (setq semantic-lex-end-point
(point)))
476 (define-lex-regex-analyzer semantic-lex-c-namespace-begin-nested-macro
477 "Handle G++'s namespace macros which the pre-processor can't handle."
478 "\\(_GLIBCXX_BEGIN_NESTED_NAMESPACE\\)(\\s-*\\(\\(?:\\w\\|\\s_\\)+\\)\\s-*,\\s-*\\(\\(?:\\w\\|\\s_\\)+\\)\\s-*)"
479 (goto-char (match-end 0))
480 (let* ((nsend (match-end 1))
481 (sym-start (match-beginning 2))
482 (sym-end (match-end 2))
483 (ms (buffer-substring-no-properties sym-start sym-end
))
484 (sym2-start (match-beginning 3))
485 (sym2-end (match-end 3))
486 (ms2 (buffer-substring-no-properties sym2-start sym2-end
)))
487 ;; Push the namespace keyword.
488 (semantic-lex-push-token
489 (semantic-lex-token 'NAMESPACE
(match-beginning 0) nsend
"namespace"))
491 (semantic-lex-push-token
492 (semantic-lex-token 'symbol sym-start sym-end ms
))
494 (goto-char (match-end 0))
495 (let ((start (point))
497 ;; If we can't find a matching end, then create the fake list.
498 (when (re-search-forward "_GLIBCXX_END_NESTED_NAMESPACE" nil t
)
500 (if semantic-lex-c-nested-namespace-ignore-second
501 ;; The same as _GLIBCXX_BEGIN_NAMESPACE
502 (semantic-lex-push-token
503 (semantic-lex-token 'semantic-list start end
504 (list 'prefix-fake
)))
505 ;; Do both the top and second level namespace
506 (semantic-lex-push-token
507 (semantic-lex-token 'semantic-list start end
508 ;; We'll depend on a quick hack
509 (list 'prefix-fake-plus
510 (semantic-lex-token 'NAMESPACE
513 (semantic-lex-token 'symbol
516 (semantic-lex-token 'semantic-list start end
517 (list 'prefix-fake
)))
520 (setq semantic-lex-end-point
(point)))
522 (define-lex-regex-analyzer semantic-lex-c-namespace-end-macro
523 "Handle G++'s namespace macros which the pre-processor can't handle."
524 "_GLIBCXX_END_\\(NESTED_\\)?NAMESPACE"
525 (goto-char (match-end 0))
526 (setq semantic-lex-end-point
(point)))
528 (define-lex-regex-analyzer semantic-lex-c-string
529 "Detect and create a C string token."
531 ;; Zing to the end of this string.
532 (semantic-lex-push-token
536 ;; Skip L prefix if present.
537 (goto-char (match-beginning 1))
538 (semantic-lex-unterminated-syntax-protection 'string
543 (define-lex-regex-analyzer semantic-c-lex-ignore-newline
544 "Detect and ignore newline tokens.
545 Use this ONLY if newlines are not whitespace characters (such as when
546 they are comment end characters)."
547 ;; Just like semantic-lex-ignore-newline, but also ignores
549 "\\s-*\\\\?\\s-*\\(\n\\|\\s>\\)"
550 (setq semantic-lex-end-point
(match-end 0)))
553 (define-lex semantic-c-lexer
554 "Lexical Analyzer for C code.
555 Use semantic-cpp-lexer for parsing text inside a CPP macro."
556 ;; C preprocessor features
557 semantic-lex-cpp-define
558 semantic-lex-cpp-undef
560 semantic-lex-c-macro-else
561 semantic-lex-c-macrobits
562 semantic-lex-c-include
563 semantic-lex-c-include-system
564 semantic-lex-c-ignore-ending-backslash
565 ;; Whitespace handling
566 semantic-lex-ignore-whitespace
567 semantic-c-lex-ignore-newline
568 ;; Non-preprocessor features
570 ;; Must detect C strings before symbols because of possible L prefix!
571 semantic-lex-c-string
572 ;; Custom handlers for some macros come before the macro replacement analyzer.
573 semantic-lex-c-namespace-begin-macro
574 semantic-lex-c-namespace-begin-nested-macro
575 semantic-lex-c-namespace-end-macro
576 semantic-lex-c-VC
++-begin-std-namespace
577 semantic-lex-c-VC
++-end-std-namespace
578 ;; Handle macros, symbols, and keywords
579 semantic-lex-spp-replace-or-symbol-or-keyword
580 semantic-lex-charquote
581 semantic-lex-paren-or-list
582 semantic-lex-close-paren
583 semantic-lex-ignore-comments
584 semantic-lex-punctuation
585 semantic-lex-default-action
)
587 (define-lex-simple-regex-analyzer semantic-lex-cpp-hashhash
588 "Match ## inside a CPP macro as special."
591 (define-lex semantic-cpp-lexer
592 "Lexical Analyzer for CPP macros in C code."
594 semantic-lex-cpp-hashhash
595 ;; C preprocessor features
596 semantic-lex-cpp-define
597 semantic-lex-cpp-undef
599 semantic-lex-c-macro-else
600 semantic-lex-c-macrobits
601 semantic-lex-c-include
602 semantic-lex-c-include-system
603 semantic-lex-c-ignore-ending-backslash
604 ;; Whitespace handling
605 semantic-lex-ignore-whitespace
606 semantic-c-lex-ignore-newline
607 ;; Non-preprocessor features
609 ;; Must detect C strings before symbols because of possible L prefix!
610 semantic-lex-c-string
611 ;; Parsing inside a macro means that we don't do macro replacement.
612 ;; semantic-lex-spp-replace-or-symbol-or-keyword
613 semantic-lex-symbol-or-keyword
614 semantic-lex-charquote
615 semantic-lex-paren-or-list
616 semantic-lex-close-paren
617 semantic-lex-ignore-comments
618 semantic-lex-punctuation
619 semantic-lex-default-action
)
621 (define-mode-local-override semantic-parse-region c-mode
622 (start end
&optional nonterminal depth returnonerror
)
623 "Calls `semantic-parse-region-default', except in a macro expansion.
624 MACRO expansion mode is handled through the nature of Emacs's non-lexical
625 binding of variables.
626 START, END, NONTERMINAL, DEPTH, and RETURNONERRORS are the same
628 (if (and (boundp 'lse
) (or (/= start
1) (/= end
(point-max))))
629 (let* ((last-lexical-token lse
)
630 (llt-class (semantic-lex-token-class last-lexical-token
))
631 (llt-fakebits (car (cdr last-lexical-token
)))
632 (macroexpand (stringp (car (cdr last-lexical-token
)))))
635 ;; It is a macro expansion. Do something special.
636 ;;(message "MOOSE %S %S, %S : %S" start end nonterminal lse)
637 (semantic-c-parse-lexical-token
638 lse nonterminal depth returnonerror
)
640 ;; Not a macro expansion, but perhaps a funny semantic-list
641 ;; is at the start? Remove the depth if our semantic list is not
642 ;; made of list tokens.
643 (if (and depth
(= depth
1)
644 (eq llt-class
'semantic-list
)
645 (not (null llt-fakebits
))
647 (symbolp (car llt-fakebits
))
652 ;; This is a copy of semantic-parse-region-default where we
653 ;; are doing something special with the lexication of the
654 ;; contents of the semantic-list token. Stuff not used by C
657 (if (and (consp llt-fakebits
)
658 (eq (car llt-fakebits
) 'prefix-fake-plus
))
659 ;; If our semantic-list is special, then only stick in the
662 ;; Lex up the region with a depth of 0
663 (semantic-lex start end
0))))
667 (semantic-repeat-parse-whole-stream tokstream
673 ;; It was not a macro expansion, nor a special semantic-list.
675 (semantic-parse-region-default start end
680 (semantic-parse-region-default start end nonterminal
684 (defvar semantic-c-parse-token-hack-depth
0
685 "Current depth of recursive calls to `semantic-c-parse-lexical-token'.")
687 (defun semantic-c-parse-lexical-token (lexicaltoken nonterminal depth
689 "Do a region parse on the contents of LEXICALTOKEN.
690 Presumably, this token has a string in it from a macro.
691 The text of the token is inserted into a different buffer, and
693 Argument NONTERMINAL, DEPTH, and RETURNONERROR are passed into
695 (let* ((semantic-c-parse-token-hack-depth (1+ semantic-c-parse-token-hack-depth
))
696 (buf (get-buffer-create (format " *C parse hack %d*"
697 semantic-c-parse-token-hack-depth
)))
699 (spp-syms semantic-lex-spp-dynamic-macro-symbol-obarray
)
701 (start (semantic-lex-token-start lexicaltoken
))
702 (end (semantic-lex-token-end lexicaltoken
))
703 (symtext (semantic-lex-token-text lexicaltoken
))
704 (macros (get-text-property 0 'macros symtext
))
706 (with-current-buffer buf
708 (when (not (eq major-mode mode
))
711 ;; Protect against user hooks throwing errors.
716 (format "There was an error initializing %s in buffer \"%s\". Debug your hooks? "
718 (semantic-c-debug-mode-init mode
)
719 (message "Macro parsing state may be broken...")
723 ;; Hack in mode-local
724 (activate-mode-local-bindings)
725 ;; CHEATER! The following 3 lines are from
726 ;; `semantic-new-buffer-fcn', but we don't want to turn
727 ;; on all the other annoying modes for this little task.
728 (setq semantic-new-buffer-fcn-was-run t
)
730 (semantic-clear-toplevel-cache)
731 (remove-hook 'semantic-lex-reset-hooks
'semantic-lex-spp-reset-hook
734 ;; Get the macro symbol table right.
735 (setq semantic-lex-spp-dynamic-macro-symbol-obarray spp-syms
)
736 ;; (message "%S" macros)
738 (semantic-lex-spp-symbol-set (car sym
) (cdr sym
)))
743 (semantic-parse-region-default
744 (point-min) (point-max) nonterminal depth returnonerror
))
746 ;; Clean up macro symbols
748 (semantic-lex-spp-symbol-remove (car sym
)))
750 ;; Convert the text of the stream.
752 ;; Only do two levels here 'cause I'm lazy.
753 (semantic--tag-set-overlay tag
(list start end
))
754 (dolist (stag (semantic-tag-components-with-overlays tag
))
755 (semantic--tag-set-overlay stag
(list start end
))
760 (defvar semantic-c-debug-mode-init-last-mode nil
761 "The most recent mode needing debugging.")
763 (defun semantic-c-debug-mode-init (mm)
764 "Debug mode init for major mode MM after we're done parsing now."
765 (interactive (list semantic-c-debug-mode-init-last-mode
))
766 (if (called-interactively-p 'interactive
)
769 (switch-to-buffer (get-buffer-create "*MODE HACK TEST*"))
770 (let ((debug-on-error t
))
773 ;; Notify about the debug
774 (setq semantic-c-debug-mode-init-last-mode mm
)
776 (add-hook 'post-command-hook
'semantic-c-debug-mode-init-pch
)))
778 (defun semantic-c-debug-mode-init-pch ()
779 "Notify user about needing to debug their major mode hooks."
780 (let ((mm semantic-c-debug-mode-init-last-mode
))
781 (switch-to-buffer-other-window
782 (get-buffer-create "*MODE HACK TEST*"))
784 (insert "A failure occurred while parsing your buffers.
786 The failure occurred while attempting to initialize " (symbol-name mm
) " in a
787 buffer not associated with a file. To debug this problem, type
789 M-x semantic-c-debug-mode-init
793 (remove-hook 'post-command-hook
'semantic-c-debug-mode-init-pch
)))
795 (defun semantic-expand-c-tag (tag)
796 "Expand TAG into a list of equivalent tags, or nil."
797 (let ((return-list nil
)
799 ;; Expand an EXTERN C first.
800 (when (eq (semantic-tag-class tag
) 'extern
)
801 (let* ((mb (semantic-tag-get-attribute tag
:members
))
804 (let ((mods (semantic-tag-get-attribute (car mb
) :typemodifiers
)))
805 (setq mods
(cons "extern" (cons "\"C\"" mods
)))
806 (semantic-tag-put-attribute (car mb
) :typemodifiers mods
))
808 (setq return-list ret
)))
810 ;; Function or variables that have a :type that is some complex
811 ;; thing, extract it, and replace it with a reference.
813 ;; Thus, struct A { int a; } B;
815 ;; will create 2 toplevel tags, one is type A, and the other variable B
816 ;; where the :type of B is just a type tag A that is a prototype, and
817 ;; the actual struct info of A is it's own toplevel tag.
818 (when (or (semantic-tag-of-class-p tag
'function
)
819 (semantic-tag-of-class-p tag
'variable
))
820 (let* ((basetype (semantic-tag-type tag
))
822 (tname (when (consp basetype
)
823 (semantic-tag-name basetype
))))
824 ;; Make tname be a string.
825 (when (consp tname
) (setq tname
(car (car tname
))))
826 ;; Is the basetype a full type with a name of its own?
827 (when (and basetype
(semantic-tag-p basetype
)
828 (not (semantic-tag-prototype-p basetype
))
830 (not (string= tname
"")))
831 ;; a type tag referencing the type we are extracting.
832 (setq typeref
(semantic-tag-new-type
833 (semantic-tag-name basetype
)
834 (semantic-tag-type basetype
)
837 ;; Convert original tag to only have a reference.
838 (setq tag
(semantic-tag-copy tag
))
839 (semantic-tag-put-attribute tag
:type typeref
)
840 ;; Convert basetype to have the location information.
841 (semantic--tag-copy-properties tag basetype
)
842 (semantic--tag-set-overlay basetype
843 (semantic-tag-overlay tag
))
844 ;; Store the base tag as part of the return list.
845 (setq return-list
(cons basetype return-list
)))))
847 ;; Name of the tag is a list, so expand it. Tag lists occur
848 ;; for variables like this: int var1, var2, var3;
850 ;; This will expand that to 3 tags that happen to share the
851 ;; same overlay information.
852 (if (consp (semantic-tag-name tag
))
853 (let ((rl (semantic-expand-c-tag-namelist tag
)))
855 ;; If this returns nothing, then return nil overall
856 ;; because that will restore the old TAG input.
857 ((not rl
) (setq return-list nil
))
858 ;; If we have a return, append it to the existing list
861 (setq return-list
(append rl return-list
)))
863 ;; If we didn't have a list, but the return-list is non-empty,
864 ;; that means we still need to take our existing tag, and glom
865 ;; it onto our extracted type.
866 (if (consp return-list
)
867 (setq return-list
(cons tag return-list
)))
870 ;; Default, don't change the tag means returning nil.
873 (defun semantic-expand-c-tag-namelist (tag)
874 "Expand TAG whose name is a list into a list of tags, or nil."
875 (cond ((semantic-tag-of-class-p tag
'variable
)
876 ;; The name part comes back in the form of:
877 ;; ( NAME NUMSTARS BITS ARRAY ASSIGN )
879 (basety (semantic-tag-type tag
))
881 (mods (semantic-tag-get-attribute tag
:typemodifiers
))
883 (lst (semantic-tag-name tag
))
886 ;; Open up each name in the name list.
888 (setq suffix
"" ty
"")
891 (setq suffix
(concat ":" (nth 2 cur
))))
892 (if (= (length basety
) 1)
893 (setq ty
(car basety
))
895 (setq default
(nth 4 cur
))
897 (semantic-tag-new-variable
901 (buffer-substring-no-properties
902 (car default
) (car (cdr default
))))
903 :constant-flag
(semantic-tag-variable-constant-p tag
)
906 :dereference
(length (nth 3 cur
))
908 :reference
(semantic-tag-get-attribute tag
:reference
)
909 :documentation
(semantic-tag-docstring tag
) ;doc
912 (semantic--tag-copy-properties tag
(car vl
))
913 (semantic--tag-set-overlay (car vl
)
914 (semantic-tag-overlay tag
))
915 (setq lst
(cdr lst
)))
918 ((semantic-tag-of-class-p tag
'type
)
919 ;; We may someday want to add an extra check for a type
920 ;; of type "typedef".
921 ;; Each elt of NAME is ( STARS NAME )
923 (names (semantic-tag-name tag
)))
925 (setq vl
(cons (semantic-tag-new-type
926 (nth 1 (car names
)) ; name
928 (semantic-tag-type-members tag
)
929 ;; parent is just tbe name of what
930 ;; is passed down as a tag.
933 (semantic-tag-type-superclasses tag
)))
935 (let ((stars (car (car (car names
)))))
936 (if (= stars
0) nil stars
))
937 ;; This specifies what the typedef
938 ;; is expanded out as. Just the
939 ;; name shows up as a parent of this
942 (semantic-tag-get-attribute tag
:superclasses
)
943 ;;(semantic-tag-type-superclasses tag)
945 (semantic-tag-docstring tag
))
947 (semantic--tag-copy-properties tag
(car vl
))
948 (semantic--tag-set-overlay (car vl
)
949 (semantic-tag-overlay tag
))
950 (setq names
(cdr names
)))
952 ((and (listp (car tag
))
953 (semantic-tag-of-class-p (car tag
) 'variable
))
954 ;; Argument lists come in this way. Append all the expansions!
957 (setq vl
(append (semantic-tag-components (car vl
))
963 (defvar-mode-local c-mode semantic-tag-expand-function
'semantic-expand-c-tag
964 "Function used to expand tags generated in the C bovine parser.")
966 (defvar semantic-c-classname nil
967 "At parse time, assign a class or struct name text here.
968 It is picked up by `semantic-c-reconstitute-token' to determine
969 if something is a constructor. Value should be:
970 (TYPENAME . TYPEOFTYPE)
971 where typename is the name of the type, and typeoftype is \"class\"
974 (defun semantic-c-reconstitute-token (tokenpart declmods typedecl
)
975 "Reconstitute a token TOKENPART with DECLMODS and TYPEDECL.
976 This is so we don't have to match the same starting text several times.
977 Optional argument STAR and REF indicate the number of * and & in the typedef."
978 (when (and (listp typedecl
)
979 (= 1 (length typedecl
))
980 (stringp (car typedecl
)))
981 (setq typedecl
(car typedecl
)))
982 (cond ((eq (nth 1 tokenpart
) 'variable
)
983 (semantic-tag-new-variable
985 (or typedecl
"int") ;type
986 nil
;default value (filled with expand)
987 :constant-flag
(if (member "const" declmods
) t nil
)
988 :typemodifiers
(delete "const" declmods
)
991 ((eq (nth 1 tokenpart
) 'function
)
992 ;; We should look at part 4 (the arglist) here, and throw an
993 ;; error of some sort if it contains parser errors so that we
994 ;; don't parser function calls, but that is a little beyond what
995 ;; is available for data here.
997 (and (or (and semantic-c-classname
998 (string= (car semantic-c-classname
)
1000 (and (stringp (car (nth 2 tokenpart
)))
1001 (string= (car (nth 2 tokenpart
)) (car tokenpart
)))
1003 (not (car (nth 3 tokenpart
)))))
1004 (fcnpointer (string-match "^\\*" (car tokenpart
)))
1005 (fnname (if fcnpointer
1006 (substring (car tokenpart
) 1)
1008 (operator (if (string-match "[a-zA-Z]" fnname
)
1013 ;; Function pointers are really variables.
1014 (semantic-tag-new-variable
1018 ;; It is a function pointer
1019 :functionpointer-flag t
1022 (semantic-tag-new-function
1025 (cond ((car (nth 3 tokenpart
) )
1026 "void") ; Destructors have no return?
1028 ;; Constructors return an object.
1029 (semantic-tag-new-type
1031 (or (car semantic-c-classname
)
1032 (car (nth 2 tokenpart
)))
1034 (or (cdr semantic-c-classname
)
1042 (nth 4 tokenpart
) ;arglist
1043 :constant-flag
(if (member "const" declmods
) t nil
)
1044 :typemodifiers
(delete "const" declmods
)
1045 :parent
(car (nth 2 tokenpart
))
1046 :destructor-flag
(if (car (nth 3 tokenpart
) ) t
)
1047 :constructor-flag
(if constructor t
)
1048 :pointer
(nth 7 tokenpart
)
1049 :operator-flag operator
1050 ;; Even though it is "throw" in C++, we use
1051 ;; `throws' as a common name for things that toss
1052 ;; exceptions about.
1053 :throws
(nth 5 tokenpart
)
1054 ;; Reemtrant is a C++ thingy. Add it here
1055 :reentrant-flag
(if (member "reentrant" (nth 6 tokenpart
)) t
)
1056 ;; A function post-const is funky. Try stuff
1057 :methodconst-flag
(if (member "const" (nth 6 tokenpart
)) t
)
1058 ;; prototypes are functions w/ no body
1059 :prototype-flag
(if (nth 8 tokenpart
) t
)
1061 :pure-virtual-flag
(if (eq (nth 8 tokenpart
) :pure-virtual-flag
) t
)
1062 ;; Template specifier.
1063 :template-specifier
(nth 9 tokenpart
)
1068 (defun semantic-c-reconstitute-template (tag specifier
)
1069 "Reconstitute the token TAG with the template SPECIFIER."
1070 (semantic-tag-put-attribute tag
:template
(or specifier
""))
1074 ;;; Override methods & Variables
1076 (define-mode-local-override semantic-format-tag-name
1077 c-mode
(tag &optional parent color
)
1078 "Convert TAG to a string that is the print name for TAG.
1079 Optional PARENT and COLOR are ignored."
1080 (let ((name (semantic-format-tag-name-default tag parent color
))
1081 (fnptr (semantic-tag-get-attribute tag
:functionpointer-flag
))
1085 (concat "(*" name
")"))
1088 (define-mode-local-override semantic-format-tag-canonical-name
1089 c-mode
(tag &optional parent color
)
1090 "Create a cannonical name for TAG.
1091 PARENT specifies a parent class.
1092 COLOR indicates that the text should be type colorized.
1093 Enhances the base class to search for the entire parent
1094 tree to make the name accurate."
1095 (semantic-format-tag-canonical-name-default tag parent color
)
1098 (define-mode-local-override semantic-format-tag-type c-mode
(tag color
)
1099 "Convert the data type of TAG to a string usable in tag formatting.
1100 Adds pointer and reference symbols to the default.
1101 Argument COLOR adds color to the text."
1102 (let* ((type (semantic-tag-type tag
))
1104 (point (semantic-tag-get-attribute tag
:pointer
))
1105 (ref (semantic-tag-get-attribute tag
:reference
))
1107 (if (semantic-tag-p type
)
1108 (let ((typetype (semantic-tag-type type
))
1109 (typename (semantic-tag-name type
)))
1110 ;; Create the string that expresses the type
1111 (if (string= typetype
"class")
1112 (setq defaulttype typename
)
1113 (setq defaulttype
(concat typetype
" " typename
))))
1114 (setq defaulttype
(semantic-format-tag-type-default tag color
)))
1118 (setq defaulttype
(semantic--format-colorize-text defaulttype
'type
)))
1120 ;; Add refs, ptrs, etc
1121 (if ref
(setq ref
"&"))
1122 (if point
(setq point
(make-string point ?
*)) "")
1124 (concat defaulttype ref point
))
1127 (define-mode-local-override semantic-find-tags-by-scope-protection
1128 c-mode
(scopeprotection parent
&optional table
)
1129 "Override the usual search for protection.
1130 We can be more effective than the default by scanning through once,
1131 and collecting tags based on the labels we see along the way."
1132 (if (not table
) (setq table
(semantic-tag-type-members parent
)))
1133 (if (null scopeprotection
)
1137 (targetprot (cond ((eq scopeprotection
'public
)
1139 ((eq scopeprotection
'protected
)
1143 (alist '(("public" .
1)
1149 ((semantic-tag-of-class-p tag
'label
)
1150 (setq curprot
(cdr (assoc (semantic-tag-name tag
) alist
)))
1152 ((>= targetprot curprot
)
1153 (setq ans
(cons tag ans
)))
1157 (define-mode-local-override semantic-tag-protection
1158 c-mode
(tag &optional parent
)
1159 "Return the protection of TAG in PARENT.
1160 Override function for `semantic-tag-protection'."
1161 (let ((mods (semantic-tag-modifiers tag
))
1163 ;; Check the modifiers for protection if we are not a child
1164 ;; of some class type.
1165 (when (or (not parent
) (not (eq (semantic-tag-class parent
) 'type
)))
1166 (while (and (not prot
) mods
)
1167 (if (stringp (car mods
))
1168 (let ((s (car mods
)))
1169 ;; A few silly defaults to get things started.
1170 (cond ((or (string= s
"extern")
1171 (string= s
"export"))
1173 ((string= s
"static")
1175 (setq mods
(cdr mods
))))
1176 ;; If we have a typed parent, look for :public style labels.
1177 (when (and parent
(eq (semantic-tag-class parent
) 'type
))
1178 (let ((pp (semantic-tag-type-members parent
)))
1179 (while (and pp
(not (semantic-equivalent-tag-p (car pp
) tag
)))
1180 (when (eq (semantic-tag-class (car pp
)) 'label
)
1182 (cond ((string= (semantic-tag-name (car pp
)) "public")
1184 ((string= (semantic-tag-name (car pp
)) "private")
1186 ((string= (semantic-tag-name (car pp
)) "protected")
1189 (setq pp
(cdr pp
)))))
1190 (when (and (not prot
) (eq (semantic-tag-class parent
) 'type
))
1192 (cond ((string= (semantic-tag-type parent
) "class") 'private
)
1193 ((string= (semantic-tag-type parent
) "struct") 'public
)
1196 (if (and parent
(semantic-tag-of-class-p parent
'type
))
1200 (define-mode-local-override semantic-tag-components c-mode
(tag)
1201 "Return components for TAG."
1202 (if (and (eq (semantic-tag-class tag
) 'type
)
1203 (string= (semantic-tag-type tag
) "typedef"))
1204 ;; A typedef can contain a parent who has positional children,
1205 ;; but that parent will not have a position. Do this funny hack
1206 ;; to make sure we can apply overlays properly.
1207 (let ((sc (semantic-tag-get-attribute tag
:typedef
)))
1208 (when (semantic-tag-p sc
) (semantic-tag-components sc
)))
1209 (semantic-tag-components-default tag
)))
1211 (defun semantic-c-tag-template (tag)
1212 "Return the template specification for TAG, or nil."
1213 (semantic-tag-get-attribute tag
:template
))
1215 (defun semantic-c-tag-template-specifier (tag)
1216 "Return the template specifier specification for TAG, or nil."
1217 (semantic-tag-get-attribute tag
:template-specifier
))
1219 (defun semantic-c-template-string-body (templatespec)
1220 "Convert TEMPLATESPEC into a string.
1221 This might be a string, or a list of tokens."
1222 (cond ((stringp templatespec
)
1224 ((semantic-tag-p templatespec
)
1225 (semantic-format-tag-abbreviate templatespec
))
1226 ((listp templatespec
)
1227 (mapconcat 'semantic-format-tag-abbreviate templatespec
", "))))
1229 (defun semantic-c-template-string (token &optional parent color
)
1230 "Return a string representing the TEMPLATE attribute of TOKEN.
1231 This string is prefixed with a space, or is the empty string.
1232 Argument PARENT specifies a parent type.
1233 Argument COLOR specifies that the string should be colorized."
1234 (let ((t2 (semantic-c-tag-template-specifier token
))
1235 (t1 (semantic-c-tag-template token
))
1236 ;; @todo - Need to account for a parent that is a template
1237 (pt1 (if parent
(semantic-c-tag-template parent
)))
1238 (pt2 (if parent
(semantic-c-tag-template-specifier parent
)))
1240 (cond (t2 ;; we have a template with specifier
1242 ;; Fill in the parts here
1243 (semantic-c-template-string-body t2
)
1245 (t1 ;; we have a template without specifier
1250 (define-mode-local-override semantic-format-tag-concise-prototype
1251 c-mode
(token &optional parent color
)
1252 "Return an abbreviated string describing TOKEN for C and C++.
1253 Optional PARENT and COLOR as specified with
1254 `semantic-format-tag-abbreviate-default'."
1255 ;; If we have special template things, append.
1256 (concat (semantic-format-tag-concise-prototype-default token parent color
)
1257 (semantic-c-template-string token parent color
)))
1259 (define-mode-local-override semantic-format-tag-uml-prototype
1260 c-mode
(token &optional parent color
)
1261 "Return an UML string describing TOKEN for C and C++.
1262 Optional PARENT and COLOR as specified with
1263 `semantic-abbreviate-tag-default'."
1264 ;; If we have special template things, append.
1265 (concat (semantic-format-tag-uml-prototype-default token parent color
)
1266 (semantic-c-template-string token parent color
)))
1268 (define-mode-local-override semantic-tag-abstract-p
1269 c-mode
(tag &optional parent
)
1270 "Return non-nil if TAG is considered abstract.
1271 PARENT is tag's parent.
1272 In C, a method is abstract if it is `virtual', which is already
1273 handled. A class is abstract iff it's destructor is virtual."
1275 ((eq (semantic-tag-class tag
) 'type
)
1276 (require 'semantic
/find
)
1277 (or (semantic-brute-find-tag-by-attribute :pure-virtual-flag
1278 (semantic-tag-components tag
)
1280 (let* ((ds (semantic-brute-find-tag-by-attribute
1282 (semantic-tag-components tag
)
1284 (cs (semantic-brute-find-tag-by-attribute
1286 (semantic-tag-components tag
)
1288 (and ds
(member "virtual" (semantic-tag-modifiers (car ds
)))
1289 cs
(eq 'protected
(semantic-tag-protection (car cs
) tag
))
1292 ((eq (semantic-tag-class tag
) 'function
)
1293 (or (semantic-tag-get-attribute tag
:pure-virtual-flag
)
1294 (member "virtual" (semantic-tag-modifiers tag
))))
1295 (t (semantic-tag-abstract-p-default tag parent
))))
1297 (defun semantic-c-dereference-typedef (type scope
&optional type-declaration
)
1298 "If TYPE is a typedef, get TYPE's type by name or tag, and return.
1299 SCOPE is not used, and TYPE-DECLARATION is used only if TYPE is not a typedef."
1300 (if (and (eq (semantic-tag-class type
) 'type
)
1301 (string= (semantic-tag-type type
) "typedef"))
1302 (let ((dt (semantic-tag-get-attribute type
:typedef
)))
1303 (cond ((and (semantic-tag-p dt
)
1304 (not (semantic-analyze-tag-prototype-p dt
)))
1305 ;; In this case, DT was declared directly. We need
1306 ;; to clone DT and apply a filename to it.
1307 (let* ((fname (semantic-tag-file-name type
))
1308 (def (semantic-tag-copy dt nil fname
)))
1310 ((stringp dt
) (list dt
(semantic-tag dt
'type
)))
1311 ((consp dt
) (list (car dt
) dt
))))
1313 (list type type-declaration
)))
1315 (defun semantic-c--instantiate-template (tag def-list spec-list
)
1316 "Replace TAG name according to template specification.
1317 DEF-LIST is the template information.
1318 SPEC-LIST is the template specifier of the datatype instantiated."
1319 (when (and (car def-list
) (car spec-list
))
1321 (when (and (string= (semantic-tag-type (car def-list
)) "class")
1322 (string= (semantic-tag-name tag
) (semantic-tag-name (car def-list
))))
1323 (semantic-tag-set-name tag
(semantic-tag-name (car spec-list
))))
1325 (semantic-c--instantiate-template tag
(cdr def-list
) (cdr spec-list
))))
1327 (defun semantic-c--template-name-1 (spec-list)
1328 "Return a string used to compute template class name.
1329 Based on SPEC-LIST, for ref<Foo,Bar> it will return 'Foo,Bar'."
1330 (when (car spec-list
)
1331 (let* ((endpart (semantic-c--template-name-1 (cdr spec-list
)))
1332 (separator (and endpart
",")))
1333 (concat (semantic-tag-name (car spec-list
)) separator endpart
))))
1335 (defun semantic-c--template-name (type spec-list
)
1336 "Return a template class name for TYPE based on SPEC-LIST.
1337 For a type `ref' with a template specifier of (Foo Bar) it will
1338 return 'ref<Foo,Bar>'."
1339 (concat (semantic-tag-name type
)
1340 "<" (semantic-c--template-name-1 (cdr spec-list
)) ">"))
1342 (defun semantic-c-dereference-template (type scope
&optional type-declaration
)
1343 "Dereference any template specifiers in TYPE within SCOPE.
1344 If TYPE is a template, return a TYPE copy with the templates types
1345 instantiated as specified in TYPE-DECLARATION."
1346 (when (semantic-tag-p type-declaration
)
1347 (let ((def-list (semantic-tag-get-attribute type
:template
))
1348 (spec-list (semantic-tag-get-attribute type-declaration
:template-specifier
)))
1349 (when (and def-list spec-list
)
1350 (setq type
(semantic-tag-deep-copy-one-tag
1353 (when (semantic-tag-of-class-p tag
'type
)
1354 (semantic-c--instantiate-template
1355 tag def-list spec-list
))
1358 (semantic-tag-set-name type
(semantic-c--template-name type spec-list
))
1359 (semantic-tag-put-attribute type
:template nil
)
1360 (semantic-tag-set-faux type
))))
1361 (list type type-declaration
))
1363 ;;; Patch here by "Raf" for instantiating templates.
1364 (defun semantic-c-dereference-member-of (type scope
&optional type-declaration
)
1365 "Dereference through the `->' operator of TYPE.
1366 Uses the return type of the '->' operator if it is contained in TYPE.
1367 SCOPE is the current local scope to perform searches in.
1368 TYPE-DECLARATION is passed through."
1369 (if semantic-c-member-of-autocast
1370 (let ((operator (car (semantic-find-tags-by-name "->" (semantic-analyze-scoped-type-parts type
)))))
1372 (list (semantic-tag-get-attribute operator
:type
) (semantic-tag-get-attribute operator
:type
))
1373 (list type type-declaration
)))
1374 (list type type-declaration
)))
1376 ;; David Engster: The following three functions deal with namespace
1377 ;; aliases and types which are member of a namespace through a using
1378 ;; statement. For examples, see the file semantic/tests/testusing.cpp,
1379 ;; tests 5 and following.
1381 (defun semantic-c-dereference-namespace (type scope
&optional type-declaration
)
1382 "Dereference namespace which might hold an 'alias' for TYPE.
1383 Such an alias can be created through 'using' statements in a
1384 namespace declaration. This function checks the namespaces in
1385 SCOPE for such statements."
1386 (let ((scopetypes (oref scope scopetypes
))
1387 typename currentns tmp usingname result namespaces
)
1388 (when (and (semantic-tag-p type-declaration
)
1389 (or (null type
) (semantic-tag-prototype-p type
)))
1390 (setq typename
(semantic-analyze-split-name (semantic-tag-name type-declaration
)))
1391 ;; If we already have that TYPE in SCOPE, we do nothing
1392 (unless (semantic-deep-find-tags-by-name (or (car-safe typename
) typename
) scopetypes
)
1393 (if (stringp typename
)
1394 ;; The type isn't fully qualified, so we have to search in all namespaces in SCOPE.
1395 (setq namespaces
(semantic-find-tags-by-type "namespace" scopetypes
))
1396 ;; This is a fully qualified name, so we only have to search one namespace.
1397 (setq namespaces
(semanticdb-typecache-find (car typename
)))
1398 ;; Make sure it's really a namespace.
1399 (if (string= (semantic-tag-type namespaces
) "namespace")
1400 (setq namespaces
(list namespaces
))
1401 (setq namespaces nil
)))
1403 ;; Iterate over all the namespaces we have to check.
1404 (while (and namespaces
1406 (setq currentns
(car namespaces
))
1407 ;; Check if this is namespace is an alias and dereference it if necessary.
1408 (setq result
(semantic-c-dereference-namespace-alias type-declaration currentns
))
1410 ;; Otherwise, check if we can reach the type through 'using' statements.
1412 (semantic-c-check-type-namespace-using type-declaration currentns
)))
1413 (setq namespaces
(cdr namespaces
)))))
1415 ;; we have found the original type
1416 (list result result
)
1417 (list type type-declaration
))))
1419 (defun semantic-c-dereference-namespace-alias (type namespace
)
1420 "Dereference TYPE in NAMESPACE, given that NAMESPACE is an alias.
1421 Checks if NAMESPACE is an alias and if so, returns a new type
1422 with a fully qualified name in the original namespace. Returns
1423 nil if NAMESPACE is not an alias."
1424 (when (eq (semantic-tag-get-attribute namespace
:kind
) 'alias
)
1425 (let ((typename (semantic-analyze-split-name (semantic-tag-name type
)))
1426 ns nstype originaltype newtype
)
1427 ;; Make typename unqualified
1428 (if (listp typename
)
1429 (setq typename
(last typename
))
1430 (setq typename
(list typename
)))
1433 ;; Get original namespace and make sure TYPE exists there.
1434 (setq ns
(semantic-tag-name
1435 (car (semantic-tag-get-attribute namespace
:members
))))
1436 (setq nstype
(semanticdb-typecache-find ns
))
1437 (setq originaltype
(semantic-find-tags-by-name
1439 (semantic-tag-get-attribute nstype
:members
))))
1440 ;; Construct new type with name in original namespace.
1441 (setq ns
(semantic-analyze-split-name ns
))
1445 (semantic-analyze-unsplit-name
1447 (append ns typename
)
1448 (append (list ns
) typename
)))))))))
1450 ;; This searches a type in a namespace, following through all using
1452 (defun semantic-c-check-type-namespace-using (type namespace
)
1453 "Check if TYPE is accessible in NAMESPACE through a using statement.
1454 Returns the original type from the namespace where it is defined,
1455 or nil if it cannot be found."
1456 (let (usings result usingname usingtype unqualifiedname members shortname tmp
)
1457 ;; Get all using statements from NAMESPACE.
1458 (when (and (setq usings
(semantic-tag-get-attribute namespace
:members
))
1459 (setq usings
(semantic-find-tags-by-class 'using usings
)))
1460 ;; Get unqualified typename.
1461 (when (listp (setq unqualifiedname
(semantic-analyze-split-name
1462 (semantic-tag-name type
))))
1463 (setq unqualifiedname
(car (last unqualifiedname
))))
1464 ;; Iterate over all using statements in NAMESPACE.
1467 (setq usingname
(semantic-analyze-split-name
1468 (semantic-tag-name (car usings
)))
1469 usingtype
(semantic-tag-type (semantic-tag-type (car usings
))))
1471 ((or (string= usingtype
"namespace")
1472 (stringp usingname
))
1473 ;; We are dealing with a 'using [namespace] NAMESPACE;'
1474 ;; Search for TYPE in that namespace
1476 (semanticdb-typecache-find usingname
))
1478 (setq members
(semantic-tag-get-attribute result
:members
))
1479 (setq members
(semantic-find-tags-by-name unqualifiedname members
)))
1480 ;; TYPE is member of that namespace, so we are finished
1481 (setq result
(car members
))
1482 ;; otherwise recursively search in that namespace for an alias
1483 (setq result
(semantic-c-check-type-namespace-using type result
))
1485 (setq result
(semantic-tag-type result
)))))
1486 ((and (string= usingtype
"class")
1488 ;; We are dealing with a 'using TYPE;'
1489 (when (string= unqualifiedname
(car (last usingname
)))
1490 ;; We have found the correct tag.
1491 (setq result
(semantic-tag-type (car usings
))))))
1492 (setq usings
(cdr usings
))))
1496 (define-mode-local-override semantic-analyze-dereference-metatype
1497 c-mode
(type scope
&optional type-declaration
)
1498 "Dereference TYPE as described in `semantic-analyze-dereference-metatype'.
1499 Handle typedef, template instantiation, and '->' operator."
1500 (let* ((dereferencer-list '(semantic-c-dereference-typedef
1501 semantic-c-dereference-template
1502 semantic-c-dereference-member-of
1503 semantic-c-dereference-namespace
))
1504 (dereferencer (pop dereferencer-list
))
1506 (original-type type
))
1508 (setq type-tuple
(funcall dereferencer type scope type-declaration
)
1509 type
(car type-tuple
)
1510 type-declaration
(cadr type-tuple
))
1511 (if (not (eq type original-type
))
1512 ;; we found a new type so break the dereferencer loop now !
1513 ;; (we will be recalled with the new type expanded by
1514 ;; semantic-analyze-dereference-metatype-stack).
1515 (setq dereferencer nil
)
1516 ;; no new type found try the next dereferencer :
1517 (setq dereferencer
(pop dereferencer-list
)))))
1518 (list type type-declaration
))
1520 (define-mode-local-override semantic-analyze-type-constants c-mode
(type)
1521 "When TYPE is a tag for an enum, return its parts.
1522 These are constants which are of type TYPE."
1523 (if (and (eq (semantic-tag-class type
) 'type
)
1524 (string= (semantic-tag-type type
) "enum"))
1525 (semantic-tag-type-members type
)))
1527 (define-mode-local-override semantic-analyze-split-name c-mode
(name)
1528 "Split up tag names on colon (:) boundaries."
1529 (let ((ans (split-string name
":")))
1530 (if (= (length ans
) 1)
1534 (define-mode-local-override semantic-analyze-unsplit-name c-mode
(namelist)
1535 "Assemble the list of names NAMELIST into a namespace name."
1536 (mapconcat 'identity namelist
"::"))
1538 (define-mode-local-override semantic-ctxt-scoped-types c
++-mode
(&optional point
)
1539 "Return a list of tags of CLASS type based on POINT.
1540 DO NOT return the list of tags encompassing point."
1541 (when point
(goto-char (point)))
1542 (let ((tagsaroundpoint (semantic-find-tag-by-overlay))
1545 ;; In C++, we want to find all the namespaces declared
1546 ;; locally and add them to the list.
1547 (setq tmp
(semantic-find-tags-by-class 'type
(current-buffer)))
1548 (setq tmp
(semantic-find-tags-by-type "namespace" tmp
))
1549 (setq tmp
(semantic-find-tags-by-name "unnamed" tmp
))
1550 (setq tagreturn tmp
)
1551 ;; We should also find all "using" type statements and
1552 ;; accept those entities in as well.
1553 (setq tmp
(semanticdb-find-tags-by-class 'using
))
1555 (len (semanticdb-find-result-length tmp
)))
1557 (setq tagreturn
(cons (semantic-tag-type (car (semanticdb-find-result-nth tmp idx
))) tagreturn
))
1558 (setq idx
(1+ idx
)))
1560 ;; Use the encompased types around point to also look for using statements.
1561 ;;(setq tagreturn (cons "bread_name" tagreturn))
1562 (while (cdr tagsaroundpoint
) ; don't search the last one
1563 (setq tmp
(semantic-find-tags-by-class 'using
(semantic-tag-components (car tagsaroundpoint
))))
1565 (setq tagreturn
(cons (semantic-tag-type T
) tagreturn
))
1567 (setq tagsaroundpoint
(cdr tagsaroundpoint
))
1569 ;; If in a function...
1570 (when (and (semantic-tag-of-class-p (car tagsaroundpoint
) 'function
)
1571 ;; ...search for using statements in the local scope...
1572 (setq tmp
(semantic-find-tags-by-class
1574 (semantic-get-local-variables))))
1575 ;; ... and add them.
1578 (mapcar 'semantic-tag-type tmp
))))
1583 (define-mode-local-override semantic-get-local-variables c
++-mode
()
1584 "Do what `semantic-get-local-variables' does, plus add `this' if needed."
1585 (let* ((origvar (semantic-get-local-variables-default))
1586 (ct (semantic-current-tag))
1587 (p (semantic-tag-function-parent ct
)))
1588 ;; If we have a function parent, then that implies we can
1589 (if (and p
(semantic-tag-of-class-p ct
'function
))
1590 ;; Append a new tag THIS into our space.
1591 (cons (semantic-tag-new-variable "this" p nil
)
1593 ;; No parent, just return the usual
1597 (define-mode-local-override semantic-idle-summary-current-symbol-info
1599 "Handle the SPP keywords, then use the default mechanism."
1600 (let* ((sym (car (semantic-ctxt-current-thing)))
1601 (spp-sym (semantic-lex-spp-symbol sym
)))
1603 (let* ((txt (concat "Macro: " sym
))
1604 (sv (symbol-value spp-sym
))
1605 (arg (semantic-lex-spp-macro-with-args sv
))
1608 (setq txt
(concat txt
(format "%S" arg
)))
1611 ;; This is optional, and potentially fraught w/ errors.
1614 (setq txt
(concat txt
" " (semantic-lex-token-text lt
))))
1615 (error (setq txt
(concat txt
" #error in summary fcn"))))
1618 (semantic-idle-summary-current-symbol-info-default))))
1620 (defvar-mode-local c-mode semantic-orphaned-member-metaparent-type
"struct"
1621 "When lost members are found in the class hierarchy generator, use a struct.")
1623 (defvar-mode-local c-mode semantic-symbol-
>name-assoc-list
1625 (variable .
"Variables")
1626 (function .
"Functions")
1627 (include .
"Includes")
1629 "List of tag classes, and strings to describe them.")
1631 (defvar-mode-local c-mode semantic-symbol-
>name-assoc-list-for-type-parts
1633 (variable .
"Attributes")
1634 (function .
"Methods")
1637 "List of tag classes in a datatype decl, and strings to describe them.")
1639 (defvar-mode-local c-mode imenu-create-index-function
'semantic-create-imenu-index
1640 "Imenu index function for C.")
1642 (defvar-mode-local c-mode semantic-type-relation-separator-character
1644 "Separator characters between something of a given type, and a field.")
1646 (defvar-mode-local c-mode semantic-command-separation-character
";"
1647 "Command separation character for C.")
1649 (defvar-mode-local c-mode senator-step-at-tag-classes
'(function variable
)
1650 "Tag classes where senator will stop at the end.")
1653 (defun semantic-default-c-setup ()
1654 "Set up a buffer for semantic parsing of the C language."
1655 (semantic-c-by--install-parser)
1656 (setq semantic-lex-syntax-modifications
'((?
> ".")
1661 (setq semantic-lex-analyzer
#'semantic-c-lexer
)
1662 (add-hook 'semantic-lex-reset-hooks
'semantic-lex-spp-reset-hook nil t
)
1666 (defun semantic-c-add-preprocessor-symbol (sym replacement
)
1667 "Add a preprocessor symbol SYM with a REPLACEMENT value."
1668 (interactive "sSymbol: \nsReplacement: ")
1669 (let ((SA (assoc sym semantic-lex-c-preprocessor-symbol-map
)))
1671 ;; Replace if there is one.
1672 (setcdr SA replacement
)
1673 ;; Otherwise, append
1674 (setq semantic-lex-c-preprocessor-symbol-map
1675 (cons (cons sym replacement
)
1676 semantic-lex-c-preprocessor-symbol-map
))))
1678 (semantic-c-reset-preprocessor-symbol-map)
1683 (defun semantic-c-describe-environment ()
1684 "Describe the Semantic features of the current C environment."
1686 (if (not (or (eq major-mode
'c-mode
) (eq major-mode
'c
++-mode
)))
1687 (error "Not useful to query C mode in %s mode" major-mode
))
1688 (let ((gcc (when (boundp 'semantic-gcc-setup-data
)
1689 semantic-gcc-setup-data
))
1691 (semantic-fetch-tags)
1693 (with-output-to-temp-buffer "*Semantic C Environment*"
1695 (princ "Calculated GCC Parameters:")
1704 (princ "\n\nInclude Path Summary:\n")
1705 (when (and (boundp 'ede-object
) ede-object
)
1706 (princ "\n This file's project include is handled by:\n")
1708 (princ (object-print ede-object
))
1709 (princ "\n with the system path:\n")
1710 (dolist (dir (ede-system-include-path ede-object
))
1716 (when semantic-dependency-include-path
1717 (princ "\n This file's generic include path is:\n")
1718 (dolist (dir semantic-dependency-include-path
)
1723 (when semantic-dependency-system-include-path
1724 (princ "\n This file's system include path is:\n")
1725 (dolist (dir semantic-dependency-system-include-path
)
1730 (princ "\n\nMacro Summary:\n")
1731 (when semantic-lex-c-preprocessor-symbol-file
1732 (princ "\n Your CPP table is primed from these files:\n")
1733 (dolist (file semantic-lex-c-preprocessor-symbol-file
)
1737 (princ " in table: ")
1738 (princ (object-print (semanticdb-file-table-object file
)))
1742 (when semantic-lex-c-preprocessor-symbol-map-builtin
1743 (princ "\n Built-in symbol map:\n")
1744 (dolist (S semantic-lex-c-preprocessor-symbol-map-builtin
)
1752 (when semantic-lex-c-preprocessor-symbol-map
1753 (princ "\n User symbol map:\n")
1754 (dolist (S semantic-lex-c-preprocessor-symbol-map
)
1762 (when (arrayp semantic-lex-spp-project-macro-symbol-obarray
)
1763 (princ "\n Project symbol map:\n")
1764 (when (and (boundp 'ede-object
) ede-object
)
1765 (princ " Your project symbol map is derived from the EDE object:\n ")
1766 (princ (object-print ede-object
)))
1771 (setq macros
(cons symbol macros
)))
1772 semantic-lex-spp-project-macro-symbol-obarray
)
1775 (princ (symbol-name S
))
1777 (princ (symbol-value S
))
1781 (princ "\n\n Use: M-x semantic-lex-spp-describe RET\n")
1782 (princ "\n to see the complete macro table.\n")
1786 (provide 'semantic
/bovine
/c
)
1788 (semantic-c-reset-preprocessor-symbol-map)
1791 ;; generated-autoload-file: "../loaddefs.el"
1792 ;; generated-autoload-load-name: "semantic/bovine/c"
1795 ;; arch-tag: 263951a8-0f18-445d-8e73-eb8f9ac8e2a3
1796 ;;; semantic/bovine/c.el ends here