-- Copyright 2015-2018 Alejandro Baez (https://keybase.io/baez). See License.txt. -- Rust LPeg lexer. local lexer = require("lexer") local token, word_match = lexer.token, lexer.word_match local P, R, S = lpeg.P, lpeg.R, lpeg.S local lex = lexer.new('rust') -- Whitespace. lex:add_rule('whitespace', token(lexer.WHITESPACE, lexer.space^1)) -- Keywords. lex:add_rule('keyword', token(lexer.KEYWORD, word_match[[ abstract alignof as become box break const continue crate do else enum extern false final fn for if impl in let loop macro match mod move mut offsetof override priv proc pub pure ref return Self self sizeof static struct super trait true type typeof unsafe unsized use virtual where while yield ]])) -- Functions. lex:add_rule('function', token(lexer.FUNCTION, lexer.word^1 * S("!"))) -- Library types lex:add_rule('library', token(lexer.LABEL, lexer.upper * (lexer.lower + lexer.dec_num)^1)) -- Types. lex:add_rule('type', token(lexer.TYPE, word_match[[ () bool isize usize char str u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 ]])) -- Strings. local sq_str = P('L')^-1 * lexer.delimited_range("'") local dq_str = P('L')^-1 * lexer.delimited_range('"') local raw_str = '#"' * (lexer.any - '#')^0 * P('#')^-1 lex:add_rule('string', token(lexer.STRING, dq_str + raw_str)) -- Identifiers. lex:add_rule('identifier', token(lexer.IDENTIFIER, lexer.word)) -- Comments. local line_comment = '//' * lexer.nonnewline_esc^0 local block_comment = '/*' * (lexer.any - '*/')^0 * P('*/')^-1 lex:add_rule('comment', token(lexer.COMMENT, line_comment + block_comment)) -- Numbers. lex:add_rule('number', token(lexer.NUMBER, lexer.float + P('0b')^-1 * (lexer.dec_num + "_")^1 + lexer.integer)) -- Operators. lex:add_rule('operator', token(lexer.OPERATOR, S('+-/*%<>!=`^~@&|?#~:;,.()[]{}'))) -- Attributes. lex:add_rule('preprocessor', token(lexer.PREPROCESSOR, "#[" * (lexer.nonnewline - ']')^0 * P("]")^-1)) -- Fold points. lex:add_fold_point(lexer.COMMENT, '/*', '*/') lex:add_fold_point(lexer.COMMENT, '//', lexer.fold_line_comments('//')) lex:add_fold_point(lexer.OPERATOR, '(', ')') lex:add_fold_point(lexer.OPERATOR, '{', '}') return lex