BNF Grammar: Difference between revisions

From Rosetta Code
Content added Content deleted
No edit summary
m (→‎Pascal: move to pacsal page)
 
(89 intermediate revisions by 25 users not shown)
Line 1: Line 1:
{{DeprecatedTask}}
{{task|BNF GRAMMAR}}
In computer science, Backus–Naur Form (BNF) is a metasyntax used to express context-free grammars: that is, a formal way to describe formal languages. John Backus and Peter Naur developed a context free grammar to define the syntax of a programming language by using two sets of rules: i.e., lexical rules and syntactic rules.
In computer science, Backus–Naur Form (BNF) is a metasyntax used to express context-free grammars: that is, a formal way to describe formal languages. John Backus and Peter Naur developed a context free grammar to define the syntax of a programming language by using two sets of rules: i.e., lexical rules and syntactic rules.


Line 6: Line 6:
There are many extensions and variants of BNF, including Extended and Augmented Backus–Naur Forms (EBNF and ABNF).
There are many extensions and variants of BNF, including Extended and Augmented Backus–Naur Forms (EBNF and ABNF).


'''This is a deprecated task. Please move these grammars to the language's category page, or somewhere else.'''
The task here is establish a BNF grammar for as many languages as possible to facilitate language categorization and translation.

=={{header|4D}}==
==[[:Category:BASIC|BASIC]]==
=={{header|ALGOL 60}}==
<div style="height:30ex;overflow:scroll"><pre>
<pre>
! ----------------------------------------------------------------------------
! -----------------------------------------------------------------------
! ALGOL 60
! BASIC '64
!
!
! Beginner's All-purpose Symbolic Instruction Code
! (ALGO)rithmic (L)anguage
!
!
! ALGOL is, by far, the most influential programming language developed to
! "It is practically impossible to teach good programming style to students
! that have had prior exposure to BASIC; as potential programmers they are
! date. Although is did not achieve mass use, a large number of syntactic
! mentally mutilated beyond hope of regeneration."
! and semantic principles and concepts were developed and incorporated into
! the language. As a result, ALGOL is considered the main reference language
! in computer science.
!
! In the late 1950's, many in the study of computer science believed that a
! new universal programming language was needed. This new language would be
! used through the study of computer science and would eventually replace
! other popular languages such as FORTRAN.
!
! The ACM (Association for Computing Machinery) and GAMM (a European
! organization of mathematics and mechanics) created an international
! committee to define and document the new language. This committee
! included computer scientists from both North America and Europe.
!
! The process of developing ALGOL included a number of challenges:
!
! First, the computers of the era varied greatly in the number of characters
! that could be represented. This made it difficult to define the exact
! lexics of the language. For instance, one mainframe could contain an
! ampersand character (&) while another may not.
!
! Another challenge involved an issue that nowadays seems trival - the
! representation of decimal points. In the 50 United States and Canada, real
! numbers are represented using a period. For instance, the value 4 1/2 can
! be written as "4.5". Europe, on the other hand, uses a comma. The same
! value is represented with "4,5". Both sides were steadfast that their
! format was superior. Although the "period" format would eventually
! dominate, this was a major issue at the time.
!
! To describe the syntax of the first version of ALGOL, Peter Naur modified
! Backus Normal Form to create Backus-Naur Form. This format is now used
! universially to describe the syntax of programming languages.
!
! To spite these challenges, ALGOL created a number of language features
! that would be incorporated into its numerious successors. These include:
!
! * Block structure
! * Free-form structure (elements are not required to be in a specific column)
! * Pass by Name (while powerful, it is not used in modern languages)
! * The For-Loop
! * The 'Else' clause on if-statements (LISP's 'cond' predates this though)
! * Reserved words
!
! The grammar below was, for the most part, cut and pasted from "Revised
! Report on the Algorithmic Language: Algol 60" by Peter Naur. The numbered
! sections refer directly to the chapters in the Report.
!
!
! - Edsger W. Dijkstra
! The grammar was modified to remove ambigities and define terminals using
! regular expressions.
!
!
! BASIC is one of the oldest programming language and one of the most popular.
! ----------------------------------------------------------------------------
! It was developed in 1964 by John G. Kemeny and Thomas E. Kurtz to teach
! students the basics of programming concepts. At the advent of the microcomputer,
! BASIC was implemented on numerous platforms such as the Commodore, Atari,
! Apple II, Altair, IBM PC computers. Over time, BASIC evolved into GW-BASIC,
! QBasic, Visual Basic, and recently Visual Basic .NET.
!
! In practically all programming languages, the reserved word/symbol that denotes
! a comment is treated as a form of whitespace - having no effect in the manner in
! which the program runs. Once such type of comment is used to indicate the remainder
! of the line is to be ignored. These can be added to the end of any line without
! changing the meaning of the program. In C++, it is the '//' symbol;
! in BASIC '64 it is 'REM'.
!
! However, in the BASIC programming language, the line comment is treated like a
! statement. For instance, if 'REM' was a normal line comment:
!
! 10 PRINT "Hello World" REM Common first program
!
! would be a valid statement. However, in BASIC, this is illegal. In the example
! above, the comment must be added as an additional statement.
!
! 10 PRINT "Hello World" : REM Common first program
!
! As a result, the Line Comment terminal that is used in the GOLD Parser cannot be
! used here. In the grammar below, a 'Remark' terminal was created that accepts all
! series of printable characters starting with the characters "REM ". In some
! implementations of BASIC, any string starting with "REM" is a comment statement.
! Examples include "REMARK", "REMARKABLE" and "REMODEL". This grammar requires the space.
!
! This grammar does not include the editor statements such as NEW, SAVE, LOAD, etc...
!
! Note: This is an ad hoc version of the language. If there are any flaws, please
! e-mail GOLDParser@DevinCook.com and I will update the grammar. Most likely I have
! included features not available in BASIC '64.
! -----------------------------------------------------------------------




"Name" = 'ALGOL 60'
"Name" = 'BASIC (Beginners All-purpose Symbolic Instruction Code)'
"Author" = 'John G. Kemeny and Thomas E. Kurtz'
"Version" = '1960'
"Version" = '1964 - Original - before Microsoft enhanced the language for the IBM PC.'
"About" = 'BASIC is one of most common and popular teaching languages ever created. '


"Case Sensitive" = False
"Author" = 'J.W. Backus, F.L. Bauer, J.Green, C. Katz, J. McCarthy, P. Naur,'
"Start Symbol" = <Lines>
| 'A.J. Perlis, H. Rutishauser, K. Samuelson, B. Vauquois,'
| 'J.H. Wegstein, A. van Wijngaarden, M. Woodger'


{String Chars} = {Printable} - ["]
"About" = 'ALGOL (ALGOrithmic Language) is the most influential'
{WS} = {Whitespace} - {CR} - {LF}
| 'programming language to date. Although it did not achieve'
| 'mass use, it established multiple syntactic and semantic'
| 'features used in languages today.'


NewLine = {CR}{LF}|{CR}
Whitespace = {WS}+


Remark = REM{Space}{Printable}*
"Start Symbol" = <program>
ID = {Letter}[$%]?
String = '"'{String Chars}*'"'
Integer = {digit}+
Real = {digit}+.{digit}+


<Lines> ::= Integer <Statements> NewLine <Lines>
| Integer <Statements> NewLine


<Statements> ::= <Statement> ':' <Statements>
! ========================================================== Terminals
| <Statement>


<Statement> ::= CLOSE '#' Integer
| DATA <Constant List>
| DIM ID '(' <Integer List> ')'
| END
| FOR ID '=' <Expression> TO <Expression>
| FOR ID '=' <Expression> TO <Expression> STEP Integer
| GOTO <Expression>
| GOSUB <Expression>
| IF <Expression> THEN <Statement>
| INPUT <ID List>
| INPUT '#' Integer ',' <ID List>
| LET Id '=' <Expression>
| NEXT <ID List>
| OPEN <Value> FOR <Access> AS '#' Integer
| POKE <Value List>
| PRINT <Print list>
| PRINT '#' Integer ',' <Print List>
| READ <ID List>
| RETURN
| RESTORE
| RUN
| STOP
| SYS <Value>
| WAIT <Value List>
| Remark


<Access> ::= INPUT
{String Ch} = {Printable} - [`] - ['']
| OUPUT
<ID List> ::= ID ',' <ID List>
| ID


<Value List> ::= <Value> ',' <Value List>
Identifier = {Letter}{Alphanumeric}*
| <Value>


<Constant List> ::= <Constant> ',' <Constant List>
String = '`' ( '`' {String Ch}* '' | {String Ch} )* ''
| <Constant>


<Integer List> ::= Integer ',' <Integer List>
IntegerLiteral = {Digit}+
| Integer
RealLiteral = {Digit}+ '.' {Digit}+ (e {Digit}+)?
<Expression List> ::= <Expression> ',' <Expression List>
| <Expression>


<Print List> ::= <Expression> ';' <Print List>
| <Expression>
|


<Expression> ::= <And Exp> OR <Expression>
! =========================================================== Rules
| <And Exp>


<And Exp> ::= <Not Exp> AND <And Exp>
<unsigned integer>
::= IntegerLiteral
| <Not Exp>
<unsigned number>
<Not Exp> ::= NOT <Compare Exp>
::= IntegerLiteral
| <Compare Exp>
| RealLiteral


<Compare Exp> ::= <Add Exp> '=' <Compare Exp>
| <Add Exp> '<>' <Compare Exp>
| <Add Exp> '><' <Compare Exp>
| <Add Exp> '>' <Compare Exp>
| <Add Exp> '>=' <Compare Exp>
| <Add Exp> '<' <Compare Exp>
| <Add Exp> '<=' <Compare Exp>
| <Add Exp>


<Add Exp> ::= <Mult Exp> '+' <Add Exp>
! ====================================================================
| <Mult Exp> '-' <Add Exp>
! 2.2.2 Logical values.
| <Mult Exp>
! ====================================================================


<Mult Exp> ::= <Negate Exp> '*' <Mult Exp>
<logical value> ::= true | false
| <Negate Exp> '/' <Mult Exp>
| <Negate Exp>


<Negate Exp> ::= '-' <Power Exp>
| <Power Exp>


<Power Exp> ::= <Power Exp> '^' <Value>
| <Value>


<Value> ::= '(' <Expression> ')'
! ====================================================================
| ID
! 3. Expressions
| ID '(' <Expression List> ')'
! ====================================================================
| <Constant>


<Constant> ::= Integer
<expression>
::= <Boolean expression>
| String
| Real
</pre></div>
==[[:Category:BASIC Commodore PET|BASIC Commodore PET]]==
<div style="height:30ex;overflow:scroll"><pre>
! -----------------------------------------------------------------------
! Commodore PET BASIC
!
! Beginner's All-purpose Symbolic Instruction Code
!
! "It is practically impossible to teach good programming style to students
! that have had prior exposure to BASIC; as potential programmers they are
! mentally mutilated beyond hope of regeneration."
!
! - Edsger W. Dijkstra
!
!
! BASIC is one of the oldest programming language and one of the most popular.
! It was developed in 1964 by John G. Kemeny and Thomas E. Kurtz to teach
! students the basics of programming concepts. At the advent of the microcomputer,
! BASIC was implemented on numerous platforms such as the Commodore, Atari,
! Apple II, Altair, IBM PC computers. Over time, BASIC evolved into GW-BASIC,
! QBasic, Visual Basic, and recently Visual Basic .NET.
!
! In practically all programming languages, the reserved word/symbol that denotes
! a comment is treated as a form of whitespace - having no effect in the manner in
! which the program runs. Once such type of comment is used to indicate the remainder
! of the line is to be ignored. These can be added to the end of any line without
! changing the meaning of the program. In C++, it is the '//' symbol.
!
! However, in the BASIC programming language, the line comment is treated like a
! statement. For instance, if 'REM' was a normal line comment:
!
! 10 PRINT "Hello World" REM Common first program
!
! would be a valid statement. However, in BASIC, this is illegal. In the example
! above, the comment must be added as an additional statement.
!
! 10 PRINT "Hello World" : REM Common first program
!
! As a result, the Line Comment terminal that is used in the GOLD Parser cannot be
! used here. In the grammar below, a 'Remark' terminal was created that accepts all
! series of printable characters starting with the characters "REM ". In some
! implementations of BASIC, any string starting with "REM" is a comment statement.
! Examples include "REMARK", "REMARKABLE" and "REMODEL". This grammar requires the space.
!
! -----------------------------------------------------------------------


! ====================================================================
! 3.1. Variables
! ====================================================================


"Name" = 'Commodore PET BASIC'
<subscript expression>
"Author" = 'Commodore Business Machines'
::= <arithmetic expression>
"Version" = '2.0'
"About" = 'This is the version of BASIC that was used on the Commodore 64.'


"Case Sensitive" = False
<subscript list>
"Start Symbol" = <Lines>
::= <subscript expression>
| <subscript list> ',' <subscript expression>


{String Chars} = {Printable} - ["]
{WS} = {Whitespace} - {CR} - {LF}


NewLine = {CR}{LF}|{CR}
<variable>
::= Identifier
Whitespace = {WS}+
| Identifier '[' <subscript list> ']' ! subscripted value


Remark = REM{Space}{Printable}*
! ====================================================================
ID = {Letter}{Alphanumeric}?[$%]? !IDs are can only have a maximum of 2 characters
! 3.2. Function designators
FunctionID = FN {Letter}{Letter}?
! ====================================================================


String = '"'{String Chars}*'"'
<actual parameter>
::= String
Integer = {Digit}+
| <expression>
Real = {Digit}+'.'{Digit}+


<Lines> ::= <Lines> <Line>
<parameter delimiter>
::= ','
| <Line>
| ')' Identifier ':' '('


<Line> ::= Integer <Statements> NewLine
<Statements> ::= <Statements> ':' <Statement>
| <Statement>


<Statement> ::= CLOSE Integer
<actual parameter list>
::= <actual parameter>
| CLR
| <actual parameter list> <parameter delimiter> <actual parameter>
| CMD <Expression>
| CONT !Continue
| DATA <Constant List>
| DEF FunctionID '(' <ID List> ')' '=' <Expression> !The ID must start with FN
| DIM ID '(' <Expression List> ')'
| END
| FOR ID '=' <Expression> TO <Expression> <Step Opt>
| GET ID
| GET '#' Integer ',' ID
| GOSUB <Expression>
| GOTO <Expression>
| IF <Expression> THEN <Then Clause>
| INPUT <ID List>
| INPUT '#' Integer ',' <ID List>
| LET ID '=' <Expression>
| LIST <Line Range>
| LOAD <Value List>
| ID '=' <Expression>
| NEW
| NEXT <ID List>
| ON ID GOTO <Expression List>
| OPEN <Expression List>
| POKE <Expression> ',' <Expression>
| PRINT <Print list>
| PRINT '#' Integer ',' <Print List>
| READ <ID List>
| RETURN
| RESTORE
| RUN
| RUN <Expression>
| STOP
| SYS <Expression>
| WAIT <Expression List>
| VERIFY <Expression List>
| Remark


<Step Opt> ::= STEP <Expression>
|
<ID List> ::= ID ',' <ID List>
| ID


<Value List> ::= <Value> ',' <Value List>
! ====================================================================
| <Value>
! 3.3. Arithmetic expressions
! ====================================================================


<Constant List> ::= <Constant> ',' <Constant List>
<adding operator> ::= '+' | '-'
| <Constant>
<Expression List> ::= <Expression> ',' <Expression List>
| <Expression>


<Print List> ::= <Expression> ';' <Print List>
<multiplying operator> ::= '*' | '/' | 'div'
| <Expression>
|


<Line Range> ::= Integer
<primary>
::= <unsigned number>
| Integer '-'
| <variable>
| Integer '-' Integer
| Identifier '(' <actual parameter list> ')'
| '(' <arithmetic expression> ')'


<Then Clause> ::= Integer
<factor>
::= <primary>
| <Statement>
| <factor> '^' <primary> !Originally an up-arrow
<term>
::= <factor>
| <term> <multiplying operator> <factor>


! ----------------------------------------------- Expressions


<Expression> ::= <And Exp> OR <Expression>
<simple arithmetic expression>
::= <term>
| <And Exp>
| <adding operator> <term>
| <simple arithmetic expression> <adding operator> <term>


<if clause> ::= if <Boolean expression> then
<And Exp> ::= <Not Exp> AND <And Exp>
| <Not Exp>
<Not Exp> ::= NOT <Compare Exp>
| <Compare Exp>


<Compare Exp> ::= <Add Exp> '=' <Compare Exp>
<arithmetic expression>
::= <simple arithmetic expression>
| <Add Exp> '<>' <Compare Exp>
| <if clause> <simple arithmetic expression> else <arithmetic expression>
| <Add Exp> '>' <Compare Exp>
| <Add Exp> '>=' <Compare Exp>
| <Add Exp> '<' <Compare Exp>
| <Add Exp> '<=' <Compare Exp>
| <Add Exp>


<Add Exp> ::= <Mult Exp> '+' <Add Exp>
| <Mult Exp> '-' <Add Exp>
| <Mult Exp>


<Mult Exp> ::= <Negate Exp> '*' <Mult Exp>
| <Negate Exp> '/' <Mult Exp>
| <Negate Exp>


<Negate Exp> ::= '-' <Power Exp>
! ====================================================================
| <Power Exp>
! 3.4. Boolean expressions
! ====================================================================


<Power Exp> ::= <Power Exp> '^' <Sub Exp> !On the Commodore, the symbol was an up-arrow
<relational operator> ::= '<' | '<=' | '=' | '>=' | '>' | '~='
| <Sub Exp>


<Sub Exp> ::= '(' <Expression> ')'
| <Value>


<Value> ::= ID
<relation>
| ABS '(' <Expression> ')'
::= <relation> <relational operator> <simple arithmetic expression>
| <simple arithmetic expression>
| ASC '(' <Expression> ')'
| ATN '(' <Expression> ')'
| 'CHR$' '(' <Expression> ')'
| COS '(' <Expression> ')'
| EXP '(' <Expression> ')'
| FunctionID '(' <Expression List> ')'
| FRE '(' <Value> ')' !The <Value> is irrelevant
| INT '(' <Expression> ')'
| 'LEFT$' '(' <Expression> ',' <Expression> ')'
| LEN '(' <Expression> ')'
| PEEK '(' <Expression> ')'
| POS '(' <Value> ')' !The <Value> is irrelevant
| 'RIGHT$' '(' <Expression> ',' <Expression> ')'
| RND '(' <Expression> ')'
| SGN '(' <Expression> ')'
| SPC '(' <Expression> ')'
| SQR '(' <Expression> ')'
| TAB '(' <Expression> ')'
| TAN '(' <Expression> ')'
| VAL '(' <Expression> ')'
| <Constant>


<Constant> ::= Integer
<Boolean primary>
::= <logical value>
| String
| <relation>
| Real


</pre></div>
<Boolean secondary>
::= <Boolean primary>
| not <Boolean primary>


==[[:Category:Brainf***|Brainf***]]==


Code ::= Command Code | <NONE>
<Boolean factor>
Command ::= "+" | "-" | "<" | ">" | "," | "." | "[" Code "]" | <ANY>
::= <Boolean secondary>
| <Boolean factor> and <Boolean secondary>


==[[:Category:PARI/GP|PARI/GP]]==
<Boolean term>
[http://pari.math.u-bordeaux.fr/cgi-bin/viewcvs.cgi/trunk/src/language/parse.y?view=markup&revision=12950&root=pari parse.y] contains a grammar for GP. The grammar for PARI is that of [http://c.comsci.us/syntax/ C].
::= <Boolean factor>
| <Boolean term> or <Boolean factor>


==[[:Category:PowerShell|PowerShell]]==
<implication>
An annotated version of the PowerShell grammar can be found in Bruce Payette's book ''Windows PowerShell in Action''. The appendix containing the grammar is available in [http://www.manning.com/payette/AppCexcerpt.pdf PDF form] on the publisher's site.
::= <Boolean term>
| <implication> implies <Boolean term>


This grammar does not accurately represent the PowerShell language, though, as for example the <code>for</code> loop mandates semicolons in the grammar but in practice does not require them when arguments are omitted. The infinite loop may be represented by
<simple Boolean>
<lang powershell>for () {}</lang>
::= <implication>
but the grammar would require
| <simple Boolean> eqv <implication>
<lang powershell>for (;;) {}</lang>


==[[:Category:VBScript|VBScript]]==
<div style="height:30ex;overflow:scroll"><pre>
!===============================
! VB Script grammar.
!
! To create the grammar I was using Microsoft's VB Script documentation
! available from http://msdn.microsoft.com/scripting,
! VB Script parser from ArrowHead project http://www.tripi.com/arrowhead/,
! and Visual Basic .Net grammar file written by Devin Cook.
!
! This grammar cannot cover all aspects of VBScript and may have some errors.
! Feel free to contact me if you find any flaws in the grammar.
!
! Vladimir Morozov vmoroz@hotmail.com
!
! Special thanks to Nathan Baulch for the grammar updates.
!
! USE GOLD PARSER BUILDER VERSION 2.1 AND LATER TO COMPILE THIS GRAMMAR.
!===============================


"Name" = 'VB Script'
<Boolean expression>
"Author" = 'John G. Kemeny and Thomas E. Kurtz'
::= <simple Boolean>
"Version" = '5.0'
| <if clause> <simple Boolean> else <Boolean expression>
"About" = 'VB Script grammar.'
"Case Sensitive" = False
"Start Symbol" = <Program>


!===============================
! Character sets
!===============================


{String Char} = {All Valid} - ["]
! ====================================================================
{Date Char} = {Printable} - [#]
! 3.5. Designational expressions
{ID Name Char} = {Printable} - ['['']']
! ====================================================================
{Hex Digit} = {Digit} + [abcdef]
{Oct Digit} = [01234567]
{WS} = {Whitespace} - {CR} - {LF}
{ID Tail} = {Alphanumeric} + [_]


!===============================
<label>
! Terminals
::= Identifier
!===============================
| <Unsigned Integer>


NewLine = {CR} {LF}
<switch designator>
::= Identifier '[' <subscript expression> ']'
| {CR}
| {LF}
| ':'


! Special white space definition. Whitespace is either space or tab, which
<simple designational expression>
! can be followed by continuation symbol '_' followed by new line character
::= <label>
Whitespace = {WS}+
| <switch designator>
| '(' <designational expression> ')'
| '_' {WS}* {CR}? {LF}?


! Special comment definition
<designational expression>
Comment Line = ''
::= <simple designational expression>
| 'Rem'
| <if clause> <simple designational expression> else <designational expression>


! Literals
StringLiteral = '"' ( {String Char} | '""' )* '"'
IntLiteral = {Digit}+
HexLiteral = '&H' {Hex Digit}+ '&'?
OctLiteral = '&' {Oct Digit}+ '&'?
FloatLiteral = {Digit}* '.' {Digit}+ ( 'E' [+-]? {Digit}+ )?
| {Digit}+ 'E' [+-]? {Digit}+
DateLiteral = '#' {Date Char}+ '#'


! Identifier is either starts with letter and followed by letter,
! ====================================================================
! number or underscore, or it can be escaped sequence of any printable
! 4.1. Compound statements and blocks
! characters ([] and [_$% :-) @] are valid identifiers)
! ====================================================================
ID = {Letter} {ID Tail}*
| '[' {ID Name Char}* ']'


! White space is not allowed to be before dot, but allowed to be after it.
<unlabelled basic statement>
::= <assignment statement>
IDDot = {Letter} {ID Tail}* '.'
| <go to statement>
| '[' {ID Name Char}* ']' '.'
| !EMPTY !dummy statement
| 'And.'
| <procedure statement>
| 'ByRef.'
| 'ByVal.'
| 'Call.'
| 'Case.'
| 'Class.'
| 'Const.'
| 'Default.'
| 'Dim.'
| 'Do.'
| 'Each.'
| 'Else.'
| 'ElseIf.'
| 'Empty.'
| 'End.'
| 'Eqv.'
| 'Erase.'
| 'Error.'
| 'Exit.'
| 'Explicit.'
| 'False.'
| 'For.'
| 'Function.'
| 'Get.'
| 'GoTo.'
| 'If.'
| 'Imp.'
| 'In.'
| 'Is.'
| 'Let.'
| 'Loop.'
| 'Mod.'
| 'New.'
| 'Next.'
| 'Not.'
| 'Nothing.'
| 'Null.'
| 'On.'
| 'Option.'
| 'Or.'
| 'Preserve.'
| 'Private.'
| 'Property.'
| 'Public.'
| 'Redim.'
| 'Rem.'
| 'Resume.'
| 'Select.'
| 'Set.'
| 'Step.'
| 'Sub.'
| 'Then.'
| 'To.'
| 'True.'
| 'Until.'
| 'WEnd.'
| 'While.'
| 'With.'
| 'Xor.'


! The following identifiers should only be used in With statement.
! This rule must be checked by contextual analyzer.
DotID = '.' {Letter} {ID Tail}*
| '.' '[' {ID Name Char}* ']'
| '.And'
| '.ByRef'
| '.ByVal'
| '.Call'
| '.Case'
| '.Class'
| '.Const'
| '.Default'
| '.Dim'
| '.Do'
| '.Each'
| '.Else'
| '.ElseIf'
| '.Empty'
| '.End'
| '.Eqv'
| '.Erase'
| '.Error'
| '.Exit'
| '.Explicit'
| '.False'
| '.For'
| '.Function'
| '.Get'
| '.GoTo'
| '.If'
| '.Imp'
| '.In'
| '.Is'
| '.Let'
| '.Loop'
| '.Mod'
| '.New'
| '.Next'
| '.Not'
| '.Nothing'
| '.Null'
| '.On'
| '.Option'
| '.Or'
| '.Preserve'
| '.Private'
| '.Property'
| '.Public'
| '.Redim'
| '.Rem'
| '.Resume'
| '.Select'
| '.Set'
| '.Step'
| '.Sub'
| '.Then'
| '.To'
| '.True'
| '.Until'
| '.WEnd'
| '.While'
| '.With'
| '.Xor'


DotIDDot = '.' {Letter}{ID Tail}* '.'
<basic statement>
| '.' '[' {ID Name Char}* ']' '.'
::= <unlabelled basic statement>
| <label> ':' <basic statement>
| '.And.'
| '.ByRef.'
| '.ByVal.'
| '.Call.'
| '.Case.'
| '.Class.'
| '.Const.'
| '.Default.'
| '.Dim.'
| '.Do.'
| '.Each.'
| '.Else.'
| '.ElseIf.'
| '.Empty.'
| '.End.'
| '.Eqv.'
| '.Erase.'
| '.Error.'
| '.Exit.'
| '.Explicit.'
| '.False.'
| '.For.'
| '.Function.'
| '.Get.'
| '.GoTo.'
| '.If.'
| '.Imp.'
| '.In.'
| '.Is.'
| '.Let.'
| '.Loop.'
| '.Mod.'
| '.New.'
| '.Next.'
| '.Not.'
| '.Nothing.'
| '.Null.'
| '.On.'
| '.Option.'
| '.Or.'
| '.Preserve.'
| '.Private.'
| '.Property.'
| '.Public.'
| '.Redim.'
| '.Rem.'
| '.Resume.'
| '.Select.'
| '.Set.'
| '.Step.'
| '.Sub.'
| '.Then.'
| '.To.'
| '.True.'
| '.Until.'
| '.WEnd.'
| '.While.'
| '.With.'
| '.Xor.'


!===============================
<unconditional statement>
! Rules
::= <basic statement>
!===============================
| <compound statement>
| <block>


<NL> ::= NewLine <NL>
<statement>
| NewLine
::= <unconditional statement>
| <conditional statement>
| <for statement>


<Program> ::= <NLOpt> <GlobalStmtList>
<compound tail>
::= <statement> end
| <statement> ';' <compound tail>


!===============================
<block head>
! Rules : Declarations
::= begin <declaration>
!===============================
| <block head> ';' <declaration>


<ClassDecl> ::= 'Class' <ExtendedID> <NL> <MemberDeclList> 'End' 'Class' <NL>
<unlabelled block>
::= <block head> ';' <compound tail>


<MemberDeclList> ::= <MemberDecl> <MemberDeclList>
<unlabelled compound>
::= begin <compound tail>
|


<MemberDecl> ::= <FieldDecl>
<compound statement>
| <VarDecl>
::= <unlabelled compound>
| <label> ':' <compound statement>
| <ConstDecl>
| <SubDecl>
| <FunctionDecl>
| <PropertyDecl>


<FieldDecl> ::= 'Private' <FieldName> <OtherVarsOpt> <NL>
<block>
| 'Public' <FieldName> <OtherVarsOpt> <NL>
::= <unlabelled block>
| <label> ':' <block>


<FieldName> ::= <FieldID> '(' <ArrayRankList> ')'
<program>
::= <block>
| <FieldID>
| <compound statement>


<FieldID> ::= ID
| 'Default'
| 'Erase'
| 'Error'
| 'Explicit'
| 'Step'


<VarDecl> ::= 'Dim' <VarName> <OtherVarsOpt> <NL>
! ====================================================================
! 4.2. Assignment statements
! ====================================================================


<VarName> ::= <ExtendedID> '(' <ArrayRankList> ')'
<left part>
| <ExtendedID>
::= <variable> ':='


<OtherVarsOpt> ::= ',' <VarName> <OtherVarsOpt>
|


<ArrayRankList> ::= <IntLiteral> ',' <ArrayRankList>
<left part list>
::= <left part>
| <IntLiteral>
| <left part list> <left part>
|


<ConstDecl> ::= <AccessModifierOpt> 'Const' <ConstList> <NL>
<assignment statement>
::= <left part list> <Boolean expression>


<ConstList> ::= <ExtendedID> '=' <ConstExprDef> ',' <ConstList>
| <ExtendedID> '=' <ConstExprDef>


<ConstExprDef> ::= '(' <ConstExprDef> ')'
| '-' <ConstExprDef>
! ====================================================================
| '+' <ConstExprDef>
! 4.3. Go to statements
| <ConstExpr>
! ====================================================================


<SubDecl> ::= <MethodAccessOpt> 'Sub' <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Sub' <NL>
<go to statement> ::= goto <designational expression>
| <MethodAccessOpt> 'Sub' <ExtendedID> <MethodArgList> <InlineStmt> 'End' 'Sub' <NL>


<FunctionDecl> ::= <MethodAccessOpt> 'Function' <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Function' <NL>
| <MethodAccessOpt> 'Function' <ExtendedID> <MethodArgList> <InlineStmt> 'End' 'Function' <NL>


<MethodAccessOpt> ::= 'Public' 'Default'
! ====================================================================
| <AccessModifierOpt>
! 4.4. Dummy statements
! ====================================================================


<AccessModifierOpt> ::= 'Public'
!<dummy statement> ::= <empty>
| 'Private'
|


<MethodArgList> ::= '(' <ArgList> ')'
| '(' ')'
|


<ArgList> ::= <Arg> ',' <ArgList>
! ====================================================================
| <Arg>
! 4.5. Conditional statements
! ====================================================================


<Arg> ::= <ArgModifierOpt> <ExtendedID> '(' ')'
<if statement> ::= <if clause> <unconditional statement>
| <ArgModifierOpt> <ExtendedID>


<ArgModifierOpt> ::= 'ByVal'
<conditional statement>
| 'ByRef'
::= <if statement>
| <if statement> else <statement>
|
| <if clause> <for statement>
| <label> ':' <conditional statement>


<PropertyDecl> ::= <MethodAccessOpt> 'Property' <PropertyAccessType> <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Property' <NL>


<PropertyAccessType> ::= 'Get'
! ====================================================================
| 'Let'
! 4.6. For statements
| 'Set'
! ====================================================================


!===============================
<for list element>
! Rules : Statements
::= <arithmetic expression>
!===============================
| <arithmetic expression> step <arithmetic expression> until <arithmetic expression>
| <arithmetic expression> while <Boolean expression>


<GlobalStmt> ::= <OptionExplicit>
<for list>
| <ClassDecl>
::= <for list element>
| <for list> ',' <for list element>
| <FieldDecl>
| <ConstDecl>
| <SubDecl>
| <FunctionDecl>
| <BlockStmt>


<MethodStmt> ::= <ConstDecl>
<for clause> ::= for <variable> ':=' <for list> do
| <BlockStmt>


<BlockStmt> ::= <VarDecl>
<for statement>
::= <for clause> <statement>
| <RedimStmt>
| <label> ':' <for statement>
| <IfStmt>
| <WithStmt>
| <SelectStmt>
| <LoopStmt>
| <ForStmt>
| <InlineStmt> <NL>


<InlineStmt> ::= <AssignStmt>
| <CallStmt>
| <SubCallStmt>
| <ErrorStmt>
| <ExitStmt>
| 'Erase' <ExtendedID>


<GlobalStmtList> ::= <GlobalStmt> <GlobalStmtList>
! ====================================================================
|
! 4.7. Procedure statements
! ====================================================================


<MethodStmtList> ::= <MethodStmt> <MethodStmtList>
|
<BlockStmtList> ::= <BlockStmt> <BlockStmtList>
|
<OptionExplicit> ::= 'Option' 'Explicit' <NL>


<ErrorStmt> ::= 'On' 'Error' 'Resume' 'Next'
<procedure statement>
| 'On' 'Error' 'GoTo' IntLiteral ! must be 0
::= Identifier '(' <actual parameter list> ')'
| Identifier


<ExitStmt> ::= 'Exit' 'Do'
| 'Exit' 'For'
| 'Exit' 'Function'
| 'Exit' 'Property'
| 'Exit' 'Sub'


<AssignStmt> ::= <LeftExpr> '=' <Expr>
! ====================================================================
| 'Set' <LeftExpr> '=' <Expr>
! 5. Declarations
| 'Set' <LeftExpr> '=' 'New' <LeftExpr>
! ====================================================================


! Hack: VB Script allows to have construct a = b = c, which means a = (b = c)
<declaration>
! In this grammar we do not allow it in order to prevent complications with
::= <type declaration>
! interpretation of a(1) = 2, which may be considered as array element assignment
| <array declaration>
! or a subroutine call: a ((1) = 2).
| <switch declaration>
! Note: VBScript allows to have missed parameters: a ,,2,3,
| <procedure declaration>
! VM: If somebody knows a better way to do it, please let me know
<SubCallStmt> ::= <QualifiedID> <SubSafeExprOpt> <CommaExprList>
| <QualifiedID> <SubSafeExprOpt>
| <QualifiedID> '(' <Expr> ')' <CommaExprList>
| <QualifiedID> '(' <Expr> ')'
| <QualifiedID> '(' ')'
| <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail> <SubSafeExprOpt> <CommaExprList>
| <QualifiedID> <IndexOrParamsListDot> <LeftExprTail> <SubSafeExprOpt> <CommaExprList>
| <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail> <SubSafeExprOpt>
| <QualifiedID> <IndexOrParamsListDot> <LeftExprTail> <SubSafeExprOpt>


! This very simplified case - the problem is that we cannot use parenthesis in aaa(bbb).ccc (ddd)
<SubSafeExprOpt> ::= <SubSafeExpr>
|


<CallStmt> ::= 'Call' <LeftExpr>
! ====================================================================
! 5.1. Type declarations
! ====================================================================


<LeftExpr> ::= <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail>
<type list>
| <QualifiedID> <IndexOrParamsListDot> <LeftExprTail>
::= Identifier
| Identifier ',' <type list>
| <QualifiedID> <IndexOrParamsList>
| <QualifiedID>
| <SafeKeywordID>


<LeftExprTail> ::= <QualifiedIDTail> <IndexOrParamsList> '.' <LeftExprTail>
<type>
| <QualifiedIDTail> <IndexOrParamsListDot> <LeftExprTail>
::= real
| <QualifiedIDTail> <IndexOrParamsList>
| integer
| Boolean
| <QualifiedIDTail>


! VB Script does not allow to have space between Identifier and dot:
<local or own type>
::= <type>
! a . b - Error ; a. b or a.b - OK
| own <type>
<QualifiedID> ::= IDDot <QualifiedIDTail>
| DotIDDot <QualifiedIDTail>
| ID
| DotID


<QualifiedIDTail> ::= IDDot <QualifiedIDTail>
<type declaration>
::= <local or own type> <type list>
| ID
| <KeywordID>


<KeywordID> ::= <SafeKeywordID>
| 'And'
| 'ByRef'
| 'ByVal'
| 'Call'
| 'Case'
| 'Class'
| 'Const'
| 'Dim'
| 'Do'
| 'Each'
| 'Else'
| 'ElseIf'
| 'Empty'
| 'End'
| 'Eqv'
| 'Exit'
| 'False'
| 'For'
| 'Function'
| 'Get'
| 'GoTo'
| 'If'
| 'Imp'
| 'In'
| 'Is'
| 'Let'
| 'Loop'
| 'Mod'
| 'New'
| 'Next'
| 'Not'
| 'Nothing'
| 'Null'
| 'On'
| 'Option'
| 'Or'
| 'Preserve'
| 'Private'
| 'Public'
| 'Redim'
| 'Resume'
| 'Select'
| 'Set'
| 'Sub'
| 'Then'
| 'To'
| 'True'
| 'Until'
| 'WEnd'
| 'While'
| 'With'
| 'Xor'


<SafeKeywordID> ::= 'Default'
! ====================================================================
| 'Erase'
! 5.2. Array declarations
| 'Error'
! ====================================================================
| 'Explicit'
| 'Property'
<lower bound> ::= <arithmetic expression>
| 'Step'
<upper bound> ::= <arithmetic expression>
<bound pair> ::= <lower bound> ':' <upper bound>
<bound pair list>
::= <bound pair>
| <bound pair list> ',' <bound pair>
<array segment>
::= Identifier '[' <bound pair list> ']'
| Identifier ',' <array segment>
<array list>
::= <array segment>
| <array list> ',' <array segment>
<array declaration>
::= array <array list>
| <local or own type> array <array list>


<ExtendedID> ::= <SafeKeywordID>
! ====================================================================
| ID
! 5.3. Switch declarations
! ====================================================================


<IndexOrParamsList> ::= <IndexOrParams> <IndexOrParamsList>
<switch list>
| <IndexOrParams>
::= <designational expression>
| <switch list> ',' <designational expression>


<IndexOrParams> ::= '(' <Expr> <CommaExprList> ')'
<switch declaration>
::= switch Identifier ':=' <switch list>
| '(' <CommaExprList> ')'
| '(' <Expr> ')'
| '(' ')'


<IndexOrParamsListDot> ::= <IndexOrParams> <IndexOrParamsListDot>
| <IndexOrParamsDot>


<IndexOrParamsDot> ::= '(' <Expr> <CommaExprList> ').'
! ====================================================================
| '(' <CommaExprList> ').'
! 5.4. Procedure declarations
| '(' <Expr> ').'
! ====================================================================
| '(' ').'


<CommaExprList> ::= ',' <Expr> <CommaExprList>
<formal parameter>
| ',' <CommaExprList>
::= Identifier
| ',' <Expr>
| ','


!========= Redim Statement
<formal parameter list>
::= <formal parameter>
| <formal parameter list> <parameter delimiter> <formal parameter>


<RedimStmt> ::= 'Redim' <RedimDeclList> <NL>
<formal parameter part>
| 'Redim' 'Preserve' <RedimDeclList> <NL>
::= !EMPTY
| '(' <formal parameter list> ')'


<RedimDeclList> ::= <RedimDecl> ',' <RedimDeclList>
<identifier list>
::= Identifier
| <RedimDecl>
| <identifier list> ',' Identifier


<RedimDecl> ::= <ExtendedID> '(' <ExprList> ')'
<value part>
::= value <identifier list> ';'
| !EMPTY


!========= If Statement
<specifier>
::= string
| <type>
| array
| <type> array
| label
| switch
| procedure
| <type> procedure


<IfStmt> ::= 'If' <Expr> 'Then' <NL> <BlockStmtList> <ElseStmtList> 'End' 'If' <NL>
<specification part>
| 'If' <Expr> 'Then' <InlineStmt> <ElseOpt> <EndIfOpt> <NL>
::= !EMPTY
| <specification>
!=== The following rule was added


<ElseStmtList> ::= 'ElseIf' <Expr> 'Then' <NL> <BlockStmtList> <ElseStmtList>
<specification>
::= <specifier> <identifier list> ';'
| 'ElseIf' <Expr> 'Then' <InlineStmt> <NL> <ElseStmtList>
| 'Else' <InlineStmt> <NL>
| <specification> <specifier> <identifier list> ';'
| 'Else' <NL> <BlockStmtList>
|


<ElseOpt> ::= 'Else' <InlineStmt>
|


<EndIfOpt> ::= 'End' 'If'
|


!========= With Statement
<procedure heading>
::= Identifier <formal parameter part> ';' <value part> <specification part>


<WithStmt> ::= 'With' <Expr> <NL> <BlockStmtList> 'End' 'With' <NL>
<procedure body>
::= <statement>
!!! | <code> !<code> refers to any embedded non-Algol code


!========= Loop Statement
<procedure declaration>
::= procedure <procedure heading> <procedure body>
| <type> procedure <procedure heading> <procedure body>


<LoopStmt> ::= 'Do' <LoopType> <Expr> <NL> <BlockStmtList> 'Loop' <NL>
</pre>
| 'Do' <NL> <BlockStmtList> 'Loop' <LoopType> <Expr> <NL>
=={{header|ALGOL 68}}==
| 'Do' <NL> <BlockStmtList> 'Loop' <NL>
=={{header|APL}}==
| 'While' <Expr> <NL> <BlockStmtList> 'WEnd' <NL>
=={{header|AWK}}==

=={{header|ActionScript}}==
<LoopType> ::= 'While'
=={{header|Ada}}==
| 'Until'
=={{header|Agda2}}==

=={{header|AmigaE}}==
!========= For Statement
=={{header|AppleScript}}==

=={{header|Assembly}}==
<ForStmt> ::= 'For' <ExtendedID> '=' <Expr> 'To' <Expr> <StepOpt> <NL> <BlockStmtList> 'Next' <NL>
=={{header|AutoHotkey}}==
| 'For' 'Each' <ExtendedID> 'In' <Expr> <NL> <BlockStmtList> 'Next' <NL>
=={{header|BASIC}}==

<pre>
<StepOpt> ::= 'Step' <Expr>
|

!========= Select Statement

<SelectStmt> ::= 'Select' 'Case' <Expr> <NL> <CaseStmtList> 'End' 'Select' <NL>

<CaseStmtList> ::= 'Case' <ExprList> <NLOpt> <BlockStmtList> <CaseStmtList>
| 'Case' 'Else' <NLOpt> <BlockStmtList>
|

<NLOpt> ::= <NL>
|

<ExprList> ::= <Expr> ',' <ExprList>
| <Expr>

!===============================
! Rules : Expressions
!===============================

<SubSafeExpr> ::= <SubSafeImpExpr>

<SubSafeImpExpr> ::= <SubSafeImpExpr> 'Imp' <EqvExpr>
| <SubSafeEqvExpr>

<SubSafeEqvExpr> ::= <SubSafeEqvExpr> 'Eqv' <XorExpr>
| <SubSafeXorExpr>

<SubSafeXorExpr> ::= <SubSafeXorExpr> 'Xor' <OrExpr>
| <SubSafeOrExpr>

<SubSafeOrExpr> ::= <SubSafeOrExpr> 'Or' <AndExpr>
| <SubSafeAndExpr>

<SubSafeAndExpr> ::= <SubSafeAndExpr> 'And' <NotExpr>
| <SubSafeNotExpr>

<SubSafeNotExpr> ::= 'Not' <NotExpr>
| <SubSafeCompareExpr>

<SubSafeCompareExpr> ::= <SubSafeCompareExpr> 'Is' <ConcatExpr>
| <SubSafeCompareExpr> 'Is' 'Not' <ConcatExpr>
| <SubSafeCompareExpr> '>=' <ConcatExpr>
| <SubSafeCompareExpr> '=>' <ConcatExpr>
| <SubSafeCompareExpr> '<=' <ConcatExpr>
| <SubSafeCompareExpr> '=<' <ConcatExpr>
| <SubSafeCompareExpr> '>' <ConcatExpr>
| <SubSafeCompareExpr> '<' <ConcatExpr>
| <SubSafeCompareExpr> '<>' <ConcatExpr>
| <SubSafeCompareExpr> '=' <ConcatExpr>
| <SubSafeConcatExpr>

<SubSafeConcatExpr> ::= <SubSafeConcatExpr> '&' <AddExpr>
| <SubSafeAddExpr>

<SubSafeAddExpr> ::= <SubSafeAddExpr> '+' <ModExpr>
| <SubSafeAddExpr> '-' <ModExpr>
| <SubSafeModExpr>

<SubSafeModExpr> ::= <SubSafeModExpr> 'Mod' <IntDivExpr>
| <SubSafeIntDivExpr>

<SubSafeIntDivExpr> ::= <SubSafeIntDivExpr> '\' <MultExpr>
| <SubSafeMultExpr>

<SubSafeMultExpr> ::= <SubSafeMultExpr> '*' <UnaryExpr>
| <SubSafeMultExpr> '/' <UnaryExpr>
| <SubSafeUnaryExpr>

<SubSafeUnaryExpr> ::= '-' <UnaryExpr>
| '+' <UnaryExpr>
| <SubSafeExpExpr>

<SubSafeExpExpr> ::= <SubSafeValue> '^' <ExpExpr>
| <SubSafeValue>

<SubSafeValue> ::= <ConstExpr>
| <LeftExpr>
! | '(' <Expr> ')'

<Expr> ::= <ImpExpr>

<ImpExpr> ::= <ImpExpr> 'Imp' <EqvExpr>
| <EqvExpr>

<EqvExpr> ::= <EqvExpr> 'Eqv' <XorExpr>
| <XorExpr>

<XorExpr> ::= <XorExpr> 'Xor' <OrExpr>
| <OrExpr>

<OrExpr> ::= <OrExpr> 'Or' <AndExpr>
| <AndExpr>

<AndExpr> ::= <AndExpr> 'And' <NotExpr>
| <NotExpr>

<NotExpr> ::= 'Not' <NotExpr>
| <CompareExpr>

<CompareExpr> ::= <CompareExpr> 'Is' <ConcatExpr>
| <CompareExpr> 'Is' 'Not' <ConcatExpr>
| <CompareExpr> '>=' <ConcatExpr>
| <CompareExpr> '=>' <ConcatExpr>
| <CompareExpr> '<=' <ConcatExpr>
| <CompareExpr> '=<' <ConcatExpr>
| <CompareExpr> '>' <ConcatExpr>
| <CompareExpr> '<' <ConcatExpr>
| <CompareExpr> '<>' <ConcatExpr>
| <CompareExpr> '=' <ConcatExpr>
| <ConcatExpr>

<ConcatExpr> ::= <ConcatExpr> '&' <AddExpr>
| <AddExpr>

<AddExpr> ::= <AddExpr> '+' <ModExpr>
| <AddExpr> '-' <ModExpr>
| <ModExpr>

<ModExpr> ::= <ModExpr> 'Mod' <IntDivExpr>
| <IntDivExpr>

<IntDivExpr> ::= <IntDivExpr> '\' <MultExpr>
| <MultExpr>

<MultExpr> ::= <MultExpr> '*' <UnaryExpr>
| <MultExpr> '/' <UnaryExpr>
| <UnaryExpr>

<UnaryExpr> ::= '-' <UnaryExpr>
| '+' <UnaryExpr>
| <ExpExpr>

<ExpExpr> ::= <Value> '^' <ExpExpr>
| <Value>

<Value> ::= <ConstExpr>
| <LeftExpr>
| '(' <Expr> ')'

<ConstExpr> ::= <BoolLiteral>
| <IntLiteral>
| FloatLiteral
| StringLiteral
| DateLiteral
| <Nothing>

<BoolLiteral> ::= 'True'
| 'False'

<IntLiteral> ::= IntLiteral
| HexLiteral
| OctLiteral

<Nothing> ::= 'Nothing'
| 'Null'
| 'Empty'
</pre></div>

==[[:Category:Visual Basic .NET|Visual Basic .NET]]==
The following link (Appedix B) has a simple BNF Syntax [http://laser.physics.sunysb.edu/~amol/papers/mollypaper.pdf VB Syntax]
<div style="height:30ex;overflow:scroll"><pre>
! -----------------------------------------------------------------------
! -----------------------------------------------------------------------
! BASIC '64
! Visual Basic .NET
!
! Visual Basic .NET is the latest version in the long evoluation of the
! BASIC programming language. The Visual Basic .NET programming language
! is far more "clean" and orthagonal than its predecessors. Although some
! of the old constructs exist, the language is far easier to read and write.
!
! Major syntax changes include, but are not limited to:
!
! 1. The primative file access of VB6 was replaced by a class library. As
! a result, special statements such as
!
! Open "test" For Input As #1
!
! no longer exist.
!
! 2. Class module files were replaced by 'Class ... End Class' declarations
!
! 3. Module files were replaced by 'Module ... End Module' declarations
!
!
! 4. Structured error handling was added with C++ style Try ... Catch
! Beginner's All-purpose Symbolic Instruction Code
! statements. The old nonstructured approach is still, unfortunately,
! available.
!
! Unfortnately, the designers of Visual Basic .NET did not remove the
! datatype postfix characters on identifiers. In the original BASIC,
! variables types were determined by $ for strings and % for integers.
! QuickBasic expanded the postix notation to include other symbols
! for long integers, singles, etc...
!
!
! Part of the ID terminal definition was commented out to prevent the
! "It is practically impossible to teach good programming style to students
! old format. You can allow the postfix characters if you like.
! that have had prior exposure to BASIC; as potential programmers they are
! mentally mutilated beyond hope of regeneration."
!
!
! This grammar also does not contain the compiler directives.
! - Edsger W. Dijkstra
!
!
! BASIC is one of the oldest programming language and one of the most popular.
! Note: This is an ad hoc version of the language. If there are any flaws,
! please visit www.DevinCook.com/GOLDParser
! It was developed in 1964 by John G. Kemeny and Thomas E. Kurtz to teach
! students the basics of programming concepts. At the advent of the microcomputer,
! BASIC was implemented on numerous platforms such as the Commodore, Atari,
! Apple II, Altair, IBM PC computers. Over time, BASIC evolved into GW-BASIC,
! QBasic, Visual Basic, and recently Visual Basic .NET.
!
!
! Updates:
! In practically all programming languages, the reserved word/symbol that denotes
! 04/082005
! a comment is treated as a form of whitespace - having no effect in the manner in
! Devin Cook
! which the program runs. Once such type of comment is used to indicate the remainder
! of the line is to be ignored. These can be added to the end of any line without
! 1. Removed minus sign from the IntLiteral and RealLiteral
! definitions. These can cause some parse errors when expressions
! changing the meaning of the program. In C++, it is the '//' symbol;
! like "2-2" are read. In this case it would have been interpreted
! in BASIC '64 it is 'REM'.
! as "2" and "-2" rather than "2", "-" and "2".
! 2. Members of an enumeration can be defined with any expression.
! 3. Made some very minor comment changes - mainly for readability.
!
!
! 03/27/2005
! However, in the BASIC programming language, the line comment is treated like a
! Adrian Moore [adrianrob@hotmail.com]
! statement. For instance, if 'REM' was a normal line comment:
! 1. Add support for Implements in Class
! 2. Add support for AddressOf keyword
! 3. No longer fails if variable starts with _
!
!
! 02/24/2004
! 10 PRINT "Hello World" REM Common first program
! Vladimir Morozov [vmoroz@hotmail.com] fixed a few flaws in the
! grammar. 1. The definition for strings did not allow the double
! double-quote override. 2. A real literal does not need to have a
! fraction if followed by an exponent. 3. Escaped identifiers can
! contain a null string and 4. Rem works the same as the '
!
!
! would be a valid statement. However, in BASIC, this is illegal. In the example
! above, the comment must be added as an additional statement.
!
! 10 PRINT "Hello World" : REM Common first program
!
! As a result, the Line Comment terminal that is used in the GOLD Parser cannot be
! used here. In the grammar below, a 'Remark' terminal was created that accepts all
! series of printable characters starting with the characters "REM ". In some
! implementations of BASIC, any string starting with "REM" is a comment statement.
! Examples include "REMARK", "REMARKABLE" and "REMODEL". This grammar requires the space.
!
! This grammar does not include the editor statements such as NEW, SAVE, LOAD, etc...
!
!
! USE GOLD PARSER BUILDER VERSION 2.1 AND LATER TO COMPILE THIS GRAMMAR.
! Note: This is an ad hoc version of the language. If there are any flaws, please
! Earlier versions cannot handle the complexity.
! e-mail GOLDParser@DevinCook.com and I will update the grammar. Most likely I have
! included features not available in BASIC '64.
! -----------------------------------------------------------------------
! -----------------------------------------------------------------------


"Name" = 'Visual Basic .NET'

"Author" = 'John G. Kemeny and Thomas E. Kurtz'
"Name" = 'BASIC (Beginners All-purpose Symbolic Instruction Code)'
"Version" = '.NET'
"Author" = 'John G. Kemeny and Thomas E. Kurtz'
"Version" = '1964 - Original - before Microsoft enhanced the language for the IBM PC.'
"About" = 'Visual Basic .NET is the latest version in the long evoluation of the'
| 'BASIC programming language.'
"About" = 'BASIC is one of most common and popular teaching languages ever created. '


"Case Sensitive" = False
"Case Sensitive" = False
"Start Symbol" = <Lines>
"Start Symbol" = <Program>


! ----------------------------------------------------------------- Sets
{String Chars} = {Printable} - ["]
{WS} = {Whitespace} - {CR} - {LF}


{String Chars} = {Printable} - ["]
NewLine = {CR}{LF}|{CR}
Whitespace = {WS}+
{Date Chars} = {Printable} - [#]
{ID Name Chars} = {Printable} - ['['']']
{Hex Digit} = {Digit} + [abcdef]
{Oct Digit} = [01234567]


Remark = REM{Space}{Printable}*
{WS} = {Whitespace} - {CR} - {LF}
ID = {Letter}[$%]?
{Id Tail} = {Alphanumeric} + [_]
String = '"'{String Chars}*'"'
Integer = {digit}+
Real = {digit}+.{digit}+


! ----------------------------------------------------------------- Terminals
<Lines> ::= Integer <Statements> NewLine <Lines>
| Integer <Statements> NewLine


NewLine = {CR}{LF} | {CR} | ':'
<Statements> ::= <Statement> ':' <Statements>
| <Statement>
Whitespace = {WS}+ | '_' {WS}* {CR} {LF}?


Comment Line = '' | Rem !Fixed by Vladimir Morozov
<Statement> ::= CLOSE '#' Integer
| DATA <Constant List>
| DIM ID '(' <Integer List> ')'
| END
| FOR ID '=' <Expression> TO <Expression>
| FOR ID '=' <Expression> TO <Expression> STEP Integer
| GOTO <Expression>
| GOSUB <Expression>
| IF <Expression> THEN <Statement>
| INPUT <ID List>
| INPUT '#' Integer ',' <ID List>
| LET Id '=' <Expression>
| NEXT <ID List>
| OPEN <Value> FOR <Access> AS '#' Integer
| POKE <Value List>
| PRINT <Print list>
| PRINT '#' Integer ',' <Print List>
| READ <ID List>
| RETURN
| RESTORE
| RUN
| STOP
| SYS <Value>
| WAIT <Value List>
| Remark


LABEL = {Letter}{ID Tail}*':'
<Access> ::= INPUT

| OUPUT
!Fixed by Vladimir Morozov

ID = [_]?{Letter}{ID Tail}* ! [%&@!#$]? !Archaic postfix chars
| '[' {ID Name Chars}* ']'
QualifiedID = ({Letter}{ID Tail}* | '['{ID Name Chars}*']') ( '.'({Letter}{ID Tail}* | '['{ID Name Chars}*']') )+

MemberID = '.' {Letter}{ID Tail}*
| '.[' {ID Name Chars}* ']'
!Fixed by Vladimir Morozov
StringLiteral = '"' ( {String Chars} | '""' )* '"'


CharLiteral = '"' {String Chars}* '"C'
IntLiteral = {digit}+ [FRDSIL]?

RealLiteral = {digit}* '.' {digit}+ ( 'E' [+-]? {Digit}+ )? [FR]?
| {digit}+ 'E' [+-]? {Digit}+ [FR]?


DateLiteral = '#'{Date chars}'#'

HexLiteral = '&H'{Hex Digit}+ [SIL]?
OctLiteral = '&O'{Oct Digit}+ [SIL]?

! ----------------------------------------------------------------- Rules

<Program> ::= <NameSpace Item> <Program>
| <Imports> <Program>
| <Option Decl> <Program>
|

! -------------------------------------------------------------------
! (Shared attributes)
! -------------------------------------------------------------------

<NL> ::= NewLine <NL>
| NewLine

<Modifiers> ::= <Modifier> <Modifiers>
|

<Modifier> ::= Shadows
| Shared
| MustInherit
| NotInheritable

| Overridable
| NotOverridable
| MustOverride
| Overrides
| Overloads
| Default
| ReadOnly
| WriteOnly
| <Access>

<Access Opt> ::= <Access>
|

<Access> ::= Public
| Private
| Friend
| Protected

<Var Member> ::= <Attributes> <Access> <Var Decl> <NL> !Variables
| <Attributes> <Access Opt> Const <Var Decl> <NL> !Constants
| <Attributes> <Access Opt> Static <Var Decl> <NL>
<Implements> ::= Implements <ID List>

<ID List> ::= <Identifier> ',' <ID List>
| <Identifier>
<Option Decl> ::= Option <IDs> <NL>

<IDs> ::= ID <IDs>
| ID
<Type> ::= As <Attributes> <Identifier>
|

<Compare Op> ::= '=' | '<>' | '<' | '>' | '>=' | '<='

! -------------------------------------------------------------------
! NameSpace
! -------------------------------------------------------------------

<NameSpace> ::= NameSpace ID <NL> <NameSpace Items> End NameSpace <NL>

<NameSpace Items> ::= <NameSpace Item> <NameSpace Items>
|

<NameSpace Item> ::= <Class>
| <Declare>
| <Delegate>
| <Enumeration>
| <Interface>
| <Structure>
| <Module>
| <Namespace>

! -------------------------------------------------------------------
! Attributes
! -------------------------------------------------------------------

<Attributes> ::= '<' <Attribute List> '>'
|

<Attribute List> ::= <Attribute> ',' <Attribute List>
| <Attribute>
<ID List> ::= ID ',' <ID List>
<Attribute> ::= <Attribute Mod> ID <Argument List Opt>
| ID
<Attribute Mod> ::= Assembly
| Module
|
! -------------------------------------------------------------------
! Delegates
! -------------------------------------------------------------------
<Delegate> ::= <Attributes> <Modifiers> Delegate <Method>
| <Attributes> <Modifiers> Delegate <Declare>


! -------------------------------------------------------------------
<Value List> ::= <Value> ',' <Value List>
! Imports
| <Value>
! -------------------------------------------------------------------


<Constant List> ::= <Constant> ',' <Constant List>
<Imports> ::= Imports <Identifier> <NL>
| <Constant>
| Imports ID '=' <Identifier> <NL>


! -------------------------------------------------------------------
<Integer List> ::= Integer ',' <Integer List>
! Events
| Integer
! -------------------------------------------------------------------

<Event Member> ::= <Attributes> <Modifiers> Event ID <Parameters Or Type> <Implements Opt> <NL>

<Parameters Or Type> ::= <Param List>
| As <Identifier>

<Implements Opt> ::= <Implements>
|
! -------------------------------------------------------------------
! Class
! -------------------------------------------------------------------

<Class> ::= <Attributes> <Modifiers> Class ID <NL> <Class Items> End Class <NL>


<Class Items> ::= <Class Item> <Class Items>
|

<Class Item> ::= <Declare>
| <Method>
| <Property>
| <Var Member>
| <Enumeration>
| <Inherits>
| <Class Implements>
<Inherits> ::= Inherits <Identifier> <NL>
<Class Implements> ::= Implements <ID List> <NL>

! -------------------------------------------------------------------
! Structures
! -------------------------------------------------------------------

<Structure> ::= <Attributes> <Modifiers> Structure ID <NL> <Structure List> End Structure <NL>

<Structure List> ::= <Structure Item> <Structure List>
|

<Structure Item> ::= <Implements>
| <Enumeration>
| <Structure>
| <Class>
| <Delegate>
| <Var Member>
| <Event Member>
| <Declare>
| <Method>
| <Property>

! -------------------------------------------------------------------
! Module
! -------------------------------------------------------------------

<Module> ::= <Attributes> <Modifiers> Module ID <NL> <Module Items> End Module <NL>

<Module Items> ::= <Module Item> <Module Items>
|
<Module Item> ::= <Declare>
<Expression List> ::= <Expression> ',' <Expression List>
| <Expression>
| <Method>
| <Property>
| <Var Member>
| <Enumeration>
| <Option Decl>


! -------------------------------------------------------------------
<Print List> ::= <Expression> ';' <Print List>
! Interface
| <Expression>
! -------------------------------------------------------------------
|


<Interface> ::= <Attributes> <Modifiers> Interface ID <NL> <Interface Items> End Interface <NL>
<Expression> ::= <And Exp> OR <Expression>


<Interface Items> ::= <Interface Item> <Interface Items>
|
<Interface Item> ::= <Implements>
| <Event Member>
| <Enum Member>
| <Method Member>
| <Property Member>

<Enum Member> ::= <Attributes> <Modifiers> Enum ID <NL>

<Method Member> ::= <Attributes> <Modifiers> Sub <Sub ID> <Param List> <Handles Or Implements> <NL>
| <Attributes> <Modifiers> Function ID <Param List> <Type> <Handles Or Implements> <NL>

<Property Member> ::= <Attributes> <Modifiers> Property ID <Param List> <Type> <Handles Or Implements> <NL>
! -------------------------------------------------------------------
! Parameters
! -------------------------------------------------------------------

<Param List Opt> ::= <Param List>
|

<Param List> ::= '(' <Param Items> ')'
| '(' ')'
<Param Items> ::= <Param Item> ',' <Param Items>
| <Param Item>

<Param Item> ::= <Param Passing> ID <Type>


<Param Passing> ::= ByVal
| ByRef
| Optional
| ParamArray
|

! -------------------------------------------------------------------
! Arguments
! -------------------------------------------------------------------

<Argument List Opt> ::= <Argument List>
|
<Argument List> ::= '(' <Argument Items> ')'
<Argument Items> ::= <Argument> ',' <Argument Items>
| <Argument>

<Argument> ::= <Expression>
| Id ':=' <Expression>
| !NULL
! -------------------------------------------------------------------
! Declares (External Procedures)
! -------------------------------------------------------------------

<Declare> ::= <Attributes> <Modifiers> Declare <Charset> Sub ID Lib StringLiteral <Alias> <Param List Opt> <NL>
| <Attributes> <Modifiers> Declare <Charset> Function ID Lib StringLiteral <Alias> <Param List Opt> <Type> <NL>

<Charset> ::= Ansi | Unicode | Auto | !Null

<Alias> ::= Alias StringLiteral
|


! -------------------------------------------------------------------
! Methods
! -------------------------------------------------------------------

<Method> ::= <Attributes> <Modifiers> Sub <Sub ID> <Param List> <Handles Or Implements> <NL> <Statements> End Sub <NL>
| <Attributes> <Modifiers> Function ID <Param List> <Type> <Handles Or Implements> <NL> <Statements> End Function <NL>
<Sub ID> ::= ID
| New !Class creation

<Handles Or Implements> ::= <Implements>
| <Handles>
|

<Handles> ::= Handles <ID List>

! -------------------------------------------------------------------
! Properties
! -------------------------------------------------------------------
<Property> ::= <Attributes> <Modifiers> Property ID <Param List> <Type> <NL> <Property Items> End Property <NL>

<Property Items> ::= <Property Item> <Property Items>
|

<Property Item> ::= Get <NL> <Statements> End Get <NL>
| Set <Param List> <NL> <Statements> End Set <NL>


! -------------------------------------------------------------------
! Enumerations
! -------------------------------------------------------------------

<Enumeration> ::= <Attributes> <Modifiers> Enum ID <NL> <Enum List> End Enum <NL>

<Enum List> ::= <Enum Item> <Enum List>
|

<Enum Item> ::= Id '=' <Expression> <NL>
| Id <NL>

! -------------------------------------------------------------------
! Variable Declaration
! -------------------------------------------------------------------

<Var Decl> ::= <Var Decl Item> ',' <Var Decl>
| <Var Decl Item>
<Var Decl Item> ::= <Var Decl ID> As <Identifier> <Argument List Opt>
| <Var Decl ID> As <Identifier> '=' <Expression> !Initialize
| <Var Decl ID> As New <Identifier> <Argument List Opt>
| <Var Decl ID>
| <Var Decl ID> '=' <Expression> !Initialize

<Var Decl ID> ::= ID <Argument List Opt>
! -------------------------------------------------------------------
! Normal Statements
! -------------------------------------------------------------------

<Statements> ::= <Statement> <Statements>
|

<Statement> ::= <Loop Stm>
| <For Stm>
| <If Stm>
| <Select Stm>
| <SyncLock Stm>
| <Try Stm>
| <With Stm>
| <Option Decl>
| <Local Decl>
| <Non-Block Stm> <NL> !Note the <NL>. A non-block statement can be a full statement
| LABEL <NL>
<Non-Block Stm> ::= Call <Variable>
| ReDim <Var Decl>
| ReDim Preserve <Var Decl>
| Erase ID
| Throw <Value>
| RaiseEvent <Identifier> <Argument List Opt>
| AddHandler <Expression> ',' <Expression>
| RemoveHandler <Expression> ',' <Expression>
| Exit Do
| Exit For
| Exit Function
| Exit Property
| Exit Select
| Exit Sub
| Exit Try
| Exit While
| GoTo ID !Argh - they still have this
| Return <Value>

| Error <Value> !Raise an error by number
| On Error GoTo IntLiteral ! 0 This is obsolete.
| On Error GoTo '-' IntLiteral !-1 This is obsolete.
| On Error GoTo Id
| On Error Resume Next
| Resume ID
| Resume Next
| <Variable> <Assign Op> <Expression>
| <Variable>
| <Method Call>

<Assign Op> ::= '=' | '^=' | '*=' | '/=' | '\=' | '+=' | '-=' | '&=' | '<<=' | '>>='


! -------------------------------------------------------------------
! Local declarations
! -------------------------------------------------------------------

<Local Decl> ::= Dim <Var Decl> <NL>
| Const <Var Decl> <NL>
| Static <Var Decl> <NL>

! -------------------------------------------------------------------
! Do Statement
! -------------------------------------------------------------------

<Loop Stm> ::= Do <Test Type> <Expression> <NL> <Statements> Loop <NL>
| Do <NL> <Statements> Loop <Test Type> <Expression> <NL>
| While <Expression> <NL> <Statements> End While <NL>

<Test Type> ::= While
| Until

! -------------------------------------------------------------------
! For Statement
! -------------------------------------------------------------------

<For Stm> ::= For <Identifier> '=' <Expression> To <Expression> <Step Opt> <NL> <Statements> Next <NL>
| For Each <Variable> In <Variable> <NL> <Statements> Next <NL>

<Step Opt> ::= Step <Expression>
|


! -------------------------------------------------------------------
! If Statement
! -------------------------------------------------------------------

<If Stm> ::= If <Expression> <Then Opt> <NL> <Statements> <If Blocks> End If <NL>
| If <Expression> Then <Non-Block Stm> <NL>
| If <Expression> Then <Non-Block Stm> Else <Non-Block Stm> <NL>

<Then Opt> ::= Then !!The reserved word 'Then' is optional for Block-If statements
|

<If Blocks> ::= ElseIf <Expression> <Then Opt> <NL> <Statements> <If Blocks>
| Else <NL> <Statements>
|

! -------------------------------------------------------------------
! Select Statement
! -------------------------------------------------------------------

<Select Stm> ::= Select <Case Opt> <Expression> <NL> <Select Blocks> End Select <NL>

<Case Opt> ::= Case !!The "Case" after Select is optional in VB.NEt
|


<Select Blocks> ::= Case <Case Clauses> <NL> <Statements> <Select Blocks>
| Case Else <NL> <Statements>
|

<Case Clauses> ::= <Case Clause> ',' <Case Clauses>
| <Case Clause>

<Case Clause> ::= <Is Opt> <Compare Op> <Expression>
| <Expression>
| <Expression> To <Expression>

<Is Opt> ::= Is
| !Null

! -------------------------------------------------------------------
! SyncLock Statement
! -------------------------------------------------------------------

<SyncLock Stm> ::= SyncLock <NL> <Statements> End SyncLock <NL>

! -------------------------------------------------------------------
! Try Statement
! -------------------------------------------------------------------

<Try Stm> ::= Try <NL> <Statements> <Catch Blocks> End Try <NL>

<Catch Blocks> ::= <Catch Block> <Catch Blocks>
| <Catch Block>

<Catch Block> ::= Catch <Identifier> As ID <NL> <Statements>
| Catch <NL> <Statements>

! -------------------------------------------------------------------
! With Statement
! -------------------------------------------------------------------

<With Stm> ::= With <Value> <NL> <Statements> End With <NL>
! -------------------------------------------------------------------
! Expressions
! -------------------------------------------------------------------

<Expression> ::= <And Exp> Or <Expression>
| <And Exp> OrElse <Expression>
| <And Exp> XOr <Expression>
| <And Exp>
| <And Exp>


<And Exp> ::= <Not Exp> AND <And Exp>
<And Exp> ::= <Not Exp> And <And Exp>
| <Not Exp> AndAlso <And Exp>
| <Not Exp>
| <Not Exp>
<Not Exp> ::= NOT <Compare Exp>
<Not Exp> ::= NOT <Compare Exp>
| <Compare Exp>
| <Compare Exp>


<Compare Exp> ::= <Add Exp> '=' <Compare Exp>
<Compare Exp> ::= <Shift Exp> <Compare Op> <Compare Exp> !e.g. x < y
| <Add Exp> '<>' <Compare Exp>
| TypeOf <Add Exp> Is <Object>
| <Add Exp> '><' <Compare Exp>
| <Shift Exp> Is <Object>
| <Add Exp> '>' <Compare Exp>
| <Shift Exp> Like <Value>
| <Add Exp> '>=' <Compare Exp>
| <Shift Exp>
| <Add Exp> '<' <Compare Exp>
| <Add Exp> '<=' <Compare Exp>
| <Add Exp>


<Add Exp> ::= <Mult Exp> '+' <Add Exp>
<Shift Exp> ::= <Concat Exp> '<<' <Shift Exp>
| <Mult Exp> '-' <Add Exp>
| <Concat Exp> '>>' <Shift Exp>
| <Mult Exp>
| <Concat Exp>

<Concat Exp> ::= <Add Exp> '&' <Concat Exp>
| <Add Exp>

<Add Exp> ::= <Modulus Exp> '+' <Add Exp>
| <Modulus Exp> '-' <Add Exp>
| <Modulus Exp>

<Modulus Exp> ::= <Int Div Exp> Mod <Modulus Exp>
| <Int Div Exp>

<Int Div Exp> ::= <Mult Exp> '\' <Int Div Exp>
| <Mult Exp>


<Mult Exp> ::= <Negate Exp> '*' <Mult Exp>
<Mult Exp> ::= <Negate Exp> '*' <Mult Exp>
Line 680: Line 1,778:
| <Value>
| <Value>


<Value> ::= '(' <Expression> ')'
<Value> ::= '(' <Expression> ')'
| ID
| New <Identifier> <Argument List Opt>
| ID '(' <Expression List> ')'
| IntLiteral
| <Constant>
| HexLiteral
| OctLiteral
| StringLiteral
| CharLiteral
| RealLiteral
| DateLiteral
| True
| False
| Me
| MyClass
| MyBase
| Nothing
| <Variable>
| AddressOf <Identifier>


<Object> ::= <Identifier> !Object identifiers
<Constant> ::= Integer
| String
| Me
| Real
| MyClass
| MyBase
</pre>
| Nothing
=={{header|Bc}}==

=={{header|Befunge}}==
<Variable> ::= <Identifier> <Argument List Opt> <Method Calls>
=={{header|Brainf***}}==
=={{header|C}}==
<Method Calls> ::= <Method Call> <Method Calls>
=={{header|C sharp}}==
|
=={{header|C++}}==

=={{header|Caml}}==
<Method Call> ::= MemberID <Argument List Opt>
=={{header|Clean}}==

=={{header|Clojure}}==

=={{header|Cobol}}==
<Identifier> ::= ID | QualifiedID !Any type of identifier
=={{header|ColdFusion}}==
</pre></div>
=={{header|Common Lisp}}==
=={{header|Component Pascal}}==
=={{header|Coq}}==
=={{header|D}}==
=={{header|DOS Batch File}}==
=={{header|Dc}}==
=={{header|Delphi}}==
=={{header|E}}==
=={{header|EC}}==
=={{header|ELLA}}==
=={{header|ESQL}}==
=={{header|Eiffel}}==
=={{header|Emacs Lisp}}==
=={{header|Erlang}}==
=={{header|F}}==
=={{header|F Sharp}}==
=={{header|FALSE}}==
=={{header|FP}}==
=={{header|Factor}}==
=={{header|Fan}}==
=={{header|Forth}}==
=={{header|Fortran}}==
=={{header|GAP}}==
=={{header|Gnuplot}}==
=={{header|Groovy}}==
=={{header|HaXe}}==
=={{header|Haskell}}==
=={{header|IDL}}==
=={{header|Icon}}==
=={{header|Io}}==
=={{header|J}}==
=={{header|JSON}}==
=={{header|JScript.NET}}==
=={{header|Java}}==
=={{header|JavaScript}}==
=={{header|JoCaml}}==
=={{header|Joy}}==
=={{header|JudoScript}}==
=={{header|Korn Shell}}==
=={{header|LSE64}}==
=={{header|LaTeX}}==
=={{header|LabVIEW}}==
=={{header|Lisaac}}==
=={{header|Lisp}}==
=={{header|Logo}}==
=={{header|Logtalk}}==
=={{header|LotusScript}}==
=={{header|Lua}}==
=={{header|Lucid}}==
=={{header|M4}}==
=={{header|MAXScript}}==
=={{header|MIRC Scripting Language}}==
=={{header|MS SQL}}==
=={{header|Make}}==
=={{header|Maple}}==
=={{header|Mathematica}}==
=={{header|Maxima}}==
=={{header|Metafont}}==
=={{header|Modula-3}}==
=={{header|NewLISP}}==
=={{header|Nial}}==
=={{header|OCaml}}==
=={{header|Oberon-2}}==
=={{header|Object Pascal}}==
=={{header|Objective-C}}==
=={{header|Octave}}==
=={{header|Omega}}==
=={{header|OpenEdge/Progress}}==
=={{header|Oz}}==
=={{header|PHP}}==
=={{header|PL/I}}==
=={{header|PL/SQL}}==
=={{header|Pascal}}==
=={{header|Perl}}==
=={{header|Pike}}==
=={{header|PlainTeX}}==
=={{header|Pop11}}==
=={{header|PostScript}}==
=={{header|PowerShell}}==
=={{header|Prolog}}==
=={{header|Python}}==
=={{header|Q}}==
=={{header|R}}==
=={{header|REXX}}==
=={{header|RapidQ}}==
=={{header|Raven}}==
=={{header|Rhope}}==
=={{header|Ruby}}==
=={{header|SAS}}==
=={{header|SETL}}==
=={{header|SMEQL}}==
=={{header|SNUSP}}==
=={{header|SQL}}==
=={{header|Scala}}==
=={{header|Scheme}}==
=={{header|Script3D}}==
=={{header|Seed7}}==
=={{header|Self}}==
=={{header|Slate}}==
=={{header|Smalltalk}}==
=={{header|Standard ML}}==
=={{header|TI-83 BASIC}}==
=={{header|TI-89 BASIC}}==
=={{header|Tcl}}==
=={{header|Toka}}==
=={{header|Tr}}==
=={{header|Transact-SQL}}==
=={{header|Twelf}}==
=={{header|UNIX Shell}}==
=={{header|UnixPipes}}==
=={{header|Unlambda}}==
=={{header|V}}==
=={{header|VBScript}}==
=={{header|Vedit macro language}}==
=={{header|Visual Basic}}==
=={{header|Visual Basic .NET}}==
=={{header|Visual Objects}}==
=={{header|Wrapl}}==
=={{header|XSLT}}==
=={{header|XTalk}}==

Latest revision as of 10:13, 17 August 2012

BNF Grammar was a programming task. It has been deprecated for reasons that are discussed in its talk page.

In computer science, Backus–Naur Form (BNF) is a metasyntax used to express context-free grammars: that is, a formal way to describe formal languages. John Backus and Peter Naur developed a context free grammar to define the syntax of a programming language by using two sets of rules: i.e., lexical rules and syntactic rules.

BNF is widely used as a notation for the grammars of computer programming languages, instruction sets and communication protocols, as well as a notation for representing parts of natural language grammars. Many textbooks for programming language theory and/or semantics document the programming language in BNF.

There are many extensions and variants of BNF, including Extended and Augmented Backus–Naur Forms (EBNF and ABNF).

This is a deprecated task. Please move these grammars to the language's category page, or somewhere else.

BASIC

! -----------------------------------------------------------------------
! BASIC '64 
!
! Beginner's All-purpose Symbolic Instruction Code 
!
!    "It is practically impossible to teach good programming style to students 
!     that have had prior exposure to BASIC; as potential programmers they are 
!     mentally mutilated beyond hope of regeneration." 
!
!     - Edsger W. Dijkstra 
!
! BASIC is one of the oldest programming language and one of the most popular. 
! It was developed in 1964 by John G. Kemeny and Thomas E. Kurtz to teach 
! students the basics of programming concepts. At the advent of the microcomputer,
! BASIC was implemented on numerous platforms such as the Commodore, Atari, 
! Apple II, Altair, IBM PC computers. Over time, BASIC evolved into GW-BASIC, 
! QBasic, Visual Basic, and recently Visual Basic .NET.
!
! In practically all programming languages, the reserved word/symbol that denotes
! a comment is treated as a form of whitespace - having no effect in the manner in
! which the program runs. Once such type of comment is used to indicate the remainder
! of the line is to be ignored. These can be added to the end of any line without
! changing the meaning of the program. In C++, it is the '//' symbol;
! in BASIC '64 it is 'REM'.
!
! However, in the BASIC programming language, the line comment is treated like a 
! statement. For instance, if 'REM' was a normal line comment:
!
!    10  PRINT "Hello World" REM Common first program
!
! would be a valid statement. However, in BASIC, this is illegal. In the example 
! above, the comment must be added as an additional statement.
!
!    10  PRINT "Hello World" : REM Common first program
!
! As a result, the Line Comment terminal that is used in the GOLD Parser cannot be
! used here. In the grammar below, a 'Remark' terminal was created that accepts all 
! series of printable characters starting with the characters "REM ". In some 
! implementations of BASIC, any string starting with "REM" is a comment statement.
! Examples include "REMARK", "REMARKABLE" and "REMODEL". This grammar requires the space.
!
! This grammar does not include the editor statements such as NEW, SAVE, LOAD, etc...
!
! Note: This is an ad hoc version of the language. If there are any flaws, please 
! e-mail GOLDParser@DevinCook.com and I will update the grammar. Most likely I have
! included features not available in BASIC '64.
! -----------------------------------------------------------------------


"Name"    = 'BASIC (Beginners All-purpose Symbolic Instruction Code)'
"Author"  = 'John G. Kemeny and Thomas E. Kurtz' 
"Version" = '1964 - Original - before Microsoft enhanced the language for the IBM PC.'
"About"   = 'BASIC is one of most common and popular teaching languages ever created. '

"Case Sensitive" = False 
"Start Symbol"   = <Lines>

{String Chars} = {Printable} - ["]
{WS}           = {Whitespace} - {CR} - {LF}

NewLine        = {CR}{LF}|{CR}
Whitespace     = {WS}+

Remark         = REM{Space}{Printable}*
ID             = {Letter}[$%]? 
String         = '"'{String Chars}*'"' 
Integer        = {digit}+ 
Real           = {digit}+.{digit}+ 

<Lines>       ::= Integer <Statements> NewLine <Lines> 
                | Integer <Statements> NewLine

<Statements>  ::= <Statement> ':' <Statements>
                | <Statement>

<Statement>   ::= CLOSE '#' Integer
                | DATA <Constant List> 
                | DIM ID '(' <Integer List> ')'
                | END          
                | FOR ID '=' <Expression> TO <Expression>     
                | FOR ID '=' <Expression> TO <Expression> STEP Integer      
                | GOTO <Expression> 
                | GOSUB <Expression> 
                | IF <Expression> THEN <Statement>         
                | INPUT <ID List>       
                | INPUT '#' Integer ',' <ID List>       
                | LET Id '=' <Expression> 
                | NEXT <ID List>               
                | OPEN <Value> FOR <Access> AS '#' Integer
                | POKE <Value List>
                | PRINT <Print list>
                | PRINT '#' Integer ',' <Print List>
                | READ <ID List>           
                | RETURN
                | RESTORE
                | RUN
                | STOP
                | SYS <Value>
                | WAIT <Value List>
                | Remark

<Access>   ::= INPUT
             | OUPUT
                   
<ID List>  ::= ID ',' <ID List> 
             | ID 

<Value List>      ::= <Value> ',' <Value List> 
                    | <Value> 

<Constant List>   ::= <Constant> ',' <Constant List> 
                    | <Constant> 

<Integer List>    ::= Integer ',' <Integer List>
                    | Integer
                 
<Expression List> ::= <Expression> ',' <Expression List> 
                    | <Expression> 

<Print List>      ::= <Expression> ';' <Print List>
                    | <Expression> 
                    |  

<Expression>  ::= <And Exp> OR <Expression> 
                | <And Exp> 

<And Exp>     ::= <Not Exp> AND <And Exp> 
                | <Not Exp> 
 
<Not Exp>     ::= NOT <Compare Exp> 
                | <Compare Exp> 

<Compare Exp> ::= <Add Exp> '='  <Compare Exp> 
                | <Add Exp> '<>' <Compare Exp> 
                | <Add Exp> '><' <Compare Exp> 
                | <Add Exp> '>'  <Compare Exp> 
                | <Add Exp> '>=' <Compare Exp> 
                | <Add Exp> '<'  <Compare Exp> 
                | <Add Exp> '<=' <Compare Exp> 
                | <Add Exp> 

<Add Exp>     ::= <Mult Exp> '+' <Add Exp> 
                | <Mult Exp> '-' <Add Exp> 
                | <Mult Exp> 

<Mult Exp>    ::= <Negate Exp> '*' <Mult Exp> 
                | <Negate Exp> '/' <Mult Exp> 
                | <Negate Exp> 

<Negate Exp>  ::= '-' <Power Exp> 
                | <Power Exp> 

<Power Exp>   ::= <Power Exp> '^' <Value> 
                | <Value> 

<Value>       ::= '(' <Expression> ')'
                | ID 
                | ID '(' <Expression List> ')'
                | <Constant> 

<Constant> ::= Integer 
             | String 
             | Real 

BASIC Commodore PET

! -----------------------------------------------------------------------
! Commodore PET BASIC 
!
! Beginner's All-purpose Symbolic Instruction Code 
!
!    "It is practically impossible to teach good programming style to students 
!    that have had prior exposure to BASIC; as potential programmers they are 
!    mentally mutilated beyond hope of regeneration."    
!
!    - Edsger W. Dijkstra 
!
!
! BASIC is one of the oldest programming language and one of the most popular. 
! It was developed in 1964 by John G. Kemeny and Thomas E. Kurtz to teach 
! students the basics of programming concepts. At the advent of the microcomputer,
! BASIC was implemented on numerous platforms such as the Commodore, Atari, 
! Apple II, Altair, IBM PC computers. Over time, BASIC evolved into GW-BASIC, 
! QBasic, Visual Basic, and recently Visual Basic .NET.
!
! In practically all programming languages, the reserved word/symbol that denotes
! a comment is treated as a form of whitespace - having no effect in the manner in
! which the program runs. Once such type of comment is used to indicate the remainder
! of the line is to be ignored. These can be added to the end of any line without
! changing the meaning of the program. In C++, it is the '//' symbol.
!
! However, in the BASIC programming language, the line comment is treated like a 
! statement. For instance, if 'REM' was a normal line comment:
!
!    10  PRINT "Hello World" REM Common first program
!
! would be a valid statement. However, in BASIC, this is illegal. In the example 
! above, the comment must be added as an additional statement.
!
!    10  PRINT "Hello World" : REM Common first program
!
! As a result, the Line Comment terminal that is used in the GOLD Parser cannot be
! used here. In the grammar below, a 'Remark' terminal was created that accepts all 
! series of printable characters starting with the characters "REM ". In some 
! implementations of BASIC, any string starting with "REM" is a comment statement.
! Examples include "REMARK", "REMARKABLE" and "REMODEL". This grammar requires the space.
!
! -----------------------------------------------------------------------


"Name"    = 'Commodore PET BASIC'
"Author"  = 'Commodore Business Machines'
"Version" = '2.0'
"About"   = 'This is the version of BASIC that was used on the Commodore 64.'

"Case Sensitive" = False 
"Start Symbol"   = <Lines>

{String Chars} = {Printable} - ["]
{WS}           = {Whitespace} - {CR} - {LF}

NewLine        = {CR}{LF}|{CR}
Whitespace     = {WS}+

Remark         = REM{Space}{Printable}*
ID             = {Letter}{Alphanumeric}?[$%]?      !IDs are can only have a maximum of 2 characters
FunctionID     = FN {Letter}{Letter}?

String         = '"'{String Chars}*'"' 
Integer        = {Digit}+ 
Real           = {Digit}+'.'{Digit}+ 

<Lines>       ::= <Lines> <Line>
                | <Line>

<Line>        ::= Integer <Statements> NewLine 
                                
<Statements>  ::= <Statements> ':' <Statement>
                | <Statement>

<Statement>   ::= CLOSE Integer
                | CLR
                | CMD  <Expression>
                | CONT                                          !Continue
                | DATA <Constant List> 
                | DEF FunctionID '(' <ID List> ')' '=' <Expression>    !The ID must start with FN
                | DIM ID '(' <Expression List> ')'
                | END          
                | FOR ID '=' <Expression> TO <Expression> <Step Opt>     
                | GET ID
                | GET '#' Integer ',' ID
                | GOSUB <Expression> 
                | GOTO <Expression>                 
                | IF <Expression> THEN <Then Clause>                
                | INPUT <ID List>       
                | INPUT '#' Integer ',' <ID List>       
                | LET ID '=' <Expression> 
                | LIST <Line Range>
                | LOAD <Value List>        
                | ID '=' <Expression> 
                | NEW
                | NEXT <ID List>               
                | ON ID GOTO <Expression List>
                | OPEN <Expression List>         
                | POKE <Expression> ',' <Expression>
                | PRINT <Print list>
                | PRINT '#' Integer ',' <Print List>
                | READ <ID List>           
                | RETURN
                | RESTORE
                | RUN
                | RUN <Expression>
                | STOP
                | SYS <Expression>
                | WAIT <Expression List>     
                | VERIFY <Expression List>     
                | Remark

<Step Opt> ::= STEP <Expression>
             | 
                   
<ID List>  ::= ID ',' <ID List> 
             | ID 

<Value List>      ::= <Value> ',' <Value List> 
                    | <Value> 

<Constant List>   ::= <Constant> ',' <Constant List> 
                    | <Constant> 
                 
<Expression List> ::= <Expression> ',' <Expression List> 
                    | <Expression> 

<Print List>      ::= <Expression> ';' <Print List>
                    | <Expression> 
                    |  

<Line Range>  ::= Integer 
                | Integer '-'
                | Integer '-' Integer 

<Then Clause> ::= Integer
                | <Statement>

! ----------------------------------------------- Expressions

<Expression>  ::= <And Exp> OR <Expression> 
                | <And Exp> 

<And Exp>     ::= <Not Exp> AND <And Exp> 
                | <Not Exp> 
 
<Not Exp>     ::= NOT <Compare Exp> 
                | <Compare Exp> 

<Compare Exp> ::= <Add Exp> '='  <Compare Exp> 
                | <Add Exp> '<>' <Compare Exp> 
                | <Add Exp> '>'  <Compare Exp> 
                | <Add Exp> '>=' <Compare Exp> 
                | <Add Exp> '<'  <Compare Exp> 
                | <Add Exp> '<=' <Compare Exp> 
                | <Add Exp> 

<Add Exp>     ::= <Mult Exp> '+' <Add Exp> 
                | <Mult Exp> '-' <Add Exp> 
                | <Mult Exp> 

<Mult Exp>    ::= <Negate Exp> '*' <Mult Exp> 
                | <Negate Exp> '/' <Mult Exp> 
                | <Negate Exp> 

<Negate Exp>  ::= '-' <Power Exp> 
                | <Power Exp> 

<Power Exp>   ::= <Power Exp> '^' <Sub Exp>        !On the Commodore, the symbol was an up-arrow
                | <Sub Exp> 

<Sub Exp>     ::= '(' <Expression> ')'
                | <Value>

<Value>       ::= ID 
                | ABS        '(' <Expression> ')'
                | ASC        '(' <Expression> ')'
                | ATN        '(' <Expression> ')'
                | 'CHR$'     '(' <Expression> ')'
                | COS        '(' <Expression> ')'
                | EXP        '(' <Expression> ')'
                | FunctionID '(' <Expression List> ')'
                | FRE        '(' <Value> ')'                  !The <Value> is  irrelevant
                | INT        '(' <Expression> ')'
                | 'LEFT$'    '(' <Expression> ',' <Expression> ')'
                | LEN        '(' <Expression> ')'
                | PEEK       '(' <Expression> ')'
                | POS        '(' <Value> ')'                  !The <Value> is  irrelevant
                | 'RIGHT$'   '(' <Expression> ',' <Expression> ')'
                | RND        '(' <Expression> ')'
                | SGN        '(' <Expression> ')' 
                | SPC        '(' <Expression> ')' 
                | SQR        '(' <Expression> ')' 
                | TAB        '(' <Expression> ')' 
                | TAN        '(' <Expression> ')' 
                | VAL        '(' <Expression> ')' 
                
                | <Constant> 

<Constant>    ::= Integer 
                | String 
                | Real 

Brainf***

 Code ::= Command Code | <NONE>
 Command ::= "+" | "-" | "<" | ">" | "," | "." | "[" Code "]" | <ANY>

PARI/GP

parse.y contains a grammar for GP. The grammar for PARI is that of C.

PowerShell

An annotated version of the PowerShell grammar can be found in Bruce Payette's book Windows PowerShell in Action. The appendix containing the grammar is available in PDF form on the publisher's site.

This grammar does not accurately represent the PowerShell language, though, as for example the for loop mandates semicolons in the grammar but in practice does not require them when arguments are omitted. The infinite loop may be represented by <lang powershell>for () {}</lang> but the grammar would require <lang powershell>for (;;) {}</lang>

VBScript

!===============================
! VB Script grammar.
!
! To create the grammar I was using Microsoft's VB Script documentation
! available from http://msdn.microsoft.com/scripting,
! VB Script parser from ArrowHead project http://www.tripi.com/arrowhead/,
! and Visual Basic .Net grammar file written by Devin Cook.
!
! This grammar cannot cover all aspects of VBScript and may have some errors.
! Feel free to contact me if you find any flaws in the grammar.
!
! Vladimir Morozov   vmoroz@hotmail.com
!
! Special thanks to Nathan Baulch for the grammar updates. 
!
! USE GOLD PARSER BUILDER VERSION 2.1 AND LATER TO COMPILE THIS GRAMMAR.
!===============================

"Name"            = 'VB Script'
"Author"          = 'John G. Kemeny and Thomas E. Kurtz'
"Version"         = '5.0'
"About"           = 'VB Script grammar.'
"Case Sensitive"  = False
"Start Symbol"    = <Program>

!===============================
! Character sets
!===============================

{String Char}   = {All Valid} - ["]
{Date Char}     = {Printable} - [#]
{ID Name Char}  = {Printable} - ['['']']
{Hex Digit}     = {Digit} + [abcdef]
{Oct Digit}     = [01234567]
{WS}            = {Whitespace} - {CR} - {LF}
{ID Tail}       = {Alphanumeric} + [_]

!===============================
! Terminals
!===============================

NewLine        = {CR} {LF}
               | {CR}
               | {LF}
               | ':'

! Special white space definition. Whitespace is either space or tab, which
! can be followed by continuation symbol '_' followed by new line character
Whitespace     = {WS}+
               | '_' {WS}* {CR}? {LF}?

! Special comment definition
Comment Line   = ''
               | 'Rem'

! Literals
StringLiteral  = '"' ( {String Char} | '""' )* '"'
IntLiteral     = {Digit}+
HexLiteral     = '&H' {Hex Digit}+ '&'?
OctLiteral     = '&' {Oct Digit}+ '&'?
FloatLiteral   = {Digit}* '.' {Digit}+ ( 'E' [+-]? {Digit}+ )?
               | {Digit}+ 'E' [+-]? {Digit}+
DateLiteral    = '#' {Date Char}+ '#'

! Identifier is either starts with letter and followed by letter,
! number or underscore, or it can be escaped sequence of any printable
! characters ([] and [_$% :-) @] are valid identifiers)
ID             = {Letter} {ID Tail}*
               | '[' {ID Name Char}* ']'

! White space is not allowed to be before dot, but allowed to be after it.
IDDot          = {Letter} {ID Tail}* '.'
               | '[' {ID Name Char}* ']' '.'
               | 'And.'
               | 'ByRef.'
               | 'ByVal.'
               | 'Call.'
               | 'Case.'
               | 'Class.'
               | 'Const.'
               | 'Default.'
               | 'Dim.'
               | 'Do.'
               | 'Each.'
               | 'Else.'
               | 'ElseIf.'
               | 'Empty.'
               | 'End.'
               | 'Eqv.'
               | 'Erase.'
               | 'Error.'
               | 'Exit.'
               | 'Explicit.'
               | 'False.'
               | 'For.'
               | 'Function.'
               | 'Get.'
               | 'GoTo.'
               | 'If.'
               | 'Imp.'
               | 'In.'
               | 'Is.'
               | 'Let.'
               | 'Loop.'
               | 'Mod.'
               | 'New.'
               | 'Next.'
               | 'Not.'
               | 'Nothing.'
               | 'Null.'
               | 'On.'
               | 'Option.'
               | 'Or.'
               | 'Preserve.'
               | 'Private.'
               | 'Property.'
               | 'Public.'
               | 'Redim.'
               | 'Rem.'
               | 'Resume.'
               | 'Select.'
               | 'Set.'
               | 'Step.'
               | 'Sub.'
               | 'Then.'
               | 'To.'
               | 'True.'
               | 'Until.'
               | 'WEnd.'
               | 'While.'
               | 'With.'
               | 'Xor.'

! The following identifiers should only be used in With statement.
! This rule must be checked by contextual analyzer.
DotID          = '.' {Letter} {ID Tail}*
               | '.' '[' {ID Name Char}* ']'
               | '.And'
               | '.ByRef'
               | '.ByVal'
               | '.Call'
               | '.Case'
               | '.Class'
               | '.Const'
               | '.Default'
               | '.Dim'
               | '.Do'
               | '.Each'
               | '.Else'
               | '.ElseIf'
               | '.Empty'
               | '.End'
               | '.Eqv'
               | '.Erase'
               | '.Error'
               | '.Exit'
               | '.Explicit'
               | '.False'
               | '.For'
               | '.Function'
               | '.Get'
               | '.GoTo'
               | '.If'
               | '.Imp'
               | '.In'
               | '.Is'
               | '.Let'
               | '.Loop'
               | '.Mod'
               | '.New'
               | '.Next'
               | '.Not'
               | '.Nothing'
               | '.Null'
               | '.On'
               | '.Option'
               | '.Or'
               | '.Preserve'
               | '.Private'
               | '.Property'
               | '.Public'
               | '.Redim'
               | '.Rem' 
               | '.Resume'
               | '.Select'
               | '.Set'
               | '.Step'
               | '.Sub'
               | '.Then'
               | '.To'
               | '.True'
               | '.Until'
               | '.WEnd'
               | '.While'
               | '.With'
               | '.Xor'

DotIDDot       = '.' {Letter}{ID Tail}* '.'
               | '.' '[' {ID Name Char}* ']' '.'
               | '.And.'
               | '.ByRef.'
               | '.ByVal.'
               | '.Call.'
               | '.Case.'
               | '.Class.'
               | '.Const.'
               | '.Default.'
               | '.Dim.'
               | '.Do.'
               | '.Each.'
               | '.Else.'
               | '.ElseIf.'
               | '.Empty.'
               | '.End.'
               | '.Eqv.'
               | '.Erase.'
               | '.Error.'
               | '.Exit.'
               | '.Explicit.'
               | '.False.'
               | '.For.'
               | '.Function.'
               | '.Get.'
               | '.GoTo.'
               | '.If.'
               | '.Imp.'
               | '.In.'
               | '.Is.'
               | '.Let.'
               | '.Loop.'
               | '.Mod.'
               | '.New.'
               | '.Next.'
               | '.Not.'
               | '.Nothing.'
               | '.Null.'
               | '.On.'
               | '.Option.'
               | '.Or.'
               | '.Preserve.'
               | '.Private.'
               | '.Property.'
               | '.Public.'
               | '.Redim.'
               | '.Rem.'
               | '.Resume.'
               | '.Select.'
               | '.Set.'
               | '.Step.'
               | '.Sub.'
               | '.Then.'
               | '.To.'
               | '.True.'
               | '.Until.'
               | '.WEnd.'
               | '.While.'
               | '.With.'
               | '.Xor.'

!===============================
! Rules
!===============================

<NL>                   ::= NewLine <NL>
                         | NewLine

<Program>              ::= <NLOpt> <GlobalStmtList>

!===============================
! Rules : Declarations
!===============================

<ClassDecl>            ::= 'Class' <ExtendedID> <NL> <MemberDeclList> 'End' 'Class' <NL>

<MemberDeclList>       ::= <MemberDecl> <MemberDeclList>
                         |

<MemberDecl>           ::= <FieldDecl>
                         | <VarDecl>
                         | <ConstDecl>
                         | <SubDecl>
                         | <FunctionDecl>
                         | <PropertyDecl>

<FieldDecl>            ::= 'Private' <FieldName> <OtherVarsOpt> <NL>
                         | 'Public' <FieldName> <OtherVarsOpt> <NL>

<FieldName>            ::= <FieldID> '(' <ArrayRankList> ')'
                         | <FieldID>

<FieldID>              ::= ID
                         | 'Default'
                         | 'Erase'
                         | 'Error'
                         | 'Explicit'
                         | 'Step'

<VarDecl>              ::= 'Dim' <VarName> <OtherVarsOpt> <NL>

<VarName>              ::= <ExtendedID> '(' <ArrayRankList> ')'
                         | <ExtendedID>

<OtherVarsOpt>         ::= ',' <VarName> <OtherVarsOpt>
                         |

<ArrayRankList>        ::= <IntLiteral> ',' <ArrayRankList>
                         | <IntLiteral>
                         |

<ConstDecl>            ::= <AccessModifierOpt> 'Const' <ConstList> <NL>

<ConstList>            ::= <ExtendedID> '=' <ConstExprDef> ',' <ConstList>
                         | <ExtendedID> '=' <ConstExprDef>

<ConstExprDef>         ::= '(' <ConstExprDef> ')'
                         | '-' <ConstExprDef>
                         | '+' <ConstExprDef> 
                         | <ConstExpr> 

<SubDecl>              ::= <MethodAccessOpt> 'Sub' <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Sub' <NL>
                         | <MethodAccessOpt> 'Sub' <ExtendedID> <MethodArgList> <InlineStmt> 'End' 'Sub' <NL>

<FunctionDecl>         ::= <MethodAccessOpt> 'Function' <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Function' <NL>
                         | <MethodAccessOpt> 'Function' <ExtendedID> <MethodArgList> <InlineStmt> 'End' 'Function' <NL>

<MethodAccessOpt>      ::= 'Public' 'Default'
                         | <AccessModifierOpt>

<AccessModifierOpt>    ::= 'Public'
                         | 'Private'
                         |

<MethodArgList>        ::= '(' <ArgList> ')'
                         | '(' ')'
                         |

<ArgList>              ::= <Arg> ',' <ArgList>
                         | <Arg>

<Arg>                  ::= <ArgModifierOpt> <ExtendedID> '(' ')'
                         | <ArgModifierOpt> <ExtendedID>

<ArgModifierOpt>       ::= 'ByVal'
                         | 'ByRef'
                         |

<PropertyDecl>         ::= <MethodAccessOpt> 'Property' <PropertyAccessType> <ExtendedID> <MethodArgList> <NL> <MethodStmtList> 'End' 'Property' <NL>                        

<PropertyAccessType>   ::= 'Get'
                         | 'Let'
                         | 'Set'

!===============================
! Rules : Statements
!===============================

<GlobalStmt>           ::= <OptionExplicit>
                         | <ClassDecl>
                         | <FieldDecl>
                         | <ConstDecl>
                         | <SubDecl>
                         | <FunctionDecl>
                         | <BlockStmt>

<MethodStmt>           ::= <ConstDecl>
                         | <BlockStmt>

<BlockStmt>            ::= <VarDecl>
                         | <RedimStmt>
                         | <IfStmt>
                         | <WithStmt>
                         | <SelectStmt>
                         | <LoopStmt>
                         | <ForStmt>
                         | <InlineStmt> <NL>

<InlineStmt>           ::= <AssignStmt>
                         | <CallStmt>
                         | <SubCallStmt>
                         | <ErrorStmt>
                         | <ExitStmt>
                         | 'Erase' <ExtendedID>

<GlobalStmtList>       ::= <GlobalStmt> <GlobalStmtList>
                         | 

<MethodStmtList>       ::= <MethodStmt> <MethodStmtList>
                         |
                        
<BlockStmtList>        ::= <BlockStmt> <BlockStmtList>
                         |
                        
<OptionExplicit>       ::= 'Option' 'Explicit' <NL>

<ErrorStmt>            ::= 'On' 'Error' 'Resume' 'Next'
                         | 'On' 'Error' 'GoTo' IntLiteral  ! must be 0

<ExitStmt>             ::= 'Exit' 'Do'
                         | 'Exit' 'For'
                         | 'Exit' 'Function'
                         | 'Exit' 'Property'
                         | 'Exit' 'Sub'

<AssignStmt>           ::= <LeftExpr> '=' <Expr>
                         | 'Set' <LeftExpr> '=' <Expr>
                         | 'Set' <LeftExpr> '=' 'New' <LeftExpr>

! Hack: VB Script allows to have construct a = b = c, which means a = (b = c)
! In this grammar we do not allow it in order to prevent complications with
! interpretation of a(1) = 2, which may be considered as array element assignment
! or a subroutine call: a ((1) = 2).
! Note: VBScript allows to have missed parameters: a ,,2,3,
! VM: If somebody knows a better way to do it, please let me know
<SubCallStmt>          ::= <QualifiedID> <SubSafeExprOpt> <CommaExprList>
                         | <QualifiedID> <SubSafeExprOpt>
                         | <QualifiedID> '(' <Expr> ')' <CommaExprList>
                         | <QualifiedID> '(' <Expr> ')'
                         | <QualifiedID> '(' ')'
                         | <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail> <SubSafeExprOpt> <CommaExprList>
                         | <QualifiedID> <IndexOrParamsListDot> <LeftExprTail> <SubSafeExprOpt> <CommaExprList>
                         | <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail> <SubSafeExprOpt>
                         | <QualifiedID> <IndexOrParamsListDot> <LeftExprTail> <SubSafeExprOpt>

! This very simplified case - the problem is that we cannot use parenthesis in aaa(bbb).ccc (ddd)
<SubSafeExprOpt>       ::= <SubSafeExpr>
                         |

<CallStmt>             ::= 'Call' <LeftExpr>

<LeftExpr>             ::= <QualifiedID> <IndexOrParamsList> '.' <LeftExprTail>
                         | <QualifiedID> <IndexOrParamsListDot> <LeftExprTail>
                         | <QualifiedID> <IndexOrParamsList>
                         | <QualifiedID>
                         | <SafeKeywordID>

<LeftExprTail>         ::= <QualifiedIDTail> <IndexOrParamsList> '.' <LeftExprTail>
                         | <QualifiedIDTail> <IndexOrParamsListDot> <LeftExprTail>
                         | <QualifiedIDTail> <IndexOrParamsList>
                         | <QualifiedIDTail>

! VB Script does not allow to have space between Identifier and dot:
! a . b - Error ; a. b or a.b - OK
<QualifiedID>          ::= IDDot <QualifiedIDTail>
                         | DotIDDot <QualifiedIDTail>
                         | ID
                         | DotID

<QualifiedIDTail>      ::= IDDot <QualifiedIDTail>
                         | ID
                         | <KeywordID>

<KeywordID>            ::= <SafeKeywordID>
                         | 'And'
                         | 'ByRef'
                         | 'ByVal'
                         | 'Call'
                         | 'Case'
                         | 'Class'
                         | 'Const'
                         | 'Dim'
                         | 'Do'
                         | 'Each'
                         | 'Else'
                         | 'ElseIf'
                         | 'Empty'
                         | 'End'
                         | 'Eqv'
                         | 'Exit'
                         | 'False'
                         | 'For'
                         | 'Function'
                         | 'Get'
                         | 'GoTo'
                         | 'If'
                         | 'Imp'
                         | 'In'
                         | 'Is'
                         | 'Let'
                         | 'Loop'
                         | 'Mod'
                         | 'New'
                         | 'Next'
                         | 'Not'
                         | 'Nothing'
                         | 'Null'
                         | 'On'
                         | 'Option'
                         | 'Or'
                         | 'Preserve'
                         | 'Private'
                         | 'Public'
                         | 'Redim'
                         | 'Resume'
                         | 'Select'
                         | 'Set'
                         | 'Sub'
                         | 'Then'
                         | 'To'
                         | 'True'
                         | 'Until'
                         | 'WEnd'
                         | 'While'
                         | 'With'
                         | 'Xor'

<SafeKeywordID>        ::= 'Default'
                         | 'Erase'
                         | 'Error'
                         | 'Explicit'
                         | 'Property'
                         | 'Step'

<ExtendedID>           ::= <SafeKeywordID>
                         | ID

<IndexOrParamsList>    ::= <IndexOrParams> <IndexOrParamsList>
                         | <IndexOrParams>

<IndexOrParams>        ::= '(' <Expr> <CommaExprList> ')'
                         | '(' <CommaExprList> ')'
                         | '(' <Expr> ')'
                         | '(' ')'

<IndexOrParamsListDot> ::= <IndexOrParams> <IndexOrParamsListDot>
                         | <IndexOrParamsDot>

<IndexOrParamsDot>     ::= '(' <Expr> <CommaExprList> ').'
                         | '(' <CommaExprList> ').'
                         | '(' <Expr> ').'
                         | '(' ').'

<CommaExprList>        ::= ',' <Expr> <CommaExprList>
                         | ',' <CommaExprList>
                         | ',' <Expr>
                         | ','

!========= Redim Statement

<RedimStmt>            ::= 'Redim' <RedimDeclList> <NL>
                         | 'Redim' 'Preserve' <RedimDeclList> <NL>

<RedimDeclList>        ::= <RedimDecl> ',' <RedimDeclList>
                         | <RedimDecl>

<RedimDecl>            ::= <ExtendedID> '(' <ExprList> ')'

!========= If Statement

<IfStmt>               ::= 'If' <Expr> 'Then' <NL> <BlockStmtList> <ElseStmtList> 'End' 'If' <NL>
                         | 'If' <Expr> 'Then' <InlineStmt> <ElseOpt> <EndIfOpt> <NL>

<ElseStmtList>         ::= 'ElseIf' <Expr> 'Then' <NL> <BlockStmtList> <ElseStmtList>
                         | 'ElseIf' <Expr> 'Then' <InlineStmt> <NL> <ElseStmtList>
                         | 'Else' <InlineStmt> <NL>
                         | 'Else' <NL> <BlockStmtList>
                         |

<ElseOpt>              ::= 'Else' <InlineStmt>
                         |

<EndIfOpt>             ::= 'End' 'If'
                         |

!========= With Statement

<WithStmt>             ::= 'With' <Expr> <NL> <BlockStmtList> 'End' 'With' <NL>

!========= Loop Statement

<LoopStmt>             ::= 'Do' <LoopType> <Expr> <NL> <BlockStmtList> 'Loop' <NL>
                         | 'Do' <NL> <BlockStmtList> 'Loop' <LoopType> <Expr> <NL>
                         | 'Do' <NL> <BlockStmtList> 'Loop' <NL>
                         | 'While' <Expr> <NL> <BlockStmtList> 'WEnd' <NL>

<LoopType>             ::= 'While'
                         | 'Until'

!========= For Statement

<ForStmt>              ::= 'For' <ExtendedID> '=' <Expr> 'To' <Expr> <StepOpt> <NL> <BlockStmtList> 'Next' <NL>
                         | 'For' 'Each' <ExtendedID> 'In' <Expr> <NL> <BlockStmtList> 'Next' <NL>

<StepOpt>              ::= 'Step' <Expr>
                         |

!========= Select Statement

<SelectStmt>           ::= 'Select' 'Case' <Expr> <NL> <CaseStmtList> 'End' 'Select' <NL>

<CaseStmtList>         ::= 'Case' <ExprList> <NLOpt> <BlockStmtList> <CaseStmtList>
                         | 'Case' 'Else' <NLOpt> <BlockStmtList>
                         |

<NLOpt>                ::= <NL>
                         |

<ExprList>             ::= <Expr> ',' <ExprList>
                         | <Expr>

!===============================
! Rules : Expressions
!===============================

<SubSafeExpr>          ::= <SubSafeImpExpr>

<SubSafeImpExpr>       ::= <SubSafeImpExpr> 'Imp' <EqvExpr>
                         | <SubSafeEqvExpr>

<SubSafeEqvExpr>       ::= <SubSafeEqvExpr> 'Eqv' <XorExpr>
                         | <SubSafeXorExpr>

<SubSafeXorExpr>       ::= <SubSafeXorExpr> 'Xor' <OrExpr>
                         | <SubSafeOrExpr>

<SubSafeOrExpr>        ::= <SubSafeOrExpr> 'Or' <AndExpr>
                         | <SubSafeAndExpr>

<SubSafeAndExpr>       ::= <SubSafeAndExpr> 'And' <NotExpr>
                         | <SubSafeNotExpr>

<SubSafeNotExpr>       ::= 'Not' <NotExpr>
                         | <SubSafeCompareExpr>

<SubSafeCompareExpr>   ::= <SubSafeCompareExpr> 'Is' <ConcatExpr>
                         | <SubSafeCompareExpr> 'Is' 'Not' <ConcatExpr>
                         | <SubSafeCompareExpr> '>=' <ConcatExpr>
                         | <SubSafeCompareExpr> '=>' <ConcatExpr>
                         | <SubSafeCompareExpr> '<=' <ConcatExpr>
                         | <SubSafeCompareExpr> '=<' <ConcatExpr>
                         | <SubSafeCompareExpr> '>'  <ConcatExpr>
                         | <SubSafeCompareExpr> '<'  <ConcatExpr>
                         | <SubSafeCompareExpr> '<>' <ConcatExpr>
                         | <SubSafeCompareExpr> '='  <ConcatExpr>
                         | <SubSafeConcatExpr>

<SubSafeConcatExpr>    ::= <SubSafeConcatExpr> '&' <AddExpr>
                         | <SubSafeAddExpr>

<SubSafeAddExpr>       ::= <SubSafeAddExpr> '+' <ModExpr>
                         | <SubSafeAddExpr> '-' <ModExpr>
                         | <SubSafeModExpr>

<SubSafeModExpr>       ::= <SubSafeModExpr> 'Mod' <IntDivExpr>
                         | <SubSafeIntDivExpr>

<SubSafeIntDivExpr>    ::= <SubSafeIntDivExpr> '\' <MultExpr>
                         | <SubSafeMultExpr>

<SubSafeMultExpr>      ::= <SubSafeMultExpr> '*' <UnaryExpr>
                         | <SubSafeMultExpr> '/' <UnaryExpr>
                         | <SubSafeUnaryExpr>

<SubSafeUnaryExpr>     ::= '-' <UnaryExpr>
                         | '+' <UnaryExpr>
                         | <SubSafeExpExpr>

<SubSafeExpExpr>       ::= <SubSafeValue> '^' <ExpExpr>
                         | <SubSafeValue>

<SubSafeValue>         ::= <ConstExpr>
                         | <LeftExpr>
!                         | '(' <Expr> ')'

<Expr>                 ::= <ImpExpr>

<ImpExpr>              ::= <ImpExpr> 'Imp' <EqvExpr>
                         | <EqvExpr>

<EqvExpr>              ::= <EqvExpr> 'Eqv' <XorExpr>
                         | <XorExpr>

<XorExpr>              ::= <XorExpr> 'Xor' <OrExpr>
                         | <OrExpr>

<OrExpr>               ::= <OrExpr> 'Or' <AndExpr>
                         | <AndExpr>

<AndExpr>              ::= <AndExpr> 'And' <NotExpr>
                         | <NotExpr>

<NotExpr>              ::= 'Not' <NotExpr>
                         | <CompareExpr>

<CompareExpr>          ::= <CompareExpr> 'Is' <ConcatExpr>
                         | <CompareExpr> 'Is' 'Not' <ConcatExpr>
                         | <CompareExpr> '>=' <ConcatExpr>
                         | <CompareExpr> '=>' <ConcatExpr>
                         | <CompareExpr> '<=' <ConcatExpr>
                         | <CompareExpr> '=<' <ConcatExpr>
                         | <CompareExpr> '>'  <ConcatExpr>
                         | <CompareExpr> '<'  <ConcatExpr>
                         | <CompareExpr> '<>' <ConcatExpr>
                         | <CompareExpr> '='  <ConcatExpr>
                         | <ConcatExpr>

<ConcatExpr>           ::= <ConcatExpr> '&' <AddExpr>
                         | <AddExpr>

<AddExpr>              ::= <AddExpr> '+' <ModExpr>
                         | <AddExpr> '-' <ModExpr>
                         | <ModExpr>

<ModExpr>              ::= <ModExpr> 'Mod' <IntDivExpr>
                         | <IntDivExpr>

<IntDivExpr>           ::= <IntDivExpr> '\' <MultExpr>
                         | <MultExpr>

<MultExpr>             ::= <MultExpr> '*' <UnaryExpr>
                         | <MultExpr> '/' <UnaryExpr>
                         | <UnaryExpr>

<UnaryExpr>            ::= '-' <UnaryExpr>
                         | '+' <UnaryExpr>
                         | <ExpExpr>

<ExpExpr>              ::= <Value> '^' <ExpExpr>
                         | <Value>

<Value>                ::= <ConstExpr>
                         | <LeftExpr>
                         | '(' <Expr> ')'

<ConstExpr>            ::= <BoolLiteral>
                         | <IntLiteral>
                         | FloatLiteral
                         | StringLiteral
                         | DateLiteral
                         | <Nothing>

<BoolLiteral>          ::= 'True'
                         | 'False'

<IntLiteral>           ::= IntLiteral
                         | HexLiteral
                         | OctLiteral

<Nothing>              ::= 'Nothing'
                         | 'Null'
                         | 'Empty'

Visual Basic .NET

The following link (Appedix B) has a simple BNF Syntax VB Syntax

! -----------------------------------------------------------------------
! Visual Basic .NET
! 
! Visual Basic .NET is the latest version in the long evoluation of the 
! BASIC programming language. The Visual Basic .NET programming language 
! is far more "clean" and orthagonal than its predecessors. Although some 
! of the old constructs exist, the language is far easier to read and write.
! 
! Major syntax changes include, but are not limited to:
! 
! 1. The primative file access of VB6 was replaced by a class library. As 
!    a result, special statements such as 
!    
!    Open "test" For Input As #1
!    
!    no longer exist. 
! 
! 2. Class module files were replaced by 'Class ... End Class' declarations
! 
! 3. Module files were replaced by 'Module ... End Module' declarations
!
! 4. Structured error handling was added with C++ style Try ... Catch 
!    statements. The old nonstructured approach is still, unfortunately,
!    available.
! 
! Unfortnately, the designers of Visual Basic .NET did not remove the 
! datatype postfix characters on identifiers. In the original BASIC, 
! variables types were determined by $ for strings and % for integers.
! QuickBasic expanded the postix notation to include other symbols 
! for long integers, singles, etc... 
!
! Part of the ID terminal definition was commented out to prevent the
! old format. You can allow the postfix characters if you like.
!
! This grammar also does not contain the compiler directives.
!
! Note: This is an ad hoc version of the language. If there are any flaws, 
! please visit www.DevinCook.com/GOLDParser
!
! Updates:
!     04/082005
!         Devin Cook
!         1. Removed minus sign from the IntLiteral and RealLiteral 
!            definitions. These can cause some parse errors when expressions
!            like "2-2" are read. In this case it would have been interpreted
!            as "2" and "-2" rather than "2", "-" and "2".
!         2. Members of an enumeration can be defined with any expression.
!         3. Made some very minor comment changes - mainly for readability.
!
!     03/27/2005
!         Adrian Moore [adrianrob@hotmail.com]
!         1. Add support for Implements in Class
!         2. Add support for AddressOf keyword
!         3. No longer fails if variable starts with _
!
!     02/24/2004
!         Vladimir Morozov [vmoroz@hotmail.com] fixed a few flaws in the
!         grammar. 1. The definition for strings did not allow the double 
!         double-quote override. 2. A real literal does not need to have a 
!         fraction if followed by an exponent. 3. Escaped identifiers can 
!         contain a null string and 4. Rem works the same as the '
!
!
! USE GOLD PARSER BUILDER VERSION 2.1 AND LATER TO COMPILE THIS GRAMMAR.
! Earlier versions cannot handle the complexity.
! -----------------------------------------------------------------------

"Name"     = 'Visual Basic .NET' 
"Author"   = 'John G. Kemeny and Thomas E. Kurtz'
"Version"  = '.NET'
"About"    = 'Visual Basic .NET is the latest version in the long evoluation of the'
           | 'BASIC programming language.'
                 

"Case Sensitive" = False 
"Start Symbol"   = <Program>

! ----------------------------------------------------------------- Sets

{String Chars}  = {Printable} - ["]
{Date Chars}    = {Printable} - [#]
{ID Name Chars} = {Printable} - ['['']']
{Hex Digit}     = {Digit} + [abcdef]
{Oct Digit}     = [01234567]

{WS}            = {Whitespace} - {CR} - {LF}
{Id Tail}       = {Alphanumeric} + [_]

! ----------------------------------------------------------------- Terminals

NewLine        = {CR}{LF} | {CR} | ':' 
Whitespace     = {WS}+  | '_' {WS}* {CR} {LF}?

Comment Line   = '' | Rem                !Fixed by Vladimir Morozov 

LABEL          = {Letter}{ID Tail}*':'

!Fixed by Vladimir Morozov 

ID             = [_]?{Letter}{ID Tail}*           ! [%&@!#$]?   !Archaic postfix chars
               | '[' {ID Name Chars}* ']'
     
QualifiedID    = ({Letter}{ID Tail}* | '['{ID Name Chars}*']')  ( '.'({Letter}{ID Tail}* | '['{ID Name Chars}*']') )+

MemberID       = '.' {Letter}{ID Tail}* 
               | '.[' {ID Name Chars}* ']'
               
!Fixed by Vladimir Morozov 
StringLiteral  = '"' ( {String Chars} | '""' )* '"'


CharLiteral    = '"' {String Chars}* '"C'
IntLiteral     = {digit}+ [FRDSIL]?

RealLiteral    = {digit}* '.' {digit}+ ( 'E' [+-]? {Digit}+ )? [FR]?
               | {digit}+ 'E' [+-]? {Digit}+  [FR]?


DateLiteral    = '#'{Date chars}'#'

HexLiteral     = '&H'{Hex Digit}+ [SIL]?
OctLiteral     = '&O'{Oct Digit}+ [SIL]?

! ----------------------------------------------------------------- Rules

<Program>    ::= <NameSpace Item>  <Program>
               | <Imports>         <Program>
               | <Option Decl>     <Program>
               |

! -------------------------------------------------------------------
! (Shared attributes)
! -------------------------------------------------------------------

<NL>    ::= NewLine <NL> 
          | NewLine

<Modifiers> ::= <Modifier> <Modifiers>
              | 

<Modifier> ::= Shadows
             | Shared
             | MustInherit 
             | NotInheritable

             | Overridable 
             | NotOverridable 
             | MustOverride 
             | Overrides 
             | Overloads
                  
             | Default 
             | ReadOnly
             | WriteOnly
            
             | <Access>

<Access Opt> ::= <Access>
               |

<Access>  ::= Public
            | Private
            | Friend
            | Protected
            

<Var Member>   ::=  <Attributes> <Access> <Var Decl> <NL>               !Variables                    
                 |  <Attributes> <Access Opt> Const  <Var Decl> <NL>    !Constants
                 |  <Attributes> <Access Opt> Static <Var Decl> <NL>                         
                
<Implements>   ::= Implements <ID List> 

<ID List>  ::= <Identifier> ',' <ID List>
             | <Identifier>
               
<Option Decl>  ::= Option <IDs> <NL>

<IDs> ::= ID <IDs> 
        | ID
   
<Type>  ::= As <Attributes> <Identifier> 
          |

<Compare Op>  ::= '=' | '<>' | '<' | '>' | '>=' | '<='

! -------------------------------------------------------------------
! NameSpace
! -------------------------------------------------------------------

<NameSpace>       ::= NameSpace ID <NL> <NameSpace Items> End NameSpace <NL>

<NameSpace Items> ::= <NameSpace Item> <NameSpace Items>                    
                    | 

<NameSpace Item> ::= <Class>      
                   | <Declare>
                   | <Delegate>
                   | <Enumeration> 
                   | <Interface>
                   | <Structure> 
                   | <Module>              
                   | <Namespace>
          

! -------------------------------------------------------------------
! Attributes
! -------------------------------------------------------------------

<Attributes> ::= '<' <Attribute List> '>'
               |

<Attribute List> ::= <Attribute> ',' <Attribute List>
                   | <Attribute>
                   
<Attribute>     ::= <Attribute Mod> ID <Argument List Opt>                  
   
<Attribute Mod> ::= Assembly 
                  | Module 
                  | 
                             
! -------------------------------------------------------------------
! Delegates
! -------------------------------------------------------------------
<Delegate> ::= <Attributes> <Modifiers> Delegate <Method>   
             | <Attributes> <Modifiers> Delegate <Declare>   
            

! -------------------------------------------------------------------
! Imports
! -------------------------------------------------------------------

<Imports> ::= Imports <Identifier> <NL> 
            | Imports ID '=' <Identifier> <NL>

! -------------------------------------------------------------------
! Events
! -------------------------------------------------------------------

<Event Member> ::= <Attributes> <Modifiers> Event ID <Parameters Or Type> <Implements Opt> <NL>

<Parameters Or Type> ::= <Param List>
                       | As <Identifier> 

<Implements Opt> ::= <Implements>
                   |
                                         
! -------------------------------------------------------------------
! Class
! -------------------------------------------------------------------

<Class>       ::= <Attributes> <Modifiers> Class ID <NL> <Class Items> End Class <NL>


<Class Items> ::= <Class Item> <Class Items>                
                |

<Class Item>  ::= <Declare>
                | <Method>        
                | <Property>   
                | <Var Member>                
                | <Enumeration>
                | <Inherits>
                | <Class Implements>
                
<Inherits> ::= Inherits <Identifier> <NL>
               
<Class Implements> ::= Implements <ID List> <NL>

! -------------------------------------------------------------------
! Structures
! -------------------------------------------------------------------

<Structure>    ::= <Attributes> <Modifiers> Structure ID <NL> <Structure List> End Structure <NL>

<Structure List> ::= <Structure Item> <Structure List>
                   | 

<Structure Item> ::= <Implements>
                   | <Enumeration>
                   | <Structure>
                   | <Class>
                   | <Delegate>   
                   | <Var Member>                    
                   | <Event Member>
                   | <Declare>
                   | <Method>
                   | <Property>

! -------------------------------------------------------------------
! Module
! -------------------------------------------------------------------

<Module>       ::= <Attributes> <Modifiers> Module ID <NL> <Module Items> End Module <NL>

<Module Items> ::= <Module Item> <Module Items>
                 | 
                 
<Module Item>  ::= <Declare>
                 | <Method>                 
                 | <Property>   
                 | <Var Member> 
                 | <Enumeration>
                 | <Option Decl>

! -------------------------------------------------------------------
! Interface
! -------------------------------------------------------------------

<Interface> ::= <Attributes> <Modifiers> Interface ID <NL> <Interface Items> End Interface <NL>


<Interface Items> ::= <Interface Item> <Interface Items>
                    | 
               
<Interface Item>  ::= <Implements>
                    | <Event Member>
                    | <Enum Member>                   
                    | <Method Member>                   
                    | <Property Member>

<Enum Member>     ::= <Attributes> <Modifiers> Enum ID <NL>

<Method Member>   ::= <Attributes> <Modifiers> Sub <Sub ID> <Param List> <Handles Or Implements> <NL>
                    | <Attributes> <Modifiers> Function ID  <Param List> <Type> <Handles Or Implements> <NL> 

<Property Member> ::= <Attributes> <Modifiers> Property ID  <Param List> <Type> <Handles Or Implements> <NL> 
               
               
! -------------------------------------------------------------------
! Parameters
! -------------------------------------------------------------------

<Param List Opt> ::= <Param List>
                   |

<Param List>     ::= '(' <Param Items> ')'
                   | '(' ')'
 
<Param Items>    ::= <Param Item> ',' <Param Items>
                   | <Param Item>

<Param Item>     ::= <Param Passing> ID <Type> 


<Param Passing>  ::= ByVal
                   | ByRef
                   | Optional 
                   | ParamArray
                   |

! -------------------------------------------------------------------
! Arguments 
! -------------------------------------------------------------------

<Argument List Opt> ::= <Argument List>
                      |
                       
<Argument List>  ::= '(' <Argument Items> ')'
              
<Argument Items> ::= <Argument> ',' <Argument Items>
                   | <Argument> 

<Argument>       ::= <Expression>
                   | Id ':=' <Expression>
                   |                          !NULL
                   
                  
! -------------------------------------------------------------------
! Declares (External Procedures)   
! -------------------------------------------------------------------

<Declare> ::= <Attributes> <Modifiers> Declare <Charset> Sub      ID Lib StringLiteral <Alias> <Param List Opt> <NL>
            | <Attributes> <Modifiers> Declare <Charset> Function ID Lib StringLiteral <Alias> <Param List Opt> <Type> <NL>

<Charset> ::= Ansi | Unicode | Auto |  !Null

<Alias> ::= Alias StringLiteral
          |


! -------------------------------------------------------------------
! Methods
! -------------------------------------------------------------------

<Method> ::= <Attributes> <Modifiers> Sub <Sub ID> <Param List>        <Handles Or Implements> <NL> <Statements> End Sub <NL>
           | <Attributes> <Modifiers> Function ID  <Param List> <Type> <Handles Or Implements> <NL> <Statements> End Function <NL>
                
<Sub ID>     ::= ID
               | New     !Class creation

<Handles Or Implements> ::= <Implements> 
                          | <Handles>
                          | 

<Handles>      ::= Handles <ID List>

! -------------------------------------------------------------------
! Properties
! -------------------------------------------------------------------
                 
<Property>   ::= <Attributes> <Modifiers> Property ID <Param List> <Type> <NL> <Property Items> End Property <NL>

<Property Items> ::= <Property Item> <Property Items>          
                   |

<Property Item> ::= Get <NL> <Statements> End Get <NL>
                  | Set <Param List> <NL> <Statements> End Set <NL>


! ------------------------------------------------------------------- 
! Enumerations
! ------------------------------------------------------------------- 

<Enumeration>   ::= <Attributes> <Modifiers> Enum ID <NL> <Enum List> End Enum <NL>

<Enum List>     ::= <Enum Item> <Enum List>
                  | 

<Enum Item>     ::= Id '=' <Expression> <NL>
                  | Id <NL>

! -------------------------------------------------------------------
! Variable Declaration
! -------------------------------------------------------------------

<Var Decl> ::= <Var Decl Item> ',' <Var Decl>
             | <Var Decl Item>
                  
<Var Decl Item>  ::= <Var Decl ID> As <Identifier> <Argument List Opt>             
                   | <Var Decl ID> As <Identifier> '=' <Expression>         !Initialize                                        
                   | <Var Decl ID> As New <Identifier> <Argument List Opt>
                   | <Var Decl ID>
                   | <Var Decl ID> '=' <Expression>                          !Initialize 

<Var Decl ID> ::= ID <Argument List Opt> 
                
! ------------------------------------------------------------------- 
! Normal Statements
! -------------------------------------------------------------------

<Statements>  ::= <Statement> <Statements>
                | 

<Statement>   ::= <Loop Stm>
                | <For Stm>
                | <If Stm>                 
                | <Select Stm> 
                | <SyncLock Stm>
                | <Try Stm>               
                | <With Stm>
                | <Option Decl>                   
                | <Local Decl>    
                | <Non-Block Stm> <NL>       !Note the <NL>. A non-block statement can be a full statement
                | LABEL           <NL>  
                                
                              
<Non-Block Stm> ::= Call <Variable>
                  | ReDim <Var Decl>  
                  | ReDim Preserve <Var Decl>
                  | Erase ID 
     
                  | Throw <Value>                                    
                  | RaiseEvent <Identifier>  <Argument List Opt>
                  | AddHandler <Expression> ',' <Expression>
                  | RemoveHandler  <Expression> ',' <Expression>
    
                  | Exit Do 
                  | Exit For                  
                  | Exit Function            
                  | Exit Property                   
                  | Exit Select      
                  | Exit Sub    
                  | Exit Try
                  | Exit While
                  | GoTo ID                   !Argh - they still have this
                  | Return <Value>           

                  | Error <Value>                      !Raise an error by number
                  | On Error GoTo IntLiteral           ! 0  This is obsolete.   
                  | On Error GoTo '-' IntLiteral       !-1  This is obsolete.
                  | On Error GoTo Id      
                  | On Error Resume Next 
                  | Resume ID 
                  | Resume Next 
                  
                  | <Variable> <Assign Op> <Expression> 
                  | <Variable>       
                  | <Method Call>         

<Assign Op>   ::= '=' | '^=' | '*=' | '/=' | '\=' | '+=' | '-=' | '&=' | '<<=' | '>>='


! ------------------------------------------------------------------- 
! Local declarations
! -------------------------------------------------------------------

<Local Decl>  ::= Dim    <Var Decl>  <NL>
                | Const  <Var Decl>  <NL>
                | Static <Var Decl>  <NL> 

! ------------------------------------------------------------------- 
! Do Statement
! -------------------------------------------------------------------

<Loop Stm>   ::= Do <Test Type> <Expression> <NL> <Statements> Loop <NL>
               | Do <NL> <Statements> Loop <Test Type> <Expression> <NL>                
               | While <Expression> <NL> <Statements> End While <NL>

<Test Type>  ::= While
               | Until                 

! -------------------------------------------------------------------
! For Statement
! -------------------------------------------------------------------

<For Stm>   ::= For <Identifier>  '=' <Expression> To <Expression> <Step Opt> <NL> <Statements> Next <NL>    
              | For Each <Variable> In <Variable> <NL> <Statements> Next <NL>

<Step Opt>  ::= Step <Expression>
              |


! -------------------------------------------------------------------
! If Statement
! -------------------------------------------------------------------

<If Stm>    ::= If <Expression> <Then Opt> <NL> <Statements> <If Blocks> End If <NL> 
              | If <Expression> Then <Non-Block Stm> <NL>
              | If <Expression> Then <Non-Block Stm> Else <Non-Block Stm> <NL>

<Then Opt>  ::= Then         !!The reserved word 'Then' is optional for Block-If statements
              |

<If Blocks> ::= ElseIf <Expression> <Then Opt> <NL> <Statements> <If Blocks>
              | Else <NL> <Statements>
              |

! -------------------------------------------------------------------
! Select Statement
! -------------------------------------------------------------------

<Select Stm>    ::= Select <Case Opt> <Expression> <NL> <Select Blocks> End Select <NL>

<Case Opt>      ::= Case                         !!The "Case" after Select is optional in VB.NEt
                  |


<Select Blocks> ::= Case <Case Clauses> <NL> <Statements>  <Select Blocks>
                  | Case Else <NL> <Statements>  
                  |                 

<Case Clauses>  ::= <Case Clause> ',' <Case Clauses>
                  | <Case Clause> 

<Case Clause>   ::= <Is Opt> <Compare Op> <Expression>
                  | <Expression> 
                  | <Expression> To <Expression>

<Is Opt> ::= Is 
           | !Null

! -------------------------------------------------------------------
! SyncLock Statement
! -------------------------------------------------------------------

<SyncLock Stm> ::= SyncLock <NL> <Statements> End SyncLock <NL>             

! -------------------------------------------------------------------
! Try Statement
! -------------------------------------------------------------------

<Try Stm>      ::= Try <NL> <Statements> <Catch Blocks> End Try <NL>  

<Catch Blocks> ::= <Catch Block> <Catch Blocks>
                 | <Catch Block>

<Catch Block>  ::= Catch <Identifier>  As ID <NL> <Statements> 
                 | Catch <NL> <Statements>

! -------------------------------------------------------------------
! With Statement
! -------------------------------------------------------------------

<With Stm> ::= With <Value> <NL> <Statements> End With <NL>
                  
! -------------------------------------------------------------------
! Expressions
! -------------------------------------------------------------------

<Expression>  ::= <And Exp> Or     <Expression> 
                | <And Exp> OrElse <Expression> 
                | <And Exp> XOr    <Expression> 
                | <And Exp> 

<And Exp>     ::= <Not Exp> And     <And Exp> 
                | <Not Exp> AndAlso <And Exp> 
                | <Not Exp> 
 
<Not Exp>     ::= NOT <Compare Exp>
                | <Compare Exp>

<Compare Exp> ::= <Shift Exp> <Compare Op> <Compare Exp>       !e.g.  x < y
                | TypeOf <Add Exp> Is <Object>
                | <Shift Exp> Is <Object>
                | <Shift Exp> Like <Value>
                | <Shift Exp>

<Shift Exp>   ::= <Concat Exp> '<<' <Shift Exp>  
                | <Concat Exp> '>>' <Shift Exp>  
                | <Concat Exp> 

<Concat Exp>  ::= <Add Exp> '&' <Concat Exp>
                | <Add Exp>

<Add Exp>     ::= <Modulus Exp> '+' <Add Exp> 
                | <Modulus Exp> '-' <Add Exp> 
                | <Modulus Exp>  

<Modulus Exp> ::= <Int Div Exp> Mod <Modulus Exp> 
                | <Int Div Exp>

<Int Div Exp> ::= <Mult Exp> '\' <Int Div Exp>                 
                | <Mult Exp>

<Mult Exp>    ::= <Negate Exp> '*' <Mult Exp> 
                | <Negate Exp> '/' <Mult Exp> 
                | <Negate Exp> 

<Negate Exp>  ::= '-' <Power Exp> 
                | <Power Exp> 

<Power Exp>   ::= <Power Exp> '^' <Value> 
                | <Value> 

<Value>       ::= '(' <Expression> ')'                
                | New <Identifier> <Argument List Opt>
                | IntLiteral 
                | HexLiteral
                | OctLiteral
                | StringLiteral 
                | CharLiteral
                | RealLiteral
                | DateLiteral 
                | True
                | False
                | Me 
                | MyClass 
                | MyBase
                | Nothing
                | <Variable>
                | AddressOf <Identifier>

<Object>      ::= <Identifier>        !Object identifiers 
                | Me 
                | MyClass 
                | MyBase
                | Nothing

<Variable>    ::= <Identifier> <Argument List Opt> <Method Calls> 
                                
<Method Calls> ::= <Method Call> <Method Calls>
                 | 

<Method Call>  ::= MemberID <Argument List Opt>                    


<Identifier>   ::= ID | QualifiedID       !Any type of identifier