1565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;;; gyp.el - font-lock-mode support for gyp files.
2565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
3565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;; Copyright (c) 2012 Google Inc. All rights reserved.
4565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;; Use of this source code is governed by a BSD-style license that can be
5565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;; found in the LICENSE file.
6565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
7565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;; Put this somewhere in your load-path and
8565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;; (require 'gyp)
9565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
10565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(require 'python)
11565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(require 'cl)
12565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
13565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(when (string-match "python-mode.el" (symbol-file 'python-mode 'defun))
14565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (error (concat "python-mode must be loaded from python.el (bundled with "
15565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 "recent emacsen), not from the older and less maintained "
16565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 "python-mode.el")))
17565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
1880a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org(defadvice python-indent-calculate-levels (after gyp-outdent-closing-parens
1980a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org                                                 activate)
20565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "De-indent closing parens, braces, and brackets in gyp-mode."
2180a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org  (when (and (eq major-mode 'gyp-mode)
2280a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org             (string-match "^ *[])}][],)}]* *$"
2380a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org                           (buffer-substring-no-properties
2480a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org                            (line-beginning-position) (line-end-position))))
2580a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org    (setf (first python-indent-levels)
2680a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org          (- (first python-indent-levels) python-indent-offset))))
27565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
28565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(define-derived-mode gyp-mode python-mode "Gyp"
29565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Major mode for editing .gyp files. See http://code.google.com/p/gyp/"
30565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; gyp-parse-history is a stack of (POSITION . PARSE-STATE) tuples,
31565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; with greater positions at the top of the stack. PARSE-STATE
32565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; is a list of section symbols (see gyp-section-name and gyp-parse-to)
33565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; with most nested section symbol at the front of the list.
34565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (set (make-local-variable 'gyp-parse-history) '((1 . (list))))
35565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (gyp-add-font-lock-keywords))
36565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
37565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-set-indentation ()
38565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Hook function to configure python indentation to suit gyp mode."
39565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (setq python-continuation-offset 2
4080a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org        python-indent-offset 2
4180a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org        python-indent-guess-indent-offset nil))
42565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
43565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(add-hook 'gyp-mode-hook 'gyp-set-indentation)
44565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
45565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(add-to-list 'auto-mode-alist '("\\.gyp\\'" . gyp-mode))
46565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(add-to-list 'auto-mode-alist '("\\.gypi\\'" . gyp-mode))
476633baab29b60f27e3dca607ffbef689ccdd82b8fischman@chromium.org(add-to-list 'auto-mode-alist '("/\\.gclient\\'" . gyp-mode))
48565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
49565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;;; Font-lock support
50565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
51565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-dependencies-regexp
52565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (regexp-opt (list "dependencies" "export_dependent_settings"))
53565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce 'dependencies' section")
54565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
55565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-sources-regexp
56565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (regexp-opt (list "action" "files" "include_dirs" "includes" "inputs"
57565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                    "libraries" "outputs" "sources"))
58565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce 'sources' sections")
59565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
60565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-conditions-regexp
61565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (regexp-opt (list "conditions" "target_conditions"))
62565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce conditions sections")
63565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
64565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-variables-regexp
65565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "^variables"
66565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce variables sections")
67565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
68565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-defines-regexp
69565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "^defines"
70565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce 'defines' sections")
71565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
72565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defconst gyp-targets-regexp
73565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "^targets"
74565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Regular expression to introduce 'targets' sections")
75565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
76565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-section-name (section)
77565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Map the sections we are interested in from SECTION to symbol.
78565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
79565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   SECTION is a string from the buffer that introduces a section.  The result is
80565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   a symbol representing the kind of section.
81565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
82565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   This allows us to treat (for the purposes of font-lock) several different
83565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   section names as the same kind of section. For example, a 'sources section
84565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   can be introduced by the 'sources', 'inputs', 'outputs' keyword.
85565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
86565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   'other is the default section kind when a more specific match is not made."
87565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (cond ((string-match-p gyp-dependencies-regexp section) 'dependencies)
88565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        ((string-match-p gyp-sources-regexp section) 'sources)
89565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        ((string-match-p gyp-variables-regexp section) 'variables)
90565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        ((string-match-p gyp-conditions-regexp section) 'conditions)
91565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        ((string-match-p gyp-targets-regexp section) 'targets)
92565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        ((string-match-p gyp-defines-regexp section) 'defines)
93565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (t 'other)))
94565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
95565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-invalidate-parse-states-after (target-point)
96565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Erase any parse information after target-point."
97565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (while (> (caar gyp-parse-history) target-point)
98565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (setq gyp-parse-history (cdr gyp-parse-history))))
99565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
100565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-parse-point ()
101565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "The point of the last parse state added by gyp-parse-to."
102565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (caar gyp-parse-history))
103565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
104565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-parse-sections ()
105565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "A list of section symbols holding at the last parse state point."
106565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (cdar gyp-parse-history))
107565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
108565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-inside-dictionary-p ()
109565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Predicate returning true if the parser is inside a dictionary."
110565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (not (eq (cadar gyp-parse-history) 'list)))
111565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
112565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-add-parse-history (point sections)
113565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Add parse state SECTIONS to the parse history at POINT so that parsing can be
114565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   resumed instantly."
115565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (while (>= (caar gyp-parse-history) point)
116565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (setq gyp-parse-history (cdr gyp-parse-history)))
117565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (setq gyp-parse-history (cons (cons point sections) gyp-parse-history)))
118565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
119565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-parse-to (target-point)
120565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Parses from (point) to TARGET-POINT adding the parse state information to
121565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   gyp-parse-state-history. Parsing stops if TARGET-POINT is reached or if a
122565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   string literal has been parsed. Returns nil if no further parsing can be
123565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   done, otherwise returns the position of the start of a parsed string, leaving
124565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   the point at the end of the string."
125565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (let ((parsing t)
126565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        string-start)
127565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (while parsing
128565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      (setq string-start nil)
129565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      ;; Parse up to a character that starts a sexp, or if the nesting
130565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      ;; level decreases.
131565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      (let ((state (parse-partial-sexp (gyp-parse-point)
132565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                       target-point
133565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                       -1
134565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                       t))
135565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org            (sections (gyp-parse-sections)))
136565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (if (= (nth 0 state) -1)
137565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org            (setq sections (cdr sections)) ; pop out a level
138565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (cond ((looking-at-p "['\"]") ; a string
139565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (setq string-start (point))
1407ab1ab090dfda4d004430d2f579edfc154158aa1tony@chromium.org                 (goto-char (scan-sexps (point) 1))
141565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (if (gyp-inside-dictionary-p)
142565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                     ;; Look for sections inside a dictionary
143565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                     (let ((section (gyp-section-name
144565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                     (buffer-substring-no-properties
145565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                      (+ 1 string-start)
146565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                      (- (point) 1)))))
147565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                       (setq sections (cons section (cdr sections)))))
148565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 ;; Stop after the string so it can be fontified.
149565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (setq target-point (point)))
150565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                ((looking-at-p "{")
151565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 ;; Inside a dictionary. Increase nesting.
152565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (forward-char 1)
153565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (setq sections (cons 'unknown sections)))
154565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                ((looking-at-p "\\[")
155565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 ;; Inside a list. Increase nesting
156565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (forward-char 1)
157565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (setq sections (cons 'list sections)))
158565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                ((not (eobp))
159565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 ;; other
160565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                 (forward-char 1))))
161565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (gyp-add-parse-history (point) sections)
162565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (setq parsing (< (point) target-point))))
163565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    string-start))
164565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
165565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-section-at-point ()
166565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Transform the last parse state, which is a list of nested sections and return
167565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   the section symbol that should be used to determine font-lock information for
168565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   the string. Can return nil indicating the string should not have any attached
169565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   section."
170565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (let ((sections (gyp-parse-sections)))
171565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (cond
172565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org     ((eq (car sections) 'conditions)
173565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      ;; conditions can occur in a variables section, but we still want to
174565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      ;; highlight it as a keyword.
175565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      nil)
176565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org     ((and (eq (car sections) 'list)
177565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org           (eq (cadr sections) 'list))
178565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      ;; conditions and sources can have items in [[ ]]
179565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      (caddr sections))
180565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org     (t (cadr sections)))))
181565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
182565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-section-match (limit)
183565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Parse from (point) to LIMIT returning by means of match data what was
184565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   matched. The group of the match indicates what style font-lock should apply.
185565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   See also `gyp-add-font-lock-keywords'."
186565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (gyp-invalidate-parse-states-after (point))
187565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (let ((group nil)
188565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (string-start t))
189565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (while (and (< (point) limit)
190565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                (not group)
191565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                string-start)
192565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      (setq string-start (gyp-parse-to limit))
193565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org      (if string-start
194565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (setq group (case (gyp-section-at-point)
195565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        ('dependencies 1)
196565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        ('variables 2)
197565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        ('conditions 2)
198565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        ('sources 3)
199565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        ('defines 4)
200565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                        (nil nil)))))
201565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (if group
202565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org        (progn
203565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          ;; Set the match data to indicate to the font-lock mechanism the
204565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          ;; highlighting to be performed.
205565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (set-match-data (append (list string-start (point))
206565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                  (make-list (* (1- group) 2) nil)
207565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                  (list (1+ string-start) (1- (point)))))
208565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          t))))
209565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
210565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;;; Please see http://code.google.com/p/gyp/wiki/GypLanguageSpecification for
211565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org;;; canonical list of keywords.
212565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(defun gyp-add-font-lock-keywords ()
213565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  "Add gyp-mode keywords to font-lock mechanism."
214565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; TODO(jknotten): Move all the keyword highlighting into gyp-section-match
215565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  ;; so that we can do the font-locking in a single font-lock pass.
216565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org  (font-lock-add-keywords
217565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   nil
218565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org   (list
219565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    ;; Top-level keywords
220565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list (concat "['\"]\\("
221565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org              (regexp-opt (list "action" "action_name" "actions" "cflags"
22280a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org                                "cflags_cc" "conditions" "configurations"
22380a221d3ac203103385d7ad0d67454f0b0b6a3aethakis@chromium.org                                "copies" "defines" "dependencies" "destination"
224565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "direct_dependent_settings"
225565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "export_dependent_settings" "extension" "files"
226565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "include_dirs" "includes" "inputs" "libraries"
227565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "link_settings" "mac_bundle" "message"
228565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "msvs_external_rule" "outputs" "product_name"
229565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "process_outputs_as_sources" "rules" "rule_name"
230565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "sources" "suppress_wildcard"
231565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "target_conditions" "target_defaults"
232565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "target_defines" "target_name" "toolsets"
233565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "targets" "type" "variables" "xcode_settings"))
234565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org              "[!/+=]?\\)") 1 'font-lock-keyword-face t)
235565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    ;; Type of target
236565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list (concat "['\"]\\("
237565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org              (regexp-opt (list "loadable_module" "static_library"
238565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org                                "shared_library" "executable" "none"))
239565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org              "\\)") 1 'font-lock-type-face t)
240565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list "\\(?:target\\|action\\)_name['\"]\\s-*:\\s-*['\"]\\([^ '\"]*\\)" 1
241565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          'font-lock-function-name-face t)
242565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list 'gyp-section-match
243565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (list 1 'font-lock-function-name-face t t) ; dependencies
244565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (list 2 'font-lock-variable-name-face t t) ; variables, conditions
245565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (list 3 'font-lock-constant-face t t) ; sources
246565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org          (list 4 'font-lock-preprocessor-face t t)) ; preprocessor
247565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    ;; Variable expansion
248565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list "<@?(\\([^\n )]+\\))" 1 'font-lock-variable-name-face t)
249565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    ;; Command expansion
250565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    (list "<!@?(\\([^\n )]+\\))" 1 'font-lock-variable-name-face t)
251565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org    )))
252565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org
253565fc074670ca3a171c2a7eb9e934b5080a153e2thakis@chromium.org(provide 'gyp)
254