Function: c-skip-comments-and-strings
c-skip-comments-and-strings is a byte-compiled function defined in
cc-fonts.el.gz.
Signature
(c-skip-comments-and-strings LIMIT)
Source Code
;; Defined in /usr/src/emacs/lisp/progmodes/cc-fonts.el.gz
(eval-and-compile
;; We need the following definitions during compilation since they're
;; used when the `c-lang-defconst' initializers are evaluated. Define
;; them at runtime too for the sake of derived modes.
;; This indicates the "font locking context", and is set just before
;; fontification is done. If non-nil, it says, e.g., point starts
;; from within a #if preprocessor construct.
(defvar c-font-lock-context nil)
(make-variable-buffer-local 'c-font-lock-context)
(defmacro c-put-font-lock-face (from to face)
;; Put a face on a region (overriding any existing face) in the way
;; font-lock would do it. In XEmacs that means putting an
;; additional font-lock property, or else the font-lock package
;; won't recognize it as fontified and might override it
;; incorrectly.
;;
;; This function does a hidden buffer change.
(declare (debug t))
(if (fboundp 'font-lock-set-face)
;; Note: This function has no docstring in XEmacs so it might be
;; considered internal.
`(font-lock-set-face ,from ,to ,face)
`(put-text-property ,from ,to 'face ,face)))
(defmacro c-remove-font-lock-face (from to)
;; This is the inverse of `c-put-font-lock-face'.
;;
;; This function does a hidden buffer change.
(declare (debug t))
(if (fboundp 'font-lock-remove-face)
`(font-lock-remove-face ,from ,to)
`(remove-text-properties ,from ,to '(face nil))))
(defmacro c-put-font-lock-string-face (from to)
;; Put `font-lock-string-face' on a string. The surrounding
;; quotes are included in Emacs but not in XEmacs. The passed
;; region should include them.
;;
;; This function does a hidden buffer change.
(declare (debug t))
(if (featurep 'xemacs)
`(c-put-font-lock-face (1+ ,from) (1- ,to) 'font-lock-string-face)
`(c-put-font-lock-face ,from ,to 'font-lock-string-face)))
(defmacro c-fontify-types-and-refs (varlist &rest body)
(declare (indent 1) (debug let*))
;; Like `let*', but additionally activates `c-record-type-identifiers'
;; and `c-record-ref-identifiers', and fontifies the recorded ranges
;; accordingly on exit.
;;
;; This function does hidden buffer changes.
`(let* ((c-record-type-identifiers t)
c-record-ref-identifiers
,@varlist)
(prog1 (progn ,@body)
(c-fontify-recorded-types-and-refs))))
(defun c-skip-comments-and-strings (limit)
;; If the point is within a region fontified as a comment or
;; string literal skip to the end of it or to LIMIT, whichever
;; comes first, and return t. Otherwise return nil. The match
;; data is not clobbered.
;;
;; This function might do hidden buffer changes.
(when (c-got-face-at (point) c-literal-faces)
(while (progn
(goto-char (c-next-single-property-change
(point) 'face nil limit))
(and (< (point) limit)
(c-got-face-at (point) c-literal-faces))))
t))
(defun c-make-syntactic-matcher (regexp)
;; Returns a byte compiled function suitable for use in place of a
;; regexp string in a `font-lock-keywords' matcher, except that
;; only matches outside comments and string literals count.
;;
;; This function does not do any hidden buffer changes, but the
;; generated functions will. (They are however used in places
;; covered by the font-lock context.)
(byte-compile
`(lambda (limit)
(let (res)
(c-skip-comments-and-strings limit)
(while (and (setq res (re-search-forward ,regexp limit t))
(progn
(goto-char (match-beginning 0))
(or (c-skip-comments-and-strings limit)
(progn
(goto-char (match-end 0))
nil)))))
res))))
(defun c-make-font-lock-search-form (regexp highlights &optional check-point)
;; Return a lisp form which will fontify every occurrence of REGEXP
;; (a regular expression, NOT a function) between POINT and `limit'
;; with HIGHLIGHTS, a list of highlighters as specified on page
;; "Search-based Fontification" in the elisp manual. If CHECK-POINT
;; is non-nil, we will check (< (point) limit) in the main loop.
`(progn
(c-skip-comments-and-strings limit)
(while
,(if check-point
`(and (< (point) limit)
(re-search-forward ,regexp limit t))
`(re-search-forward ,regexp limit t))
(unless (progn
(goto-char (match-beginning 0))
(c-skip-comments-and-strings limit))
(goto-char (match-end 0))
,@(mapcar
(lambda (highlight)
(if (integerp (car highlight))
;; e.g. highlight is (1 font-lock-type-face t)
(progn
(unless (eq (nth 2 highlight) t)
(error
"The override flag must currently be t in %s"
highlight))
(when (nth 3 highlight)
(error
"The laxmatch flag may currently not be set in %s"
highlight))
`(save-match-data
(c-put-font-lock-face
(match-beginning ,(car highlight))
(match-end ,(car highlight))
,(elt highlight 1))))
;; highlight is an "ANCHORED HIGHLIGHTER" of the form
;; (ANCHORED-MATCHER PRE-FORM POST-FORM SUBEXP-HIGHLIGHTERS...)
(when (nth 3 highlight)
(error "Match highlights currently not supported in %s"
highlight))
`(progn
,(nth 1 highlight)
(save-match-data ,(car highlight))
,(nth 2 highlight))))
highlights)))))
(defun c-make-font-lock-search-function (regexp &rest highlights)
;; This function makes a byte compiled function that works much like
;; a matcher element in `font-lock-keywords'. It cuts out a little
;; bit of the overhead compared to a real matcher. The main reason
;; is however to pass the real search limit to the anchored
;; matcher(s), since most (if not all) font-lock implementations
;; arbitrarily limit anchored matchers to the same line, and also
;; to insulate against various other irritating differences between
;; the different (X)Emacs font-lock packages.
;;
;; REGEXP is the matcher, which must be a regexp. Only matches
;; where the beginning is outside any comment or string literal are
;; significant.
;;
;; HIGHLIGHTS is a list of highlight specs, just like in
;; `font-lock-keywords', with these limitations: The face is always
;; overridden (no big disadvantage, since hits in comments etc are
;; filtered anyway), there is no "laxmatch", and an anchored matcher
;; is always a form which must do all the fontification directly.
;; `limit' is a variable bound to the real limit in the context of
;; the anchored matcher forms.
;;
;; This function does not do any hidden buffer changes, but the
;; generated functions will. (They are however used in places
;; covered by the font-lock context.)
;; Note: Replace `byte-compile' with `eval' to debug the generated
;; lambda more easily.
(byte-compile
`(lambda (limit)
(let ( ;; The font-lock package in Emacs is known to clobber
;; `parse-sexp-lookup-properties' (when it exists).
(parse-sexp-lookup-properties
(cc-eval-when-compile
(boundp 'parse-sexp-lookup-properties))))
,(c-make-font-lock-search-form regexp highlights t))
nil)))
(defun c-make-font-lock-BO-decl-search-function (regexp &rest highlights)
;; This function makes a byte compiled function that first moves back
;; to the beginning of the current declaration (if any), then searches
;; forward for matcher elements (as in `font-lock-keywords') and
;; fontifies them.
;;
;; The motivation for moving back to the declaration start is to
;; establish a context for the current text when, e.g., a character
;; is typed on a C++ inheritance continuation line, or a jit-lock
;; chunk starts there.
;;
;; The new function works much like a matcher element in
;; `font-lock-keywords'. It cuts out a little bit of the overhead
;; compared to a real matcher. The main reason is however to pass the
;; real search limit to the anchored matcher(s), since most (if not
;; all) font-lock implementations arbitrarily limit anchored matchers
;; to the same line, and also to insulate against various other
;; irritating differences between the different (X)Emacs font-lock
;; packages.
;;
;; REGEXP is the matcher, which must be a regexp. Only matches
;; where the beginning is outside any comment or string literal are
;; significant.
;;
;; HIGHLIGHTS is a list of highlight specs, just like in
;; `font-lock-keywords', with these limitations: The face is always
;; overridden (no big disadvantage, since hits in comments etc are
;; filtered anyway), there is no "laxmatch", and an anchored matcher
;; is always a form which must do all the fontification directly.
;; `limit' is a variable bound to the real limit in the context of
;; the anchored matcher forms.
;;
;; This function does not do any hidden buffer changes, but the
;; generated functions will. (They are however used in places
;; covered by the font-lock context.)
;; Note: Replace `byte-compile' with `eval' to debug the generated
;; lambda more easily.
(byte-compile
`(lambda (limit)
(let ((lit-start (c-literal-start)))
(when lit-start (goto-char lit-start)))
(let ( ;; The font-lock package in Emacs is known to clobber
;; `parse-sexp-lookup-properties' (when it exists).
(parse-sexp-lookup-properties
(cc-eval-when-compile
(boundp 'parse-sexp-lookup-properties)))
(BOD-limit
(c-determine-limit 1000)))
(goto-char
(let ((here (point)))
(if (eq (car (c-beginning-of-decl-1 BOD-limit)) 'same)
(point)
here)))
,(c-make-font-lock-search-form regexp highlights))
nil)))
(defun c-make-font-lock-context-search-function (normal &rest state-stanzas)
;; This function makes a byte compiled function that works much like
;; a matcher element in `font-lock-keywords', with the following
;; enhancement: the generated function will test for particular "font
;; lock contexts" at the start of the region, i.e. is this point in
;; the middle of some particular construct? if so the generated
;; function will first fontify the tail of the construct, before
;; going into the main loop and fontify full constructs up to limit.
;;
;; The generated function takes one parameter called `limit', and
;; will fontify the region between POINT and LIMIT.
;;
;; NORMAL is a list of the form (REGEXP HIGHLIGHTS .....), and is
;; used to fontify the "regular" bit of the region.
;; STATE-STANZAS is list of elements of the form (STATE LIM REGEXP
;; HIGHLIGHTS), each element coding one possible font lock context.
;; o - REGEXP is a font-lock regular expression (NOT a function),
;; o - HIGHLIGHTS is a list of zero or more highlighters as defined
;; on page "Search-based Fontification" in the elisp manual. As
;; yet (2009-06), they must have OVERRIDE set, and may not have
;; LAXMATCH set.
;;
;; o - STATE is the "font lock context" (e.g. in-cpp-expr) and is
;; not quoted.
;; o - LIM is a lisp form whose evaluation will yield the limit
;; position in the buffer for fontification by this stanza.
;;
;; This function does not do any hidden buffer changes, but the
;; generated functions will. (They are however used in places
;; covered by the font-lock context.)
;;
;; Note: Replace `byte-compile' with `eval' to debug the generated
;; lambda more easily.
(byte-compile
`(lambda (limit)
(let ( ;; The font-lock package in Emacs is known to clobber
;; `parse-sexp-lookup-properties' (when it exists).
(parse-sexp-lookup-properties
(cc-eval-when-compile
(boundp 'parse-sexp-lookup-properties))))
,@(mapcar
(lambda (stanza)
(let ((state (car stanza))
(lim (nth 1 stanza))
(regexp (nth 2 stanza))
(highlights (cdr (cddr stanza))))
`(if (eq c-font-lock-context ',state)
(let ((limit ,lim))
,(c-make-font-lock-search-form
regexp highlights)))))
state-stanzas)
;; In the next form, check that point hasn't been moved beyond
;; `limit' in any of the above stanzas.
,(c-make-font-lock-search-form (car normal) (cdr normal) t)
nil)))))