pmacs3/mode/rust.py

151 lines
5.3 KiB
Python

import os.path
from mode import Fundamental
import tab
from lex import Grammar, PatternRule, RegionRule, PatternMatchRule, OverridePatternRule
from mode.python import StringGrammar2
chr1 = '[a-zA-Z_]'
chr2 = '[a-zA-Z0-9_]'
word = chr1 + chr2 + '*'
spaces = r'[\t ]+'
type_ = '[a-zA-Z0-9_<>]+'
class RustGrammar(Grammar):
rules = [
PatternRule('spaces', r'[\t ]+'),
PatternRule('eol', r'\n$'),
PatternRule('rust.comment', '//.*$'),
PatternMatchRule('x', r'(fn)( *)(' + word + r')',
'rust.keyword', 'spaces', 'rust.function', 'spaces'),
PatternMatchRule('x', r'(\|)( *)(' + word + r')( *)(\|)',
'rust.delimiter', 'spaces', 'rust.param', 'spaces', 'rust.delimiter'),
PatternMatchRule('x', r'(' + word + ')( *)(:)( *)(&?)(' + type_ + r')',
'rust.param', 'spaces', 'rust.delimiter', 'spaces',
'rust.delimiter', 'rust.type'),
PatternMatchRule('x', r'(->)( *)(' + type_ + ')',
'rust.operator', 'spaces', 'rust.type'),
RegionRule('rust.string', '"', StringGrammar2, '"'),
PatternRule("rust.float", r"-?[0-9]+\.[0-9]+|-?\.[0-9]+|-?(?:[0-9]|[0-9]+\.[0-9]*|-?\.[0-9]+)[eE][\+-]?[0-9]+"),
PatternRule("rust.integer", r"(?:0(?![x0-9])|-?[1-9][0-9]*|0[0-7]+|0[xX][0-9a-fA-F]+)[lL]?"),
#PatternRule('rust.keyword', r"(?<=[a-zA-Z0-9_])(?:while|where|use|unsafe|type|true|trait|super|struct|static|Self|self|return|ref|pub|mut|move|mod|match|loop|let|in|impl|if|for|fn|false|extern|enum|else|dyn|crate|continue|const|break|await|async|as)"),
PatternRule('rust.keyword', r"(?<![a-zA-Z0-9_])(?:while|where|use|unsafe|type|true|trait|super|struct|static|Self|self|return|ref|pub|mut|move|mod|match|loop|let|in|impl|if|for|fn|false|extern|enum|else|dyn|crate|continue|const|break|await|async|as)(?![a-zA-Z0-9_])"),
PatternRule('rust.reserved', r"(?<![a-zA-Z0-9_])(?:yield|virtual|unsized|typeof|try|priv|override|macro|final|do|box|become|abstract)(?![a-zA-Z0-9_])"),
# weak keywords
PatternRule('rust.keyword', r"(?<![a-zA-Z0-9_])(?:union|'static)(?![a-zA-Z0-9_])"),
PatternRule('rust.method', r"(?:fn)(?!" + chr2 + ")"),
PatternRule('rust.delimiter', r"[;\(\){}\[\]]"),
PatternRule('rust.delimiter', r"(?:->|\.\.|%|==)"),
PatternRule('rust.bareword', word),
]
class RustTabber(tab.StackTabber2):
open_tokens = {'rust.delimiter': {'{': '}', '(': ')', '[': ']'}}
close_tokens = {'rust.delimiter': {'}': '{', ')': '(', ']': '['}}
is_indent_tokens = set(['spaces'])
is_ignored_tokens = set(['spaces', 'eol', 'comment'])
end_at_eof = False
end_at_tokens = {'rust.delimiter': {';': 1}}
nocontinue_tokens = {'rust.delimiter': set([';', ',', '}'])}
start_free_tokens = {'rust.string.start': 'rust.string.end'}
end_free_tokens = {'rust.string.end': 'rust.string.start'}
# white is for delimiters, operators, numbers
default = ('default', 'default')
# magenta is for keywords/builtins
lo_magenta = ('magenta202', 'default')
hi_magenta = ('magenta505', 'default')
# red is for comments
lo_red = ('red300', 'default')
hi_red = ('red511', 'default')
# orange is for macro definitions, headers and constants
hi_orange = ('yellow531', 'default')
lo_orange = ('yellow520', 'default')
# yellow is for parts of macros
hi_yellow = ('yellow551', 'default')
lo_yellow = ('yellow330', 'default')
# green is for strings and characters
lo_green = ('green030', 'default')
hi_green = ('green050', 'default')
# cyan is for types
lo_cyan = ('cyan033', 'default')
hi_cyan = ('cyan155', 'default')
# blue is definitions, functions and some macros
lo_blue = ('blue113', 'default')
hi_blue = ('blue225', 'default')
class Rust(Fundamental):
name = 'rust'
extensions = ['.rs']
grammar = RustGrammar
opentokens = ('delimiter',)
opentags = {'(': ')', '[': ']', '{': '}'}
closetokens = ('delimiter',)
closetags = {')': '(', ']': '[', '}': '{'}
commentc = '//'
tabbercls = RustTabber
colors = {
'rust.comment': hi_red,
'rust.comment.start': hi_red,
'rust.comment.data': hi_red,
'rust.comment.end': hi_red,
'rust.param': lo_yellow,
'rust.type': hi_green,
'rust.delimiter': lo_cyan,
'rust.operator': lo_cyan,
#'c.include': hi_blue,
#'c.header': lo_orange,
'rust.integer': hi_orange,
#'rust.bareword': lo_cyan,
}
config = {
#'c.syntax-cmd': "gcc -x c -fsyntax-only %(path)s",
#'c.syntax-rel-dir': False,
#'c.make-cmd': "make",
#'c.make-rel-dir': True,
}
lconfig = {
#'ignore_suffix': ['.o'],
}
_bindings = {
'close-paren': (')',),
'close-brace': ('}',),
'close-bracket': (']',),
#'c-check-syntax': ('C-c s',),
#'c-make': ('C-c C-c',),
}
#def get_functions(self): return {}
#def get_function_names(self): return []
#def get_line_function(self, y): return None
#def get_status_names(self):
# names = Fundamental.get_status_names(self)
# c = self.window.logical_cursor()
# names['func'] = self.get_line_function(c.y)
# return names
install = Rust.install