VimL grammar
Target
File = {Statement};
Statements
Statement = LetStatement| UnletStatement | SetStatement | FunctionDefinition | Conditional;
InFunctionStatement = LetStatement | UnletStatement | SetStatement | InFunctionConditional | ReturnStatement;
AssignmentStatement = ((ListItem | Sublist | DictionaryEntry), '=', Expression) |
((InternalVariable | Option), ('=' | '+=' | '-=' | '.='), Expression) |
((EnvironmentVariable | Register), ('=' | '.='), Expression) |
('[', InternalVariable, {',', InternalVariable}, [';', InternalVariable], ']',
('=' | '+=' | '-=' | '.='), Expression);
LetStatement = 'let', ({Variable} | AssignmentStatement);
UnletStatement = 'unl', ['et'], ['!'], InternalVariable, {InternalVariable}; (* up to 20 variables *)
(* Decimal number in LockVariableStatement and UnlockVariableStatement is: 1 <= n <= 100 *)
LockVariableStatement = 'lockv', ['ar'], ['!'], [Decimal], InternalVariable, {InternalVariable}; (* up to 20 variables *)
UnlockVariableStatement = 'unlo', ['ckvar'], ['!'], [Decimal], InternalVariable, {InternalVariable}; (* up to 20 variables *)
SetStatement = 'se', ['t'], [('all', ['&']) | 'termcap' | {SetOption}];
SetOption = (( 'no' | 'inv' ), Identifier) |
(Identifier, [ '?' | '!' | '&' ]) |
(Identifier, ( '=' | ':' | '+=' | '^=' | '-=' ), Expression);
ReturnStatement = 'retu', ['rn'], Expression;
Definition
FunctionDefinition = 'fu', ['nction'], [!], UserFunctionName, '(', [Variable, {',', Variable}], ')',
{InFunctionStatement},
'endf', ['unction'];
Conditionals
Conditional = 'if', Condition, {Statement},
[{'elsei', ['f'], Condition, {Statement}}],
['el', ['se'], {Statement}],
'en', ['dif'];
InFunctionConditional = 'if', Condition, {InFunctionStatement},
[{'elsei', ['f'], Condition, {InFunctionStatement}}],
['el', ['se'], {InFunctionStatement}],
'en', ['dif'];
Condition = Expression;
Expressions
(* If ExpressionN cannot be parsed, it must be parsed as ExpressionM, M = N + 1. *)
Expression = Expression1;
Expression1 = Expression2, '?', Expression1, ':', Expression1;
Expression2 = Expression3, LogicalOr, Expression3;
Expression3 = Expression4, LogicalAnd, Expression4;
Expression4 = Expression5, ComparisonOperator, Expression5;
Expression5 = Expression6, ('+' | '-' | '.'), Expression6;
Expression6 = Expression7, ('*' | '/' | '%'), Expression7;
Expression7 = UnaryOperator, Expression7;
Expression8 = ListItem | Sublist | DictionaryEntry;
Expression9 = Value | Variable | NestedExpression | FunctionCall;
NestedExpression = '(', Expression, ')';
FunctionCall = Identifier, '(', [FunctionParameter, {',', FunctionParameter}], ')';
FunctionParameter = Expression;
ListItem = Variable, '[', Expression, ']';
Sublist = Variable, '[', Expression, ':', Expression, ']';
DictionaryEntry = Variable, '.', KeyString;
KeyString = (Letter | DecimalDigit | '_'), {(Letter | DecimalDigit | '_')};
Operators
UnaryOperator = '!' | '-' | '+';
BinaryLogicalOperator = LogicalOr | LogicalAnd;
LogicalOr = '||';
LogicalAnd = '&&';
ComparisonOperator = (('==' | '!=' | '>' | '>=' | '<' | '<=' | '=~' | '!~'), ['#' | '?']) | 'is' | 'isnot';
AssignmentOperator = '=' | '+=' | '-=' | '*=' | '/=';
BinaryArithmeticOperator = '+' | '-' | '.' | '*' | '/' | '%';
Various identifiers
UserFunctionName = UppercaseLetter, {Letter | '_' | DecimalDigit};
BuiltInFunctionName = LowercaseLetter, {Letter | '_' | DecimalDigit};
Identifier = Name;
Variable = EnvironmentVariable | Option | Register | InternalVariable | Identifier;
EnvironmentVariable = '$', Name;
Option = '&', [('g' | 'l'), ':'], Name;
Register = '@', Name;
InternalVariable = ('a' | 'b' | 'g' | 'l' | 's' | 't' | 'v' | 'w' ), ':', Name;
Name = ( Letter | '_' ), { ( Letter | '_' | DecimalDigit ) };
Constants
Value = Number | String | Funcref | List | Dictionary;
Dictionary = '{', [(String | Number), ':', Expression], '}';
List = '[', [Value, {',', Value}], ']';
Funcref = 'function(', String, ')';
String = ('"', {AnyCharacter - '"'}, '"') | ("'", {AnyCharacter - "'"}, "'");
Number = Integer | Float;
Integer = DecimalNumber | HexadecimalNumber | OctalNumber;
Float = [ '-' | '+' ], DecimalNumber, '.', DecimalNumber, [ ( 'e' | 'E' ), [ [ '-' | '+' ], DecimalNumber ];
DecimalNumber = '0' | ( [ '-' | '+' ], ( DecimalDigitExcludingZero, { DecimalDigit } ) );
HexadecimalNumber = '0', ( 'x' | 'X' ), HexadecimalDigit, { HexadecimalDigit };
OctalNumber = '0', OctalDigit, { OctalDigit };
Symbols
DecimalDigitExcludingZero = '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9';
DecimalDigit = '0' | DecimalDigitExcludingZero;
HexadecimalDigit = DecimalDigit | 'a' | 'A' | 'b' | 'B' | 'c' | 'C' | 'd' | 'D' | 'e' | 'E' | 'f' | 'F';
OctalDigit = '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7';
Letter = UppercaseLetter | LowercaseLetter;
UppercaseLetter = 'A' | 'B' | 'C' | 'D' | 'E' | 'F' | 'G' | 'H' | 'I' | 'J' | 'K' | 'L' | 'M' | 'N' | 'O' |
'P' | 'Q' | 'R' | 'S' | 'T' | 'U' | 'V' | 'W' | 'X' | 'Y' | 'Z';
LowercaseLetter = 'a' | 'b' | 'c' | 'd' | 'e' | 'f' | 'g' | 'h' | 'i' | 'j' | 'k' | 'l' | 'm' | 'n' | 'o' |
'p' | 'q' | 'r' | 's' | 't' | 'u' | 'v' | 'w' | 'x' | 'y' | 'z';
Whitespace = ' ', {' '};
NewlineCharacter = [ '\r' | '\r\n' | '\n' ];
AnyCharacter = ? any visible character ?