1 ;;; dts-mode.el --- Major mode for Devicetree source code
3 ;; Copyright (C) 2014 Ben Gamari
6 ;; Author: Ben Gamari <ben@smart-cactus.org>
9 ;; This program is free software; you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation, either version 3 of the License, or
12 ;; (at your option) any later version.
14 ;; This program is distributed in the hope that it will be useful,
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 ;; GNU General Public License for more details.
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with this program. If not, see <http://www.gnu.org/licenses/>.
28 (defconst dts-re-ident "\\([[:word:]_][[:word:][:multibyte:]_,[:digit:]-]*\\)")
30 (defvar dts-mode-font-lock-keywords
32 ;; names like `name: hi {`
33 (,(concat dts-re-ident ":") 1 font-lock-variable-name-face)
35 (,(concat dts-re-ident "\\(@[[:xdigit:]]+\\)?[[:space:]]*{") 1 font-lock-type-face)
37 (,(concat dts-re-ident "[[:space:]]*=") 1 font-lock-variable-name-face)
38 (,(concat dts-re-ident "[[:space:]]*;") 1 font-lock-variable-name-face)
40 (,(concat "\\&" dts-re-ident) 1 font-lock-variable-name-face)
44 (defvar dts-mode-syntax-table
45 (let ((table (make-syntax-table)))
46 (modify-syntax-entry ?< "(" table)
47 (modify-syntax-entry ?> ")" table)
49 (modify-syntax-entry ?& "." table)
50 (modify-syntax-entry ?| "." table)
51 (modify-syntax-entry ?& "." table)
52 (modify-syntax-entry ?~ "." table)
54 ;; _ and , are both word characters
55 (modify-syntax-entry ?, "_" table)
56 (modify-syntax-entry ?_ "w" table)
59 (modify-syntax-entry ?\" "\"" table)
60 (modify-syntax-entry ?\\ "\\" table)
63 (modify-syntax-entry ?/ ". 124b" table)
64 (modify-syntax-entry ?* ". 23" table)
65 (modify-syntax-entry ?\n "> b" table)
66 (modify-syntax-entry ?\^m "> b" table)
70 (defun dts--calculate-indentation ()
73 (let ((end (point-at-eol))
75 (initial-point (point)))
77 (while (re-search-forward "\\([{}]\\)" end t)
78 (if (string= (match-string-no-properties 0) "{")
81 ;; subtract one if the current line has an opening brace since we
82 ;; shouldn't add the indentation level until the following line
83 (goto-char initial-point)
85 (when (re-search-forward "{" (point-at-eol) t)
89 (defun dts-indent-line ()
91 (let ((indent (dts--calculate-indentation)))
92 (indent-line-to (* indent tab-width))))
94 (defalias 'dts-parent-mode
95 (if (fboundp 'prog-mode) 'prog-mode 'fundamental-mode))
98 (define-derived-mode dts-mode dts-parent-mode "Devicetree"
99 "Major mode for editing Devicetrees"
101 :syntax-table dts-mode-syntax-table
104 (set (make-local-variable 'font-lock-defaults) '(dts-mode-font-lock-keywords nil nil nil nil))
106 (set (make-local-variable 'comment-start) "/* ")
107 (set (make-local-variable 'comment-end) " */")
108 (set (make-local-variable 'comment-multi-line) t)
109 (set (make-local-variable 'indent-line-function) 'dts-indent-line))
112 (add-to-list 'auto-mode-alist '("\\.dts\\'" . dts-mode))
114 (add-to-list 'auto-mode-alist '("\\.dtsi\\'" . dts-mode))
117 ;;; dts-mode.el ends here