|
1 # -*- coding: utf-8 -*- |
|
2 """ |
|
3 pygments.lexers.dsls |
|
4 ~~~~~~~~~~~~~~~~~~~~ |
|
5 |
|
6 Lexers for various domain-specific languages. |
|
7 |
|
8 :copyright: Copyright 2006-2017 by the Pygments team, see AUTHORS. |
|
9 :license: BSD, see LICENSE for details. |
|
10 """ |
|
11 |
|
12 import re |
|
13 |
|
14 from pygments.lexer import ExtendedRegexLexer, RegexLexer, bygroups, words, \ |
|
15 include, default, this, using, combined |
|
16 from pygments.token import Text, Comment, Operator, Keyword, Name, String, \ |
|
17 Number, Punctuation, Literal, Whitespace |
|
18 |
|
19 __all__ = ['ProtoBufLexer', 'BroLexer', 'PuppetLexer', 'RslLexer', |
|
20 'MscgenLexer', 'VGLLexer', 'AlloyLexer', 'PanLexer', |
|
21 'CrmshLexer', 'ThriftLexer', 'FlatlineLexer', 'SnowballLexer'] |
|
22 |
|
23 |
|
24 class ProtoBufLexer(RegexLexer): |
|
25 """ |
|
26 Lexer for `Protocol Buffer <http://code.google.com/p/protobuf/>`_ |
|
27 definition files. |
|
28 |
|
29 .. versionadded:: 1.4 |
|
30 """ |
|
31 |
|
32 name = 'Protocol Buffer' |
|
33 aliases = ['protobuf', 'proto'] |
|
34 filenames = ['*.proto'] |
|
35 |
|
36 tokens = { |
|
37 'root': [ |
|
38 (r'[ \t]+', Text), |
|
39 (r'[,;{}\[\]()<>]', Punctuation), |
|
40 (r'/(\\\n)?/(\n|(.|\n)*?[^\\]\n)', Comment.Single), |
|
41 (r'/(\\\n)?\*(.|\n)*?\*(\\\n)?/', Comment.Multiline), |
|
42 (words(( |
|
43 'import', 'option', 'optional', 'required', 'repeated', 'default', |
|
44 'packed', 'ctype', 'extensions', 'to', 'max', 'rpc', 'returns', |
|
45 'oneof'), prefix=r'\b', suffix=r'\b'), |
|
46 Keyword), |
|
47 (words(( |
|
48 'int32', 'int64', 'uint32', 'uint64', 'sint32', 'sint64', |
|
49 'fixed32', 'fixed64', 'sfixed32', 'sfixed64', |
|
50 'float', 'double', 'bool', 'string', 'bytes'), suffix=r'\b'), |
|
51 Keyword.Type), |
|
52 (r'(true|false)\b', Keyword.Constant), |
|
53 (r'(package)(\s+)', bygroups(Keyword.Namespace, Text), 'package'), |
|
54 (r'(message|extend)(\s+)', |
|
55 bygroups(Keyword.Declaration, Text), 'message'), |
|
56 (r'(enum|group|service)(\s+)', |
|
57 bygroups(Keyword.Declaration, Text), 'type'), |
|
58 (r'\".*?\"', String), |
|
59 (r'\'.*?\'', String), |
|
60 (r'(\d+\.\d*|\.\d+|\d+)[eE][+-]?\d+[LlUu]*', Number.Float), |
|
61 (r'(\d+\.\d*|\.\d+|\d+[fF])[fF]?', Number.Float), |
|
62 (r'(\-?(inf|nan))\b', Number.Float), |
|
63 (r'0x[0-9a-fA-F]+[LlUu]*', Number.Hex), |
|
64 (r'0[0-7]+[LlUu]*', Number.Oct), |
|
65 (r'\d+[LlUu]*', Number.Integer), |
|
66 (r'[+-=]', Operator), |
|
67 (r'([a-zA-Z_][\w.]*)([ \t]*)(=)', |
|
68 bygroups(Name.Attribute, Text, Operator)), |
|
69 (r'[a-zA-Z_][\w.]*', Name), |
|
70 ], |
|
71 'package': [ |
|
72 (r'[a-zA-Z_]\w*', Name.Namespace, '#pop'), |
|
73 default('#pop'), |
|
74 ], |
|
75 'message': [ |
|
76 (r'[a-zA-Z_]\w*', Name.Class, '#pop'), |
|
77 default('#pop'), |
|
78 ], |
|
79 'type': [ |
|
80 (r'[a-zA-Z_]\w*', Name, '#pop'), |
|
81 default('#pop'), |
|
82 ], |
|
83 } |
|
84 |
|
85 |
|
86 class ThriftLexer(RegexLexer): |
|
87 """ |
|
88 For `Thrift <https://thrift.apache.org/>`__ interface definitions. |
|
89 |
|
90 .. versionadded:: 2.1 |
|
91 """ |
|
92 name = 'Thrift' |
|
93 aliases = ['thrift'] |
|
94 filenames = ['*.thrift'] |
|
95 mimetypes = ['application/x-thrift'] |
|
96 |
|
97 tokens = { |
|
98 'root': [ |
|
99 include('whitespace'), |
|
100 include('comments'), |
|
101 (r'"', String.Double, combined('stringescape', 'dqs')), |
|
102 (r'\'', String.Single, combined('stringescape', 'sqs')), |
|
103 (r'(namespace)(\s+)', |
|
104 bygroups(Keyword.Namespace, Text.Whitespace), 'namespace'), |
|
105 (r'(enum|union|struct|service|exception)(\s+)', |
|
106 bygroups(Keyword.Declaration, Text.Whitespace), 'class'), |
|
107 (r'((?:(?:[^\W\d]|\$)[\w.\[\]$<>]*\s+)+?)' # return arguments |
|
108 r'((?:[^\W\d]|\$)[\w$]*)' # method name |
|
109 r'(\s*)(\()', # signature start |
|
110 bygroups(using(this), Name.Function, Text, Operator)), |
|
111 include('keywords'), |
|
112 include('numbers'), |
|
113 (r'[&=]', Operator), |
|
114 (r'[:;,{}()<>\[\]]', Punctuation), |
|
115 (r'[a-zA-Z_](\.\w|\w)*', Name), |
|
116 ], |
|
117 'whitespace': [ |
|
118 (r'\n', Text.Whitespace), |
|
119 (r'\s+', Text.Whitespace), |
|
120 ], |
|
121 'comments': [ |
|
122 (r'#.*$', Comment), |
|
123 (r'//.*?\n', Comment), |
|
124 (r'/\*[\w\W]*?\*/', Comment.Multiline), |
|
125 ], |
|
126 'stringescape': [ |
|
127 (r'\\([\\nrt"\'])', String.Escape), |
|
128 ], |
|
129 'dqs': [ |
|
130 (r'"', String.Double, '#pop'), |
|
131 (r'[^\\"\n]+', String.Double), |
|
132 ], |
|
133 'sqs': [ |
|
134 (r"'", String.Single, '#pop'), |
|
135 (r'[^\\\'\n]+', String.Single), |
|
136 ], |
|
137 'namespace': [ |
|
138 (r'[a-z*](\.\w|\w)*', Name.Namespace, '#pop'), |
|
139 default('#pop'), |
|
140 ], |
|
141 'class': [ |
|
142 (r'[a-zA-Z_]\w*', Name.Class, '#pop'), |
|
143 default('#pop'), |
|
144 ], |
|
145 'keywords': [ |
|
146 (r'(async|oneway|extends|throws|required|optional)\b', Keyword), |
|
147 (r'(true|false)\b', Keyword.Constant), |
|
148 (r'(const|typedef)\b', Keyword.Declaration), |
|
149 (words(( |
|
150 'cpp_namespace', 'cpp_include', 'cpp_type', 'java_package', |
|
151 'cocoa_prefix', 'csharp_namespace', 'delphi_namespace', |
|
152 'php_namespace', 'py_module', 'perl_package', |
|
153 'ruby_namespace', 'smalltalk_category', 'smalltalk_prefix', |
|
154 'xsd_all', 'xsd_optional', 'xsd_nillable', 'xsd_namespace', |
|
155 'xsd_attrs', 'include'), suffix=r'\b'), |
|
156 Keyword.Namespace), |
|
157 (words(( |
|
158 'void', 'bool', 'byte', 'i16', 'i32', 'i64', 'double', |
|
159 'string', 'binary', 'map', 'list', 'set', 'slist', |
|
160 'senum'), suffix=r'\b'), |
|
161 Keyword.Type), |
|
162 (words(( |
|
163 'BEGIN', 'END', '__CLASS__', '__DIR__', '__FILE__', |
|
164 '__FUNCTION__', '__LINE__', '__METHOD__', '__NAMESPACE__', |
|
165 'abstract', 'alias', 'and', 'args', 'as', 'assert', 'begin', |
|
166 'break', 'case', 'catch', 'class', 'clone', 'continue', |
|
167 'declare', 'def', 'default', 'del', 'delete', 'do', 'dynamic', |
|
168 'elif', 'else', 'elseif', 'elsif', 'end', 'enddeclare', |
|
169 'endfor', 'endforeach', 'endif', 'endswitch', 'endwhile', |
|
170 'ensure', 'except', 'exec', 'finally', 'float', 'for', |
|
171 'foreach', 'function', 'global', 'goto', 'if', 'implements', |
|
172 'import', 'in', 'inline', 'instanceof', 'interface', 'is', |
|
173 'lambda', 'module', 'native', 'new', 'next', 'nil', 'not', |
|
174 'or', 'pass', 'public', 'print', 'private', 'protected', |
|
175 'raise', 'redo', 'rescue', 'retry', 'register', 'return', |
|
176 'self', 'sizeof', 'static', 'super', 'switch', 'synchronized', |
|
177 'then', 'this', 'throw', 'transient', 'try', 'undef', |
|
178 'unless', 'unsigned', 'until', 'use', 'var', 'virtual', |
|
179 'volatile', 'when', 'while', 'with', 'xor', 'yield'), |
|
180 prefix=r'\b', suffix=r'\b'), |
|
181 Keyword.Reserved), |
|
182 ], |
|
183 'numbers': [ |
|
184 (r'[+-]?(\d+\.\d+([eE][+-]?\d+)?|\.?\d+[eE][+-]?\d+)', Number.Float), |
|
185 (r'[+-]?0x[0-9A-Fa-f]+', Number.Hex), |
|
186 (r'[+-]?[0-9]+', Number.Integer), |
|
187 ], |
|
188 } |
|
189 |
|
190 |
|
191 class BroLexer(RegexLexer): |
|
192 """ |
|
193 For `Bro <http://bro-ids.org/>`_ scripts. |
|
194 |
|
195 .. versionadded:: 1.5 |
|
196 """ |
|
197 name = 'Bro' |
|
198 aliases = ['bro'] |
|
199 filenames = ['*.bro'] |
|
200 |
|
201 _hex = r'[0-9a-fA-F_]' |
|
202 _float = r'((\d*\.?\d+)|(\d+\.?\d*))([eE][-+]?\d+)?' |
|
203 _h = r'[A-Za-z0-9][-A-Za-z0-9]*' |
|
204 |
|
205 tokens = { |
|
206 'root': [ |
|
207 # Whitespace |
|
208 (r'^@.*?\n', Comment.Preproc), |
|
209 (r'#.*?\n', Comment.Single), |
|
210 (r'\n', Text), |
|
211 (r'\s+', Text), |
|
212 (r'\\\n', Text), |
|
213 # Keywords |
|
214 (r'(add|alarm|break|case|const|continue|delete|do|else|enum|event' |
|
215 r'|export|for|function|if|global|hook|local|module|next' |
|
216 r'|of|print|redef|return|schedule|switch|type|when|while)\b', Keyword), |
|
217 (r'(addr|any|bool|count|counter|double|file|int|interval|net' |
|
218 r'|pattern|port|record|set|string|subnet|table|time|timer' |
|
219 r'|vector)\b', Keyword.Type), |
|
220 (r'(T|F)\b', Keyword.Constant), |
|
221 (r'(&)((?:add|delete|expire)_func|attr|(?:create|read|write)_expire' |
|
222 r'|default|disable_print_hook|raw_output|encrypt|group|log' |
|
223 r'|mergeable|optional|persistent|priority|redef' |
|
224 r'|rotate_(?:interval|size)|synchronized)\b', |
|
225 bygroups(Punctuation, Keyword)), |
|
226 (r'\s+module\b', Keyword.Namespace), |
|
227 # Addresses, ports and networks |
|
228 (r'\d+/(tcp|udp|icmp|unknown)\b', Number), |
|
229 (r'(\d+\.){3}\d+', Number), |
|
230 (r'(' + _hex + r'){7}' + _hex, Number), |
|
231 (r'0x' + _hex + r'(' + _hex + r'|:)*::(' + _hex + r'|:)*', Number), |
|
232 (r'((\d+|:)(' + _hex + r'|:)*)?::(' + _hex + r'|:)*', Number), |
|
233 (r'(\d+\.\d+\.|(\d+\.){2}\d+)', Number), |
|
234 # Hostnames |
|
235 (_h + r'(\.' + _h + r')+', String), |
|
236 # Numeric |
|
237 (_float + r'\s+(day|hr|min|sec|msec|usec)s?\b', Literal.Date), |
|
238 (r'0[xX]' + _hex, Number.Hex), |
|
239 (_float, Number.Float), |
|
240 (r'\d+', Number.Integer), |
|
241 (r'/', String.Regex, 'regex'), |
|
242 (r'"', String, 'string'), |
|
243 # Operators |
|
244 (r'[!%*/+:<=>?~|-]', Operator), |
|
245 (r'([-+=&|]{2}|[+=!><-]=)', Operator), |
|
246 (r'(in|match)\b', Operator.Word), |
|
247 (r'[{}()\[\]$.,;]', Punctuation), |
|
248 # Identfier |
|
249 (r'([_a-zA-Z]\w*)(::)', bygroups(Name, Name.Namespace)), |
|
250 (r'[a-zA-Z_]\w*', Name) |
|
251 ], |
|
252 'string': [ |
|
253 (r'"', String, '#pop'), |
|
254 (r'\\([\\abfnrtv"\']|x[a-fA-F0-9]{2,4}|[0-7]{1,3})', String.Escape), |
|
255 (r'[^\\"\n]+', String), |
|
256 (r'\\\n', String), |
|
257 (r'\\', String) |
|
258 ], |
|
259 'regex': [ |
|
260 (r'/', String.Regex, '#pop'), |
|
261 (r'\\[\\nt/]', String.Regex), # String.Escape is too intense here. |
|
262 (r'[^\\/\n]+', String.Regex), |
|
263 (r'\\\n', String.Regex), |
|
264 (r'\\', String.Regex) |
|
265 ] |
|
266 } |
|
267 |
|
268 |
|
269 class PuppetLexer(RegexLexer): |
|
270 """ |
|
271 For `Puppet <http://puppetlabs.com/>`__ configuration DSL. |
|
272 |
|
273 .. versionadded:: 1.6 |
|
274 """ |
|
275 name = 'Puppet' |
|
276 aliases = ['puppet'] |
|
277 filenames = ['*.pp'] |
|
278 |
|
279 tokens = { |
|
280 'root': [ |
|
281 include('comments'), |
|
282 include('keywords'), |
|
283 include('names'), |
|
284 include('numbers'), |
|
285 include('operators'), |
|
286 include('strings'), |
|
287 |
|
288 (r'[]{}:(),;[]', Punctuation), |
|
289 (r'[^\S\n]+', Text), |
|
290 ], |
|
291 |
|
292 'comments': [ |
|
293 (r'\s*#.*$', Comment), |
|
294 (r'/(\\\n)?[*](.|\n)*?[*](\\\n)?/', Comment.Multiline), |
|
295 ], |
|
296 |
|
297 'operators': [ |
|
298 (r'(=>|\?|<|>|=|\+|-|/|\*|~|!|\|)', Operator), |
|
299 (r'(in|and|or|not)\b', Operator.Word), |
|
300 ], |
|
301 |
|
302 'names': [ |
|
303 (r'[a-zA-Z_]\w*', Name.Attribute), |
|
304 (r'(\$\S+)(\[)(\S+)(\])', bygroups(Name.Variable, Punctuation, |
|
305 String, Punctuation)), |
|
306 (r'\$\S+', Name.Variable), |
|
307 ], |
|
308 |
|
309 'numbers': [ |
|
310 # Copypasta from the Python lexer |
|
311 (r'(\d+\.\d*|\d*\.\d+)([eE][+-]?[0-9]+)?j?', Number.Float), |
|
312 (r'\d+[eE][+-]?[0-9]+j?', Number.Float), |
|
313 (r'0[0-7]+j?', Number.Oct), |
|
314 (r'0[xX][a-fA-F0-9]+', Number.Hex), |
|
315 (r'\d+L', Number.Integer.Long), |
|
316 (r'\d+j?', Number.Integer) |
|
317 ], |
|
318 |
|
319 'keywords': [ |
|
320 # Left out 'group' and 'require' |
|
321 # Since they're often used as attributes |
|
322 (words(( |
|
323 'absent', 'alert', 'alias', 'audit', 'augeas', 'before', 'case', |
|
324 'check', 'class', 'computer', 'configured', 'contained', |
|
325 'create_resources', 'crit', 'cron', 'debug', 'default', |
|
326 'define', 'defined', 'directory', 'else', 'elsif', 'emerg', |
|
327 'err', 'exec', 'extlookup', 'fail', 'false', 'file', |
|
328 'filebucket', 'fqdn_rand', 'generate', 'host', 'if', 'import', |
|
329 'include', 'info', 'inherits', 'inline_template', 'installed', |
|
330 'interface', 'k5login', 'latest', 'link', 'loglevel', |
|
331 'macauthorization', 'mailalias', 'maillist', 'mcx', 'md5', |
|
332 'mount', 'mounted', 'nagios_command', 'nagios_contact', |
|
333 'nagios_contactgroup', 'nagios_host', 'nagios_hostdependency', |
|
334 'nagios_hostescalation', 'nagios_hostextinfo', 'nagios_hostgroup', |
|
335 'nagios_service', 'nagios_servicedependency', 'nagios_serviceescalation', |
|
336 'nagios_serviceextinfo', 'nagios_servicegroup', 'nagios_timeperiod', |
|
337 'node', 'noop', 'notice', 'notify', 'package', 'present', 'purged', |
|
338 'realize', 'regsubst', 'resources', 'role', 'router', 'running', |
|
339 'schedule', 'scheduled_task', 'search', 'selboolean', 'selmodule', |
|
340 'service', 'sha1', 'shellquote', 'split', 'sprintf', |
|
341 'ssh_authorized_key', 'sshkey', 'stage', 'stopped', 'subscribe', |
|
342 'tag', 'tagged', 'template', 'tidy', 'true', 'undef', 'unmounted', |
|
343 'user', 'versioncmp', 'vlan', 'warning', 'yumrepo', 'zfs', 'zone', |
|
344 'zpool'), prefix='(?i)', suffix=r'\b'), |
|
345 Keyword), |
|
346 ], |
|
347 |
|
348 'strings': [ |
|
349 (r'"([^"])*"', String), |
|
350 (r"'(\\'|[^'])*'", String), |
|
351 ], |
|
352 |
|
353 } |
|
354 |
|
355 |
|
356 class RslLexer(RegexLexer): |
|
357 """ |
|
358 `RSL <http://en.wikipedia.org/wiki/RAISE>`_ is the formal specification |
|
359 language used in RAISE (Rigorous Approach to Industrial Software Engineering) |
|
360 method. |
|
361 |
|
362 .. versionadded:: 2.0 |
|
363 """ |
|
364 name = 'RSL' |
|
365 aliases = ['rsl'] |
|
366 filenames = ['*.rsl'] |
|
367 mimetypes = ['text/rsl'] |
|
368 |
|
369 flags = re.MULTILINE | re.DOTALL |
|
370 |
|
371 tokens = { |
|
372 'root': [ |
|
373 (words(( |
|
374 'Bool', 'Char', 'Int', 'Nat', 'Real', 'Text', 'Unit', 'abs', |
|
375 'all', 'always', 'any', 'as', 'axiom', 'card', 'case', 'channel', |
|
376 'chaos', 'class', 'devt_relation', 'dom', 'elems', 'else', 'elif', |
|
377 'end', 'exists', 'extend', 'false', 'for', 'hd', 'hide', 'if', |
|
378 'in', 'is', 'inds', 'initialise', 'int', 'inter', 'isin', 'len', |
|
379 'let', 'local', 'ltl_assertion', 'object', 'of', 'out', 'post', |
|
380 'pre', 'read', 'real', 'rng', 'scheme', 'skip', 'stop', 'swap', |
|
381 'then', 'theory', 'test_case', 'tl', 'transition_system', 'true', |
|
382 'type', 'union', 'until', 'use', 'value', 'variable', 'while', |
|
383 'with', 'write', '~isin', '-inflist', '-infset', '-list', |
|
384 '-set'), prefix=r'\b', suffix=r'\b'), |
|
385 Keyword), |
|
386 (r'(variable|value)\b', Keyword.Declaration), |
|
387 (r'--.*?\n', Comment), |
|
388 (r'<:.*?:>', Comment), |
|
389 (r'\{!.*?!\}', Comment), |
|
390 (r'/\*.*?\*/', Comment), |
|
391 (r'^[ \t]*([\w]+)[ \t]*:[^:]', Name.Function), |
|
392 (r'(^[ \t]*)([\w]+)([ \t]*\([\w\s,]*\)[ \t]*)(is|as)', |
|
393 bygroups(Text, Name.Function, Text, Keyword)), |
|
394 (r'\b[A-Z]\w*\b', Keyword.Type), |
|
395 (r'(true|false)\b', Keyword.Constant), |
|
396 (r'".*"', String), |
|
397 (r'\'.\'', String.Char), |
|
398 (r'(><|->|-m->|/\\|<=|<<=|<\.|\|\||\|\^\||-~->|-~m->|\\/|>=|>>|' |
|
399 r'\.>|\+\+|-\\|<->|=>|:-|~=|\*\*|<<|>>=|\+>|!!|\|=\||#)', |
|
400 Operator), |
|
401 (r'[0-9]+\.[0-9]+([eE][0-9]+)?[fd]?', Number.Float), |
|
402 (r'0x[0-9a-f]+', Number.Hex), |
|
403 (r'[0-9]+', Number.Integer), |
|
404 (r'.', Text), |
|
405 ], |
|
406 } |
|
407 |
|
408 def analyse_text(text): |
|
409 """ |
|
410 Check for the most common text in the beginning of a RSL file. |
|
411 """ |
|
412 if re.search(r'scheme\s*.*?=\s*class\s*type', text, re.I) is not None: |
|
413 return 1.0 |
|
414 |
|
415 |
|
416 class MscgenLexer(RegexLexer): |
|
417 """ |
|
418 For `Mscgen <http://www.mcternan.me.uk/mscgen/>`_ files. |
|
419 |
|
420 .. versionadded:: 1.6 |
|
421 """ |
|
422 name = 'Mscgen' |
|
423 aliases = ['mscgen', 'msc'] |
|
424 filenames = ['*.msc'] |
|
425 |
|
426 _var = r'(\w+|"(?:\\"|[^"])*")' |
|
427 |
|
428 tokens = { |
|
429 'root': [ |
|
430 (r'msc\b', Keyword.Type), |
|
431 # Options |
|
432 (r'(hscale|HSCALE|width|WIDTH|wordwraparcs|WORDWRAPARCS' |
|
433 r'|arcgradient|ARCGRADIENT)\b', Name.Property), |
|
434 # Operators |
|
435 (r'(abox|ABOX|rbox|RBOX|box|BOX|note|NOTE)\b', Operator.Word), |
|
436 (r'(\.|-|\|){3}', Keyword), |
|
437 (r'(?:-|=|\.|:){2}' |
|
438 r'|<<=>>|<->|<=>|<<>>|<:>' |
|
439 r'|->|=>>|>>|=>|:>|-x|-X' |
|
440 r'|<-|<<=|<<|<=|<:|x-|X-|=', Operator), |
|
441 # Names |
|
442 (r'\*', Name.Builtin), |
|
443 (_var, Name.Variable), |
|
444 # Other |
|
445 (r'\[', Punctuation, 'attrs'), |
|
446 (r'\{|\}|,|;', Punctuation), |
|
447 include('comments') |
|
448 ], |
|
449 'attrs': [ |
|
450 (r'\]', Punctuation, '#pop'), |
|
451 (_var + r'(\s*)(=)(\s*)' + _var, |
|
452 bygroups(Name.Attribute, Text.Whitespace, Operator, Text.Whitespace, |
|
453 String)), |
|
454 (r',', Punctuation), |
|
455 include('comments') |
|
456 ], |
|
457 'comments': [ |
|
458 (r'(?://|#).*?\n', Comment.Single), |
|
459 (r'/\*(?:.|\n)*?\*/', Comment.Multiline), |
|
460 (r'[ \t\r\n]+', Text.Whitespace) |
|
461 ] |
|
462 } |
|
463 |
|
464 |
|
465 class VGLLexer(RegexLexer): |
|
466 """ |
|
467 For `SampleManager VGL <http://www.thermoscientific.com/samplemanager>`_ |
|
468 source code. |
|
469 |
|
470 .. versionadded:: 1.6 |
|
471 """ |
|
472 name = 'VGL' |
|
473 aliases = ['vgl'] |
|
474 filenames = ['*.rpf'] |
|
475 |
|
476 flags = re.MULTILINE | re.DOTALL | re.IGNORECASE |
|
477 |
|
478 tokens = { |
|
479 'root': [ |
|
480 (r'\{[^}]*\}', Comment.Multiline), |
|
481 (r'declare', Keyword.Constant), |
|
482 (r'(if|then|else|endif|while|do|endwhile|and|or|prompt|object' |
|
483 r'|create|on|line|with|global|routine|value|endroutine|constant' |
|
484 r'|global|set|join|library|compile_option|file|exists|create|copy' |
|
485 r'|delete|enable|windows|name|notprotected)(?! *[=<>.,()])', |
|
486 Keyword), |
|
487 (r'(true|false|null|empty|error|locked)', Keyword.Constant), |
|
488 (r'[~^*#!%&\[\]()<>|+=:;,./?-]', Operator), |
|
489 (r'"[^"]*"', String), |
|
490 (r'(\.)([a-z_$][\w$]*)', bygroups(Operator, Name.Attribute)), |
|
491 (r'[0-9][0-9]*(\.[0-9]+(e[+\-]?[0-9]+)?)?', Number), |
|
492 (r'[a-z_$][\w$]*', Name), |
|
493 (r'[\r\n]+', Text), |
|
494 (r'\s+', Text) |
|
495 ] |
|
496 } |
|
497 |
|
498 |
|
499 class AlloyLexer(RegexLexer): |
|
500 """ |
|
501 For `Alloy <http://alloy.mit.edu>`_ source code. |
|
502 |
|
503 .. versionadded:: 2.0 |
|
504 """ |
|
505 |
|
506 name = 'Alloy' |
|
507 aliases = ['alloy'] |
|
508 filenames = ['*.als'] |
|
509 mimetypes = ['text/x-alloy'] |
|
510 |
|
511 flags = re.MULTILINE | re.DOTALL |
|
512 |
|
513 iden_rex = r'[a-zA-Z_][\w\']*' |
|
514 text_tuple = (r'[^\S\n]+', Text) |
|
515 |
|
516 tokens = { |
|
517 'sig': [ |
|
518 (r'(extends)\b', Keyword, '#pop'), |
|
519 (iden_rex, Name), |
|
520 text_tuple, |
|
521 (r',', Punctuation), |
|
522 (r'\{', Operator, '#pop'), |
|
523 ], |
|
524 'module': [ |
|
525 text_tuple, |
|
526 (iden_rex, Name, '#pop'), |
|
527 ], |
|
528 'fun': [ |
|
529 text_tuple, |
|
530 (r'\{', Operator, '#pop'), |
|
531 (iden_rex, Name, '#pop'), |
|
532 ], |
|
533 'root': [ |
|
534 (r'--.*?$', Comment.Single), |
|
535 (r'//.*?$', Comment.Single), |
|
536 (r'/\*.*?\*/', Comment.Multiline), |
|
537 text_tuple, |
|
538 (r'(module|open)(\s+)', bygroups(Keyword.Namespace, Text), |
|
539 'module'), |
|
540 (r'(sig|enum)(\s+)', bygroups(Keyword.Declaration, Text), 'sig'), |
|
541 (r'(iden|univ|none)\b', Keyword.Constant), |
|
542 (r'(int|Int)\b', Keyword.Type), |
|
543 (r'(this|abstract|extends|set|seq|one|lone|let)\b', Keyword), |
|
544 (r'(all|some|no|sum|disj|when|else)\b', Keyword), |
|
545 (r'(run|check|for|but|exactly|expect|as)\b', Keyword), |
|
546 (r'(and|or|implies|iff|in)\b', Operator.Word), |
|
547 (r'(fun|pred|fact|assert)(\s+)', bygroups(Keyword, Text), 'fun'), |
|
548 (r'!|#|&&|\+\+|<<|>>|>=|<=>|<=|\.|->', Operator), |
|
549 (r'[-+/*%=<>&!^|~{}\[\]().]', Operator), |
|
550 (iden_rex, Name), |
|
551 (r'[:,]', Punctuation), |
|
552 (r'[0-9]+', Number.Integer), |
|
553 (r'"(\\\\|\\"|[^"])*"', String), |
|
554 (r'\n', Text), |
|
555 ] |
|
556 } |
|
557 |
|
558 |
|
559 class PanLexer(RegexLexer): |
|
560 """ |
|
561 Lexer for `pan <http://github.com/quattor/pan/>`_ source files. |
|
562 |
|
563 Based on tcsh lexer. |
|
564 |
|
565 .. versionadded:: 2.0 |
|
566 """ |
|
567 |
|
568 name = 'Pan' |
|
569 aliases = ['pan'] |
|
570 filenames = ['*.pan'] |
|
571 |
|
572 tokens = { |
|
573 'root': [ |
|
574 include('basic'), |
|
575 (r'\(', Keyword, 'paren'), |
|
576 (r'\{', Keyword, 'curly'), |
|
577 include('data'), |
|
578 ], |
|
579 'basic': [ |
|
580 (words(( |
|
581 'if', 'for', 'with', 'else', 'type', 'bind', 'while', 'valid', 'final', |
|
582 'prefix', 'unique', 'object', 'foreach', 'include', 'template', |
|
583 'function', 'variable', 'structure', 'extensible', 'declaration'), |
|
584 prefix=r'\b', suffix=r'\s*\b'), |
|
585 Keyword), |
|
586 (words(( |
|
587 'file_contents', 'format', 'index', 'length', 'match', 'matches', |
|
588 'replace', 'splice', 'split', 'substr', 'to_lowercase', 'to_uppercase', |
|
589 'debug', 'error', 'traceback', 'deprecated', 'base64_decode', |
|
590 'base64_encode', 'digest', 'escape', 'unescape', 'append', 'create', |
|
591 'first', 'nlist', 'key', 'list', 'merge', 'next', 'prepend', 'is_boolean', |
|
592 'is_defined', 'is_double', 'is_list', 'is_long', 'is_nlist', 'is_null', |
|
593 'is_number', 'is_property', 'is_resource', 'is_string', 'to_boolean', |
|
594 'to_double', 'to_long', 'to_string', 'clone', 'delete', 'exists', |
|
595 'path_exists', 'if_exists', 'return', 'value'), |
|
596 prefix=r'\b', suffix=r'\s*\b'), |
|
597 Name.Builtin), |
|
598 (r'#.*', Comment), |
|
599 (r'\\[\w\W]', String.Escape), |
|
600 (r'(\b\w+)(\s*)(=)', bygroups(Name.Variable, Text, Operator)), |
|
601 (r'[\[\]{}()=]+', Operator), |
|
602 (r'<<\s*(\'?)\\?(\w+)[\w\W]+?\2', String), |
|
603 (r';', Punctuation), |
|
604 ], |
|
605 'data': [ |
|
606 (r'(?s)"(\\\\|\\[0-7]+|\\.|[^"\\])*"', String.Double), |
|
607 (r"(?s)'(\\\\|\\[0-7]+|\\.|[^'\\])*'", String.Single), |
|
608 (r'\s+', Text), |
|
609 (r'[^=\s\[\]{}()$"\'`\\;#]+', Text), |
|
610 (r'\d+(?= |\Z)', Number), |
|
611 ], |
|
612 'curly': [ |
|
613 (r'\}', Keyword, '#pop'), |
|
614 (r':-', Keyword), |
|
615 (r'\w+', Name.Variable), |
|
616 (r'[^}:"\'`$]+', Punctuation), |
|
617 (r':', Punctuation), |
|
618 include('root'), |
|
619 ], |
|
620 'paren': [ |
|
621 (r'\)', Keyword, '#pop'), |
|
622 include('root'), |
|
623 ], |
|
624 } |
|
625 |
|
626 |
|
627 class CrmshLexer(RegexLexer): |
|
628 """ |
|
629 Lexer for `crmsh <http://crmsh.github.io/>`_ configuration files |
|
630 for Pacemaker clusters. |
|
631 |
|
632 .. versionadded:: 2.1 |
|
633 """ |
|
634 name = 'Crmsh' |
|
635 aliases = ['crmsh', 'pcmk'] |
|
636 filenames = ['*.crmsh', '*.pcmk'] |
|
637 mimetypes = [] |
|
638 |
|
639 elem = words(( |
|
640 'node', 'primitive', 'group', 'clone', 'ms', 'location', |
|
641 'colocation', 'order', 'fencing_topology', 'rsc_ticket', |
|
642 'rsc_template', 'property', 'rsc_defaults', |
|
643 'op_defaults', 'acl_target', 'acl_group', 'user', 'role', |
|
644 'tag'), suffix=r'(?![\w#$-])') |
|
645 sub = words(( |
|
646 'params', 'meta', 'operations', 'op', 'rule', |
|
647 'attributes', 'utilization'), suffix=r'(?![\w#$-])') |
|
648 acl = words(('read', 'write', 'deny'), suffix=r'(?![\w#$-])') |
|
649 bin_rel = words(('and', 'or'), suffix=r'(?![\w#$-])') |
|
650 un_ops = words(('defined', 'not_defined'), suffix=r'(?![\w#$-])') |
|
651 date_exp = words(('in_range', 'date', 'spec', 'in'), suffix=r'(?![\w#$-])') |
|
652 acl_mod = (r'(?:tag|ref|reference|attribute|type|xpath)') |
|
653 bin_ops = (r'(?:lt|gt|lte|gte|eq|ne)') |
|
654 val_qual = (r'(?:string|version|number)') |
|
655 rsc_role_action = (r'(?:Master|Started|Slave|Stopped|' |
|
656 r'start|promote|demote|stop)') |
|
657 |
|
658 tokens = { |
|
659 'root': [ |
|
660 (r'^#.*\n?', Comment), |
|
661 # attr=value (nvpair) |
|
662 (r'([\w#$-]+)(=)("(?:""|[^"])*"|\S+)', |
|
663 bygroups(Name.Attribute, Punctuation, String)), |
|
664 # need this construct, otherwise numeric node ids |
|
665 # are matched as scores |
|
666 # elem id: |
|
667 (r'(node)(\s+)([\w#$-]+)(:)', |
|
668 bygroups(Keyword, Whitespace, Name, Punctuation)), |
|
669 # scores |
|
670 (r'([+-]?([0-9]+|inf)):', Number), |
|
671 # keywords (elements and other) |
|
672 (elem, Keyword), |
|
673 (sub, Keyword), |
|
674 (acl, Keyword), |
|
675 # binary operators |
|
676 (r'(?:%s:)?(%s)(?![\w#$-])' % (val_qual, bin_ops), Operator.Word), |
|
677 # other operators |
|
678 (bin_rel, Operator.Word), |
|
679 (un_ops, Operator.Word), |
|
680 (date_exp, Operator.Word), |
|
681 # builtin attributes (e.g. #uname) |
|
682 (r'#[a-z]+(?![\w#$-])', Name.Builtin), |
|
683 # acl_mod:blah |
|
684 (r'(%s)(:)("(?:""|[^"])*"|\S+)' % acl_mod, |
|
685 bygroups(Keyword, Punctuation, Name)), |
|
686 # rsc_id[:(role|action)] |
|
687 # NB: this matches all other identifiers |
|
688 (r'([\w#$-]+)(?:(:)(%s))?(?![\w#$-])' % rsc_role_action, |
|
689 bygroups(Name, Punctuation, Operator.Word)), |
|
690 # punctuation |
|
691 (r'(\\(?=\n)|[\[\](){}/:@])', Punctuation), |
|
692 (r'\s+|\n', Whitespace), |
|
693 ], |
|
694 } |
|
695 |
|
696 |
|
697 class FlatlineLexer(RegexLexer): |
|
698 """ |
|
699 Lexer for `Flatline <https://github.com/bigmlcom/flatline>`_ expressions. |
|
700 |
|
701 .. versionadded:: 2.2 |
|
702 """ |
|
703 name = 'Flatline' |
|
704 aliases = ['flatline'] |
|
705 filenames = [] |
|
706 mimetypes = ['text/x-flatline'] |
|
707 |
|
708 special_forms = ('let',) |
|
709 |
|
710 builtins = ( |
|
711 "!=", "*", "+", "-", "<", "<=", "=", ">", ">=", "abs", "acos", "all", |
|
712 "all-but", "all-with-defaults", "all-with-numeric-default", "and", |
|
713 "asin", "atan", "avg", "avg-window", "bin-center", "bin-count", "call", |
|
714 "category-count", "ceil", "cond", "cond-window", "cons", "cos", "cosh", |
|
715 "count", "diff-window", "div", "ensure-value", "ensure-weighted-value", |
|
716 "epoch", "epoch-day", "epoch-fields", "epoch-hour", "epoch-millisecond", |
|
717 "epoch-minute", "epoch-month", "epoch-second", "epoch-weekday", |
|
718 "epoch-year", "exp", "f", "field", "field-prop", "fields", "filter", |
|
719 "first", "floor", "head", "if", "in", "integer", "language", "length", |
|
720 "levenshtein", "linear-regression", "list", "ln", "log", "log10", "map", |
|
721 "matches", "matches?", "max", "maximum", "md5", "mean", "median", "min", |
|
722 "minimum", "missing", "missing-count", "missing?", "missing_count", |
|
723 "mod", "mode", "normalize", "not", "nth", "occurrences", "or", |
|
724 "percentile", "percentile-label", "population", "population-fraction", |
|
725 "pow", "preferred", "preferred?", "quantile-label", "rand", "rand-int", |
|
726 "random-value", "re-quote", "real", "replace", "replace-first", "rest", |
|
727 "round", "row-number", "segment-label", "sha1", "sha256", "sin", "sinh", |
|
728 "sqrt", "square", "standard-deviation", "standard_deviation", "str", |
|
729 "subs", "sum", "sum-squares", "sum-window", "sum_squares", "summary", |
|
730 "summary-no", "summary-str", "tail", "tan", "tanh", "to-degrees", |
|
731 "to-radians", "variance", "vectorize", "weighted-random-value", "window", |
|
732 "winnow", "within-percentiles?", "z-score", |
|
733 ) |
|
734 |
|
735 valid_name = r'(?!#)[\w!$%*+<=>?/.#-]+' |
|
736 |
|
737 tokens = { |
|
738 'root': [ |
|
739 # whitespaces - usually not relevant |
|
740 (r'[,\s]+', Text), |
|
741 |
|
742 # numbers |
|
743 (r'-?\d+\.\d+', Number.Float), |
|
744 (r'-?\d+', Number.Integer), |
|
745 (r'0x-?[a-f\d]+', Number.Hex), |
|
746 |
|
747 # strings, symbols and characters |
|
748 (r'"(\\\\|\\"|[^"])*"', String), |
|
749 (r"\\(.|[a-z]+)", String.Char), |
|
750 |
|
751 # expression template placeholder |
|
752 (r'_', String.Symbol), |
|
753 |
|
754 # highlight the special forms |
|
755 (words(special_forms, suffix=' '), Keyword), |
|
756 |
|
757 # highlight the builtins |
|
758 (words(builtins, suffix=' '), Name.Builtin), |
|
759 |
|
760 # the remaining functions |
|
761 (r'(?<=\()' + valid_name, Name.Function), |
|
762 |
|
763 # find the remaining variables |
|
764 (valid_name, Name.Variable), |
|
765 |
|
766 # parentheses |
|
767 (r'(\(|\))', Punctuation), |
|
768 ], |
|
769 } |
|
770 |
|
771 |
|
772 class SnowballLexer(ExtendedRegexLexer): |
|
773 """ |
|
774 Lexer for `Snowball <http://snowballstem.org/>`_ source code. |
|
775 |
|
776 .. versionadded:: 2.2 |
|
777 """ |
|
778 |
|
779 name = 'Snowball' |
|
780 aliases = ['snowball'] |
|
781 filenames = ['*.sbl'] |
|
782 |
|
783 _ws = r'\n\r\t ' |
|
784 |
|
785 def __init__(self, **options): |
|
786 self._reset_stringescapes() |
|
787 ExtendedRegexLexer.__init__(self, **options) |
|
788 |
|
789 def _reset_stringescapes(self): |
|
790 self._start = "'" |
|
791 self._end = "'" |
|
792 |
|
793 def _string(do_string_first): |
|
794 def callback(lexer, match, ctx): |
|
795 s = match.start() |
|
796 text = match.group() |
|
797 string = re.compile(r'([^%s]*)(.)' % re.escape(lexer._start)).match |
|
798 escape = re.compile(r'([^%s]*)(.)' % re.escape(lexer._end)).match |
|
799 pos = 0 |
|
800 do_string = do_string_first |
|
801 while pos < len(text): |
|
802 if do_string: |
|
803 match = string(text, pos) |
|
804 yield s + match.start(1), String.Single, match.group(1) |
|
805 if match.group(2) == "'": |
|
806 yield s + match.start(2), String.Single, match.group(2) |
|
807 ctx.stack.pop() |
|
808 break |
|
809 yield s + match.start(2), String.Escape, match.group(2) |
|
810 pos = match.end() |
|
811 match = escape(text, pos) |
|
812 yield s + match.start(), String.Escape, match.group() |
|
813 if match.group(2) != lexer._end: |
|
814 ctx.stack[-1] = 'escape' |
|
815 break |
|
816 pos = match.end() |
|
817 do_string = True |
|
818 ctx.pos = s + match.end() |
|
819 return callback |
|
820 |
|
821 def _stringescapes(lexer, match, ctx): |
|
822 lexer._start = match.group(3) |
|
823 lexer._end = match.group(5) |
|
824 return bygroups(Keyword.Reserved, Text, String.Escape, Text, |
|
825 String.Escape)(lexer, match, ctx) |
|
826 |
|
827 tokens = { |
|
828 'root': [ |
|
829 (words(('len', 'lenof'), suffix=r'\b'), Operator.Word), |
|
830 include('root1'), |
|
831 ], |
|
832 'root1': [ |
|
833 (r'[%s]+' % _ws, Text), |
|
834 (r'\d+', Number.Integer), |
|
835 (r"'", String.Single, 'string'), |
|
836 (r'[()]', Punctuation), |
|
837 (r'/\*[\w\W]*?\*/', Comment.Multiline), |
|
838 (r'//.*', Comment.Single), |
|
839 (r'[!*+\-/<=>]=|[-=]>|<[+-]|[$*+\-/<=>?\[\]]', Operator), |
|
840 (words(('as', 'get', 'hex', 'among', 'define', 'decimal', |
|
841 'backwardmode'), suffix=r'\b'), |
|
842 Keyword.Reserved), |
|
843 (words(('strings', 'booleans', 'integers', 'routines', 'externals', |
|
844 'groupings'), suffix=r'\b'), |
|
845 Keyword.Reserved, 'declaration'), |
|
846 (words(('do', 'or', 'and', 'for', 'hop', 'non', 'not', 'set', 'try', |
|
847 'fail', 'goto', 'loop', 'next', 'test', 'true', |
|
848 'false', 'unset', 'atmark', 'attach', 'delete', 'gopast', |
|
849 'insert', 'repeat', 'sizeof', 'tomark', 'atleast', |
|
850 'atlimit', 'reverse', 'setmark', 'tolimit', 'setlimit', |
|
851 'backwards', 'substring'), suffix=r'\b'), |
|
852 Operator.Word), |
|
853 (words(('size', 'limit', 'cursor', 'maxint', 'minint'), |
|
854 suffix=r'\b'), |
|
855 Name.Builtin), |
|
856 (r'(stringdef\b)([%s]*)([^%s]+)' % (_ws, _ws), |
|
857 bygroups(Keyword.Reserved, Text, String.Escape)), |
|
858 (r'(stringescapes\b)([%s]*)(.)([%s]*)(.)' % (_ws, _ws), |
|
859 _stringescapes), |
|
860 (r'[A-Za-z]\w*', Name), |
|
861 ], |
|
862 'declaration': [ |
|
863 (r'\)', Punctuation, '#pop'), |
|
864 (words(('len', 'lenof'), suffix=r'\b'), Name, |
|
865 ('root1', 'declaration')), |
|
866 include('root1'), |
|
867 ], |
|
868 'string': [ |
|
869 (r"[^']*'", _string(True)), |
|
870 ], |
|
871 'escape': [ |
|
872 (r"[^']*'", _string(False)), |
|
873 ], |
|
874 } |
|
875 |
|
876 def get_tokens_unprocessed(self, text=None, context=None): |
|
877 self._reset_stringescapes() |
|
878 return ExtendedRegexLexer.get_tokens_unprocessed(self, text, context) |