using System.Drawing;
using System.Collections;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.Text;
using ICSharpCode.NRefactory.Parser.AST;
using ICSharpCode.NRefactory.Parser.VB;
using ASTAttribute = ICSharpCode.NRefactory.Parser.AST.Attribute;

COMPILER VBNET

private string assemblyName = null;
private Stack withStatements;
private StringBuilder qualidentBuilder = new StringBuilder();

public string ContainingAssembly
{
	set { assemblyName = value; }
}
Token t
{
	get {
		return lexer.Token;
	}
}
Token la
{
	get {
		return lexer.LookAhead;
	}
}

/* Return the n-th token after the current lookahead token */
void StartPeek()
{
	lexer.StartPeek();
}

Token Peek()
{
	return lexer.Peek();
}

Token Peek (int n)
{
	lexer.StartPeek();
	Token x = la;
	while (n > 0) {
		x = lexer.Peek();
		n--;
	}
	return x;
}

public void Error(string s)
{
	if (errDist >= minErrDist) {
		errors.Error(la.line, la.col, s);
	}
	errDist = 0;
}

public override Expression ParseExpression()
{
	lexer.NextToken();
	Expression expr;
	Expr(out expr);
	return expr;
}

bool LeaveBlock()
{
  int peek = Peek(1).kind;
  return Tokens.BlockSucc[la.kind] && (la.kind != Tokens.End || peek == Tokens.EOL || peek == Tokens.Colon);
}

/* True, if "." is followed by an ident */
bool DotAndIdentOrKw () {
	int peek = Peek(1).kind;
	return la.kind == Tokens.Dot && (peek == Tokens.Identifier || peek >= Tokens.AddHandler);
}

bool IsEndStmtAhead()
{
	int peek = Peek(1).kind;
	return la.kind == Tokens.End && (peek == Tokens.EOL || peek == Tokens.Colon);
}

bool IsNotClosingParenthesis() {
	return la.kind != Tokens.CloseParenthesis;
}

/*
	True, if ident is followed by "="
*/
bool IdentAndAsgn () {
	if(la.kind == Tokens.Identifier) {
		if(Peek(1).kind == Tokens.Assign) return true;
		if(Peek(1).kind == Tokens.Colon && Peek(2).kind == Tokens.Assign) return true;
	}
	return false;
}

/*
	True, if ident is followed by "=" or by ":" and "="
*/
bool IsNamedAssign() {
//	if(Peek(1).kind == Tokens.Assign) return true; // removed: not in the lang spec
	if(Peek(1).kind == Tokens.Colon && Peek(2).kind == Tokens.Assign) return true;
	return false;
}

bool IsObjectCreation() {
	return la.kind == Tokens.As && Peek(1).kind == Tokens.New;
}

/*
	True, if "<" is followed by the ident "assembly" or "module"
*/
bool IsGlobalAttrTarget () {
	Token pt = Peek(1);
	return la.kind == Tokens.LessThan && ( string.Equals(pt.val, "assembly", StringComparison.InvariantCultureIgnoreCase) || string.Equals(pt.val, "module", StringComparison.InvariantCultureIgnoreCase));
}

/*
	True if the next token is a "(" and is followed by "," or ")"
*/
bool IsDims()
{
	int peek = Peek(1).kind;
	return la.kind == Tokens.OpenParenthesis
						&& (peek == Tokens.Comma || peek == Tokens.CloseParenthesis);
}

bool IsSize()
{
	return la.kind == Tokens.OpenParenthesis;
}

/*
	True, if the comma is not a trailing one,
	like the last one in: a, b, c,
*/
bool NotFinalComma() {
	int peek = Peek(1).kind;
	return la.kind == Tokens.Comma &&
		   peek != Tokens.CloseCurlyBrace;
}

/*
	True, if the next token is "Else" and this one
	if followed by "If"
*/
bool IsElseIf()
{
	int peek = Peek(1).kind;
	return la.kind == Tokens.Else && peek == Tokens.If;
}

/*
	True if the next token is goto and this one is
	followed by minus ("-") (this is allowd in in
	error clauses)
*/
bool IsNegativeLabelName()
{
	int peek = Peek(1).kind;
	return la.kind == Tokens.GoTo && peek == Tokens.Minus;
}

/*
	True if the next statement is a "Resume next" statement
*/
bool IsResumeNext()
{
	int peek = Peek(1).kind;
	return la.kind == Tokens.Resume && peek == Tokens.Next;
}

/*
	True, if ident/literal integer is followed by ":"
*/
bool IsLabel()
{
	return (la.kind == Tokens.Identifier || la.kind == Tokens.LiteralInteger)
			&& Peek(1).kind == Tokens.Colon;
}

bool IsNotStatementSeparator()
{
	return la.kind == Tokens.Colon && Peek(1).kind == Tokens.EOL;
}

bool IsAssignment ()
{
	return IdentAndAsgn();
}

bool IsMustOverride(Modifiers m)
{
	return m.Contains(Modifier.Abstract);
}

TypeReferenceExpression GetTypeReferenceExpression(Expression expr, List<TypeReference> genericTypes)
{
	TypeReferenceExpression	tre = expr as TypeReferenceExpression;
	if (tre != null) {
		return new TypeReferenceExpression(new TypeReference(tre.TypeReference.Type, tre.TypeReference.PointerNestingLevel, tre.TypeReference.RankSpecifier, genericTypes));
	}
	StringBuilder b = new StringBuilder();
	if (!WriteFullTypeName(b, expr)) {
		// there is some TypeReferenceExpression hidden in the expression
		while (expr is FieldReferenceExpression) {
			expr = ((FieldReferenceExpression)expr).TargetObject;
		}
		tre = expr as TypeReferenceExpression;
		if (tre != null) {
			TypeReference typeRef = tre.TypeReference;
			if (typeRef.GenericTypes.Count == 0) {
				typeRef = typeRef.Clone();
				typeRef.Type += "." + b.ToString();
				typeRef.GenericTypes.AddRange(genericTypes);
			} else {
				typeRef = new InnerClassTypeReference(typeRef, b.ToString(), genericTypes);
			}
			return new TypeReferenceExpression(typeRef);
		}
	}
	return new TypeReferenceExpression(new TypeReference(b.ToString(), 0, null, genericTypes));
}

/* Writes the type name represented through the expression into the string builder. */
/* Returns true when the expression was converted successfully, returns false when */
/* There was an unknown expression (e.g. TypeReferenceExpression) in it */
bool WriteFullTypeName(StringBuilder b, Expression expr)
{
	FieldReferenceExpression fre = expr as FieldReferenceExpression;
	if (fre != null) {
		bool result = WriteFullTypeName(b, fre.TargetObject);
		if (b.Length > 0) b.Append('.');
		b.Append(fre.FieldName);
		return result;
	} else if (expr is IdentifierExpression) {
		b.Append(((IdentifierExpression)expr).Identifier);
		return true;
	} else {
		return false;
	}
}

/*
	True, if lookahead is a local attribute target specifier,
	i.e. one of "event", "return", "field", "method",
	"module", "param", "property", or "type"
*/
bool IsLocalAttrTarget() {
	// TODO
	return false;
}

/* START AUTOGENERATED TOKENS SECTION */
TOKENS
	/* ----- terminal classes ----- */
	/* EOF is 0 */
	EOL
	ident
	LiteralString
	LiteralCharacter
	LiteralInteger
	LiteralDouble
	LiteralSingle
	LiteralDecimal
	LiteralDate

	/* ----- special character ----- */
	"."
	"="
	","
	":"
	"+"
	"-"
	"*"
	"/"
	"\\"
	"&"
	"^"
	"?"
	"{"
	"}"
	"("
	")"
	">"
	"<"
	"<>"
	">="
	"<="
	"<<"
	">>"
	"+="
	"^="
	"-="
	"*="
	"/="
	"\\="
	"<<="
	">>="
	"&="

	/* ----- keywords ----- */
	"AddHandler"
	"AddressOf"
	"Alias"
	"And"
	"AndAlso"
	"Ansi"
	"As"
	"Assembly"
	"Auto"
	"Binary"
	"Boolean"
	"ByRef"
	"Byte"
	"ByVal"
	"Call"
	"Case"
	"Catch"
	"CBool"
	"CByte"
	"CChar"
	"CDate"
	"CDbl"
	"CDec"
	"Char"
	"CInt"
	"Class"
	"CLng"
	"CObj"
	"Compare"
	"Const"
	"CShort"
	"CSng"
	"CStr"
	"CType"
	"Date"
	"Decimal"
	"Declare"
	"Default"
	"Delegate"
	"Dim"
	"DirectCast"
	"Do"
	"Double"
	"Each"
	"Else"
	"ElseIf"
	"End"
	"EndIf"
	"Enum"
	"Erase"
	"Error"
	"Event"
	"Exit"
	"Explicit"
	"False"
	"Finally"
	"For"
	"Friend"
	"Function"
	"Get"
	"GetType"
	"GoSub"
	"GoTo"
	"Handles"
	"If"
	"Implements"
	"Imports"
	"In"
	"Inherits"
	"Integer"
	"Interface"
	"Is"
	"Let"
	"Lib"
	"Like"
	"Long"
	"Loop"
	"Me"
	"Mod"
	"Module"
	"MustInherit"
	"MustOverride"
	"MyBase"
	"MyClass"
	"Namespace"
	"New"
	"Next"
	"Not"
	"Nothing"
	"NotInheritable"
	"NotOverridable"
	"Object"
	"Off"
	"On"
	"Option"
	"Optional"
	"Or"
	"OrElse"
	"Overloads"
	"Overridable"
	"Overrides"
	"ParamArray"
	"Preserve"
	"Private"
	"Property"
	"Protected"
	"Public"
	"RaiseEvent"
	"ReadOnly"
	"ReDim"
	"RemoveHandler"
	"Resume"
	"Return"
	"Select"
	"Set"
	"Shadows"
	"Shared"
	"Short"
	"Single"
	"Static"
	"Step"
	"Stop"
	"Strict"
	"String"
	"Structure"
	"Sub"
	"SyncLock"
	"Text"
	"Then"
	"Throw"
	"To"
	"True"
	"Try"
	"TypeOf"
	"Unicode"
	"Until"
	"Variant"
	"Wend"
	"When"
	"While"
	"With"
	"WithEvents"
	"WriteOnly"
	"Xor"
	"Continue"
	"Operator"
	"Using"
	"IsNot"
	"SByte"
	"UInteger"
	"ULong"
	"UShort"
	"CSByte"
	"CUShort"
	"CUInt"
	"CULng"
	"Global"
	"TryCast"
	"Of"
	"Narrowing"
	"Widening"
	"Partial"
	"Custom"
/* END AUTOGENERATED TOKENS SECTION */


PRODUCTIONS

VBNET
	(.
		lexer.NextToken(); // get the first token
		compilationUnit = new CompilationUnit();
		withStatements = new Stack();
	.) =
	{ EOL }
	{ OptionStmt }
	{ ImportsStmt}
	{ IF (IsGlobalAttrTarget()) GlobalAttributeSection }
	{ NamespaceMemberDecl }
	EOF
	.

OptionStmt (. INode node = null; bool val = true; .) =
	"Option" (. Point startPos = t.Location; .)
	(
		"Explicit" [ OptionValue<ref val> ]
		(. node = new OptionDeclaration(OptionType.Explicit, val); .)
		|
		"Strict" [ OptionValue<ref val> ]
		(. node = new OptionDeclaration(OptionType.Strict, val); .)
		|
		"Compare" ( "Binary" (. node = new OptionDeclaration(OptionType.CompareBinary, val); .)
				  | "Text" (. node = new OptionDeclaration(OptionType.CompareText, val); .)
				  )
	)
	EndOfStmt
	(.
		if (node != null) {
			node.StartLocation = startPos;
			node.EndLocation   = t.Location;
			compilationUnit.AddChild(node);
		}
	.)
	.

OptionValue<ref bool val> =
	(
		"On" (. val = true; .)
	|
		"Off" (. val = false; .)
	)
	.

EndOfStmt =
		EOL
	|
		":" [ EOL ]
	.

ImportsStmt
	(.List<Using> usings = new List<Using>();
	.) =
	"Imports"
	(.
		Point startPos = t.Location;
		Using u;
	.)
	ImportClause<out u> (. usings.Add(u); .)
	{
		"," ImportClause<out u> (. usings.Add(u); .)
	}
	EndOfStmt
	(.
		UsingDeclaration usingDeclaration = new UsingDeclaration(usings);
		usingDeclaration.StartLocation = startPos;
		usingDeclaration.EndLocation   = t.Location;
		compilationUnit.AddChild(usingDeclaration);
	.)
	.

ImportClause<out Using u>
	(.
		string qualident  = null;
		TypeReference aliasedType = null;
		u = null;
	.) =
	Qualident<out qualident>
	[ "=" TypeName<out aliasedType> ]
	(.
		if (qualident != null && qualident.Length > 0) {
			if (aliasedType != null) {
				u = new Using(qualident, aliasedType);
			} else {
				u = new Using(qualident);
			}
		}
	.)
	.

/* 6.4.2 */
NamespaceMemberDecl
	(.
		Modifiers m = new Modifiers();
		AttributeSection section;
		List<AttributeSection> attributes = new List<AttributeSection>();
		string qualident;
	.) =
	"Namespace"
	(.
		Point startPos = t.Location;
	.)
	Qualident<out qualident>
	(.
		INode node =  new NamespaceDeclaration(qualident);
		node.StartLocation = startPos;
		compilationUnit.AddChild(node);
		compilationUnit.BlockStart(node);
	.)
	EOL
	NamespaceBody
	(.
		node.EndLocation = t.Location;
		compilationUnit.BlockEnd();
	.)
	|
	{ AttributeSection<out section> (. attributes.Add(section); .) }
	{ TypeModifier<m> } NonModuleDeclaration<m, attributes>
	.

/* 4.9.1 */
TypeParameterList<List<TemplateDefinition> templates>
(.
	TemplateDefinition template;
.) =
	[
		IF (la.kind == Tokens.OpenParenthesis && Peek(1).kind == Tokens.Of)
		"(" "Of" TypeParameter<out template>
		(.
			if (template != null) templates.Add(template);
		.)
		{
			"," TypeParameter<out template>
			(.
				if (template != null) templates.Add(template);
			.)
		}
		")"
	]
.

/* 4.9.1 */
TypeParameter<out TemplateDefinition template>
=
	Identifier (. template = new TemplateDefinition(t.val, null); .)
	[TypeParameterConstraints<template>]
.

/* 4.9.2 */
TypeParameterConstraints<TemplateDefinition template>
(.
	TypeReference constraint;
.)
=
	"As"
	(
		"{"
		TypeName<out constraint> (. if (constraint != null) { template.Bases.Add(constraint); } .)
		{
			","
			TypeName<out constraint> (. if (constraint != null) { template.Bases.Add(constraint); } .)
		}
		"}"
		| TypeName<out constraint> (. if (constraint != null) { template.Bases.Add(constraint); } .)
	)
.

/* 6.4.2 */
NonModuleDeclaration<Modifiers m, List<AttributeSection> attributes>
			(.
				TypeReference typeRef = null;
				List<TypeReference> baseInterfaces = null;
			.) =
	(. m.Check(Modifier.Classes); .)
	/* Spec, 7.5 */
	"Class"
					(. TypeDeclaration newType = new TypeDeclaration(m.Modifier, attributes);
						newType.StartLocation = t.Location;
						compilationUnit.AddChild(newType);
						compilationUnit.BlockStart(newType);
						
						newType.Type       = ClassType.Class;
					.)
	Identifier			 (. newType.Name = t.val; .) 
	TypeParameterList<newType.Templates>
	EndOfStmt
	[ ClassBaseType<out typeRef> (. newType.BaseTypes.Add(typeRef); .) ]
	{ TypeImplementsClause<out baseInterfaces> (. newType.BaseTypes.AddRange(baseInterfaces); .) }
	ClassBody<newType>
	(.
		compilationUnit.BlockEnd();
	.)
	| "Module"
		(.
			m.Check(Modifier.VBModules);
			TypeDeclaration newType = new TypeDeclaration(m.Modifier, attributes);
			compilationUnit.AddChild(newType);
			compilationUnit.BlockStart(newType);
			newType.StartLocation = m.GetDeclarationLocation(t.Location);
			newType.Type = ClassType.Module;
		.)
	Identifier			 (. newType.Name = t.val; .)
	EOL
	ModuleBody<newType>
	(.
		compilationUnit.BlockEnd();
	.)
	| "Structure"
		(.
			m.Check(Modifier.VBStructures);
			TypeDeclaration newType = new TypeDeclaration(m.Modifier, attributes);
			compilationUnit.AddChild(newType);
			compilationUnit.BlockStart(newType);
			newType.StartLocation = m.GetDeclarationLocation(t.Location);
			newType.Type = ClassType.Struct;
		.)
	Identifier			 (. newType.Name = t.val; .) 
	TypeParameterList<newType.Templates>
	EOL { TypeImplementsClause<out baseInterfaces> (. newType.BaseTypes.AddRange(baseInterfaces);.) }
	StructureBody<newType>
	(.
		compilationUnit.BlockEnd();
	.)
	| /* 7.4 */
	"Enum"
		(.
			m.Check(Modifier.VBEnums);
			TypeDeclaration newType = new TypeDeclaration(m.Modifier, attributes);
			newType.StartLocation = m.GetDeclarationLocation(t.Location);
			compilationUnit.AddChild(newType);
			compilationUnit.BlockStart(newType);
			
			newType.Type = ClassType.Enum;
		.)
	Identifier			 (. newType.Name = t.val; .) 
	[ "As" NonArrayTypeName<out typeRef, false> (. newType.BaseTypes.Add(typeRef); .) ]
	EOL
	EnumBody<newType>
	(.
		compilationUnit.BlockEnd();
	.)
	| /* 7.8 */
	"Interface"
		(.
			m.Check(Modifier.VBInterfacs);
			TypeDeclaration newType = new TypeDeclaration(m.Modifier, attributes);
			newType.StartLocation = m.GetDeclarationLocation(t.Location);
			compilationUnit.AddChild(newType);
			compilationUnit.BlockStart(newType);
			newType.Type = ClassType.Interface;
		.)
	Identifier			 (. newType.Name = t.val; .) 
	TypeParameterList<newType.Templates>
	EndOfStmt { InterfaceBase<out baseInterfaces> (. newType.BaseTypes.AddRange(baseInterfaces); .) }
	InterfaceBody<newType>
	(.
		compilationUnit.BlockEnd();
	.)
	| /* 7.10 */
	"Delegate"
	(.
		m.Check(Modifier.VBDelegates);
		DelegateDeclaration delegateDeclr = new DelegateDeclaration(m.Modifier, attributes);
		delegateDeclr.ReturnType = new TypeReference("", "System.Void");
		delegateDeclr.StartLocation = m.GetDeclarationLocation(t.Location);
		List<ParameterDeclarationExpression> p = new List<ParameterDeclarationExpression>();
	.)
	(
		"Sub" Identifier (. delegateDeclr.Name = t.val; .)
		TypeParameterList<delegateDeclr.Templates>
		[ "(" [ FormalParameterList<p> ] ")" (. delegateDeclr.Parameters = p; .) ]
		|
		"Function" Identifier (. delegateDeclr.Name = t.val; .)
		TypeParameterList<delegateDeclr.Templates>
		[ "(" [ FormalParameterList<p> ] ")" (. delegateDeclr.Parameters = p; .) ]
		[ "As" (. TypeReference type; .) TypeName<out type> (. delegateDeclr.ReturnType = type; .)]
	)
	(. 		delegateDeclr.EndLocation = t.EndLocation; .)
	EOL
	(.
		compilationUnit.AddChild(delegateDeclr);
	.)
	.

NamespaceBody =
	{ NamespaceMemberDecl }
	"End" "Namespace"
	EOL
	.

ClassBody<TypeDeclaration newType>
	(. AttributeSection section; .) =
	{
		(.List<AttributeSection> attributes = new List<AttributeSection>();
			Modifiers m = new Modifiers();
		.)
		{ AttributeSection<out section> (. attributes.Add(section); .) }
		{ MemberModifier<m> }
		ClassMemberDecl<m, attributes>
	}
	"End" "Class" (. newType.EndLocation = t.EndLocation; .)
	EOL
	.

StructureBody<TypeDeclaration newType>
	(. AttributeSection section; .) =
	{
		(.List<AttributeSection> attributes = new List<AttributeSection>();
			Modifiers m = new Modifiers();
		.)
		{ AttributeSection<out section> (. attributes.Add(section); .) }
		{ MemberModifier<m> }
		StructureMemberDecl<m, attributes>
	}
	"End" "Structure" (. newType.EndLocation = t.EndLocation; .)
	EOL
	.

/* 7.7.1 */
ModuleBody<TypeDeclaration newType>
	(. AttributeSection section; .) =
	{
		(.List<AttributeSection> attributes = new List<AttributeSection>();
			Modifiers m = new Modifiers();
		.)
		{ AttributeSection<out section> (. attributes.Add(section); .) }
		{ MemberModifier<m> }
		ClassMemberDecl<m, attributes>
	}
	"End" "Module" (. newType.EndLocation = t.EndLocation; .)
	EOL
	.

EnumBody<TypeDeclaration newType>
	(. FieldDeclaration f; .) =
	{
		EnumMemberDecl<out f> (. compilationUnit.AddChild(f); .)
	}
	"End" "Enum" (. newType.EndLocation = t.EndLocation; .)
	EOL
	.

InterfaceBody<TypeDeclaration newType> =
	{ InterfaceMemberDecl }
	"End" "Interface" (. newType.EndLocation = t.EndLocation; .)
	EOL
	.

/* The information provided in the spec about */
/* interface declarations is wrong */
InterfaceMemberDecl
	(.
		TypeReference type =null;
		List<ParameterDeclarationExpression> p = new List<ParameterDeclarationExpression>();
		List<TemplateDefinition> templates = new List<TemplateDefinition>();
		AttributeSection section, returnTypeAttributeSection = null;
		Modifiers mod = new Modifiers();
		List<AttributeSection> attributes = new List<AttributeSection>();
		string name;
	.) =
	{ AttributeSection<out section>			(. attributes.Add(section); .) }
	/* this is different to c#: not only the Shadows modifier is allowed, */
	/*  also member modifiers like overloads etc. */
	{ MemberModifier<mod> }
	(
		"Event"
		(. mod.Check(Modifier.VBInterfaceEvents); .)
		Identifier (. name = t.val; .)
		[ "(" [ FormalParameterList<p> ] ")" ]
		[ "As" TypeName<out type> ]
		EOL
		(.
			EventDeclaration ed = new EventDeclaration(type, mod.Modifier, p, attributes, name, null);
			compilationUnit.AddChild(ed);
			ed.EndLocation = t.EndLocation;
		.)
		|
		"Sub"
		(. mod.Check(Modifier.VBInterfaceMethods); .)
		Identifier (. name = t.val; .)
		TypeParameterList<templates>
		[ "(" [ FormalParameterList<p> ] ")" ]
		EOL
		(.
			MethodDeclaration md = new MethodDeclaration(name, mod.Modifier, null, p, attributes);
			md.TypeReference = new TypeReference("", "System.Void");
			md.EndLocation = t.EndLocation;
			md.Templates = templates;
			compilationUnit.AddChild(md);
		.)
		|
		"Function"
		(. mod.Check(Modifier.VBInterfaceMethods); .)
		Identifier (. name = t.val; .)
		TypeParameterList<templates>
		[ "(" [ FormalParameterList<p> ] ")" ]
		[ "As" { AttributeSection<out returnTypeAttributeSection> } TypeName<out type> ]
		(.
			if(type == null) {
				type = new TypeReference("System.Object");
			}
			MethodDeclaration md = new MethodDeclaration(name, mod.Modifier, type, p, attributes);
			md.ReturnTypeAttributeSection = returnTypeAttributeSection;
			md.EndLocation = t.EndLocation;
			md.Templates = templates;
			compilationUnit.AddChild(md);
		.)
		EOL
		|
		"Property"
		(. mod.Check(Modifier.VBInterfaceProperties); .)
		Identifier	(. name = t.val;  .)
		[ "(" [ FormalParameterList<p> ] ")" ]
		[ "As" TypeName<out type> ]
		(.
			if(type == null) {
				type = new TypeReference("System.Object");
			}
		.)
		EOL
		(.
			PropertyDeclaration pd = new PropertyDeclaration(name, type, mod.Modifier, attributes);
			pd.Parameters = p;
			pd.EndLocation = t.EndLocation;
			compilationUnit.AddChild(pd);
		.)
	)
	| /* inner type declarations */
	NonModuleDeclaration<mod, attributes>
	.

/* 7.4.1 */
EnumMemberDecl<out FieldDeclaration f>
	(.
		Expression expr = null;List<AttributeSection> attributes = new List<AttributeSection>();
		AttributeSection section = null;
		VariableDeclaration varDecl = null;
	.) =
	{ AttributeSection<out section> (. attributes.Add(section); .) }
	Identifier
	(.
		f = new FieldDeclaration(attributes);
		varDecl = new VariableDeclaration(t.val);
		f.Fields.Add(varDecl);
		f.StartLocation = t.Location;
	.)
	[ "=" Expr<out expr> (. varDecl.Initializer = expr; .) ]
	EOL
	.

ClassMemberDecl<Modifiers m, List<AttributeSection> attributes> =
	StructureMemberDecl<m, attributes>
	.

ClassBaseType<out TypeReference typeRef>
(.
	typeRef = null;
.) =
	"Inherits"
	TypeName<out typeRef>
	EndOfStmt
.

/* 7.6.1 */
StructureMemberDecl<Modifiers m, List<AttributeSection> attributes>
	(.
		TypeReference type = null;
		List<ParameterDeclarationExpression> p = new List<ParameterDeclarationExpression>();
		Statement stmt = null;
		List<VariableDeclaration> variableDeclarators = new List<VariableDeclaration>();
		List<TemplateDefinition> templates = new List<TemplateDefinition>();
	.)=
	NonModuleDeclaration<m, attributes>
	| /* 9.2.1 */
	"Sub"
	(.
		Point startPos = t.Location;
	.)
	(
		(.
			string name = String.Empty;
			MethodDeclaration methodDeclaration; ArrayList handlesClause = null;
			List<InterfaceImplementation> implementsClause = null;
		.)
		Identifier
		(.
			name = t.val;
			m.Check(Modifier.VBMethods);
		.)
		TypeParameterList<templates>
		[ "(" [ FormalParameterList<p> ] ")" ]
		[
			(
				ImplementsClause<out implementsClause>
				|
				HandlesClause<out handlesClause>
			)
		]
		(. Point endLocation = t.EndLocation; .)
		EOL
		(
			/* abstract methods without a body */
			IF(IsMustOverride(m))
			(.
				methodDeclaration = new MethodDeclaration(name, m.Modifier,  null, p, attributes);
				methodDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				methodDeclaration.EndLocation   = endLocation;
				methodDeclaration.TypeReference = new TypeReference("", "System.Void");
				
				methodDeclaration.Templates = templates;
				methodDeclaration.HandlesClause = handlesClause;
				methodDeclaration.InterfaceImplementations = implementsClause;
				
				compilationUnit.AddChild(methodDeclaration);
			.)
		|
			(.
				methodDeclaration = new MethodDeclaration(name, m.Modifier,  null, p, attributes);
				methodDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				methodDeclaration.EndLocation   = endLocation;
				methodDeclaration.TypeReference = new TypeReference("", "System.Void");
				
				methodDeclaration.Templates = templates;
				methodDeclaration.HandlesClause = handlesClause;
				methodDeclaration.InterfaceImplementations = implementsClause;
				
				compilationUnit.AddChild(methodDeclaration);
				compilationUnit.BlockStart(methodDeclaration);
			.)
			Block<out stmt>
			(.
				compilationUnit.BlockEnd();
				methodDeclaration.Body  = (BlockStatement)stmt;
			.)
			"End" "Sub" (. methodDeclaration.Body.EndLocation = t.EndLocation; .) EOL 
		)
		/* 9.3 */
		| "New" [ "(" [ FormalParameterList<p> ] ")" ]
		(. m.Check(Modifier.Constructors); .)
		(. Point constructorEndLocation = t.EndLocation; .)
		EOL
		Block<out stmt>
		"End" "Sub" (. Point endLocation = t.EndLocation; .) EOL
		(.
			ConstructorDeclaration cd = new ConstructorDeclaration("New", m.Modifier, p, attributes); 
			cd.StartLocation = m.GetDeclarationLocation(startPos);
			cd.EndLocation   = constructorEndLocation;
			cd.Body = (BlockStatement)stmt;
			cd.Body.EndLocation   = endLocation;
			compilationUnit.AddChild(cd);
		.)
	)
	|
	/* 9.2.1 */
	"Function"
	(.
		m.Check(Modifier.VBMethods);
		string name = String.Empty;
		Point startPos = t.Location;
		MethodDeclaration methodDeclaration;ArrayList handlesClause = null;
		List<InterfaceImplementation> implementsClause = null;
		AttributeSection returnTypeAttributeSection = null;
	.)
	Identifier			(. name = t.val; .)
	TypeParameterList<templates>
	[ "("	[ FormalParameterList<p> ] ")" ]
	["As"  { AttributeSection<out returnTypeAttributeSection> } TypeName<out type> ]
	(.
		if(type == null) {
			type = new TypeReference("System.Object");
		}
	.)
	[
		(
			ImplementsClause<out implementsClause>
			|
			HandlesClause<out handlesClause>
		)
	]
	EOL
	(
		/* abstract methods without a body */
		IF(IsMustOverride(m))
			(.
				methodDeclaration = new MethodDeclaration(name, m.Modifier,  type, p, attributes);
				methodDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				methodDeclaration.EndLocation   = t.EndLocation;
				
				methodDeclaration.HandlesClause = handlesClause;
				methodDeclaration.Templates     = templates;
				methodDeclaration.InterfaceImplementations = implementsClause;
				methodDeclaration.ReturnTypeAttributeSection = returnTypeAttributeSection;
				compilationUnit.AddChild(methodDeclaration);
			.)
		|
			(.
				methodDeclaration = new MethodDeclaration(name, m.Modifier,  type, p, attributes);
				methodDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				methodDeclaration.EndLocation   = t.EndLocation;
				
				methodDeclaration.Templates     = templates;
				methodDeclaration.HandlesClause = handlesClause;
				methodDeclaration.InterfaceImplementations = implementsClause;
				methodDeclaration.ReturnTypeAttributeSection = returnTypeAttributeSection;
				
				compilationUnit.AddChild(methodDeclaration);
				compilationUnit.BlockStart(methodDeclaration);
			.)
			Block<out stmt>
			(.
				compilationUnit.BlockEnd();
				methodDeclaration.Body  = (BlockStatement)stmt;
			.)
			"End" "Function" 
			(.
				methodDeclaration.Body.StartLocation = methodDeclaration.EndLocation;
				methodDeclaration.Body.EndLocation   = t.EndLocation;
			.)
			EOL
	)
	|
	/* 9.2.2. */
	"Declare"
	(.
		m.Check(Modifier.VBExternalMethods);
		Point startPos = t.Location;
		CharsetModifier charsetModifer = CharsetModifier.None;
		string library = String.Empty;
		string alias = null;
		string name = String.Empty;
	.)
	[Charset<out charsetModifer> ]
	(
			"Sub"
			Identifier				(. name = t.val; .)
			"Lib" LiteralString		(. library = t.val.ToString(); .)
			["Alias" LiteralString	(. alias = t.val.ToString(); .)]
			[ "("	[ FormalParameterList<p> ] ")" ]
			EOL
			(.
				DeclareDeclaration declareDeclaration = new DeclareDeclaration(name, m.Modifier, null, p, attributes, library, alias, charsetModifer);
				declareDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				declareDeclaration.EndLocation   = t.EndLocation;
				compilationUnit.AddChild(declareDeclaration);
			.)
		|
			"Function" 
			Identifier					(. name = t.val; .)
			"Lib" LiteralString		(. library = t.val; .)
			["Alias" LiteralString	(. alias = t.val; .)]
			[ "("	[ FormalParameterList<p> ] ")" ]
			["As" TypeName<out type> ]
			EOL
			(.
				DeclareDeclaration declareDeclaration = new DeclareDeclaration(name, m.Modifier, type, p, attributes, library, alias, charsetModifer);
				declareDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
				declareDeclaration.EndLocation   = t.EndLocation;
				compilationUnit.AddChild(declareDeclaration);
			.)
		)
	|
	/* 9. 4 */
	"Event"
	(.
		m.Check(Modifier.VBEvents);
		Point startPos = t.Location;
		EventDeclaration eventDeclaration;
		string name = String.Empty;
		List<InterfaceImplementation> implementsClause = null;
	.)
	Identifier (. name= t.val; .)
	(
		"As" TypeName<out type>
		|
		[ "("	[ FormalParameterList<p> ] ")" ]
	)
	[ ImplementsClause<out implementsClause> ]
	(.
		eventDeclaration = new EventDeclaration(type, m.Modifier, p, attributes, name, implementsClause);
		eventDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
		eventDeclaration.EndLocation = t.EndLocation;
		compilationUnit.AddChild(eventDeclaration);
	.)
	EOL
	| /* 9.6 */
	(. Point startPos = t.Location; .)
	(.
		m.Check(Modifier.Fields);
		FieldDeclaration fd = new FieldDeclaration(attributes, type, m.Modifier);
		fd.StartLocation = m.GetDeclarationLocation(startPos); 
	.)
	VariableDeclarator<variableDeclarators>
	{ "," VariableDeclarator<variableDeclarators> }
	EOL
	(.
		fd.EndLocation = t.EndLocation;
		fd.Fields = variableDeclarators;
		compilationUnit.AddChild(fd);
	.)
	| /* 9.4 */
	(. m.Check(Modifier.Fields); .)
	"Const" (.  m.Add(Modifier.Const, t.Location);  .)
	(.
		FieldDeclaration fd = new FieldDeclaration(attributes, type, m.Modifier);
		fd.StartLocation = m.GetDeclarationLocation(t.Location);
		List<VariableDeclaration> constantDeclarators = new List<VariableDeclaration>();
	.)
	ConstantDeclarator<constantDeclarators>
	{ "," ConstantDeclarator<constantDeclarators> }
	(.
		fd.Fields = constantDeclarators;
		fd.EndLocation = t.Location;
	.)
	EOL
	(.
		fd.EndLocation = t.EndLocation;
		compilationUnit.AddChild(fd);
	.)
	| /* 9.7 */
	"Property"
	(.
		m.Check(Modifier.VBProperties);
		Point startPos = t.Location;
		List<InterfaceImplementation> implementsClause = null;
	.)
	Identifier (. string propertyName = t.val; .)
	[ "("	[ FormalParameterList<p> ] ")" ]
	[ "As" TypeName<out type> ]
	(.
		if(type == null) {
			type = new TypeReference("System.Object");
		}
	.)
	[ ImplementsClause<out implementsClause> ]
	EOL
	(
	/* abstract properties without a body */
	IF(IsMustOverride(m))
		(.
			PropertyDeclaration pDecl = new PropertyDeclaration(propertyName, type, m.Modifier, attributes);
			pDecl.StartLocation = m.GetDeclarationLocation(startPos);
			pDecl.EndLocation   = t.Location;
			pDecl.TypeReference = type;
			pDecl.InterfaceImplementations = implementsClause;
			pDecl.Parameters = p;
			compilationUnit.AddChild(pDecl);
		.)
	|
		(.
			PropertyDeclaration pDecl = new PropertyDeclaration(propertyName, type, m.Modifier, attributes);
			pDecl.StartLocation = m.GetDeclarationLocation(startPos);
			pDecl.EndLocation   = t.Location;
			pDecl.BodyStart   = t.Location;
			pDecl.TypeReference = type;
			pDecl.InterfaceImplementations = implementsClause;
			pDecl.Parameters = p;
			PropertyGetRegion getRegion;
			PropertySetRegion setRegion;
		.)
		AccessorDecls<out getRegion, out setRegion> 
		"End" "Property"
		EOL
		(.
			pDecl.GetRegion = getRegion;
			pDecl.SetRegion = setRegion;
			pDecl.BodyEnd = t.EndLocation;
			compilationUnit.AddChild(pDecl);
		.)
	)
	|
	"Custom" (. Point startPos = t.Location; .) "Event"
	(.
		m.Check(Modifier.VBCustomEvents);
		EventAddRemoveRegion eventAccessorDeclaration;
		EventAddRegion addHandlerAccessorDeclaration = null;
		EventRemoveRegion removeHandlerAccessorDeclaration = null;
		EventRaiseRegion raiseEventAccessorDeclaration = null;
		List<InterfaceImplementation> implementsClause = null;
	.)
	Identifier (. string customEventName = t.val; .)
	"As" TypeName<out type>
	[ ImplementsClause<out implementsClause> ]
	EOL
	{
		EventAccessorDeclaration<out eventAccessorDeclaration>
		(.
			if(eventAccessorDeclaration is EventAddRegion)
			{
				addHandlerAccessorDeclaration = (EventAddRegion)eventAccessorDeclaration;
			}
			else if(eventAccessorDeclaration is EventRemoveRegion)
			{
				removeHandlerAccessorDeclaration = (EventRemoveRegion)eventAccessorDeclaration;
			}
			else if(eventAccessorDeclaration is EventRaiseRegion)
			{
				raiseEventAccessorDeclaration = (EventRaiseRegion)eventAccessorDeclaration;
			}
		.)
	}
	"End" "Event" EOL
	(.
		if(addHandlerAccessorDeclaration == null)
		{
			Error("Need to provide AddHandler accessor.");
		}
		
		if(removeHandlerAccessorDeclaration == null)
		{
			Error("Need to provide RemoveHandler accessor.");
		}
		
		if(raiseEventAccessorDeclaration == null)
		{
			Error("Need to provide RaiseEvent accessor.");
		}
	
		EventDeclaration decl = new EventDeclaration(type, customEventName, m.Modifier, attributes);
		decl.StartLocation = m.GetDeclarationLocation(startPos);
		decl.EndLocation = t.EndLocation;
		decl.AddRegion = addHandlerAccessorDeclaration;
		decl.RemoveRegion = removeHandlerAccessorDeclaration;
		decl.RaiseRegion = raiseEventAccessorDeclaration;
		compilationUnit.AddChild(decl);
	.)
	|
	"Operator"
	(.
		m.Check(Modifier.VBOperators);
		Point startPos = t.Location;
		TypeReference returnType = NullTypeReference.Instance;
		TypeReference operandType = NullTypeReference.Instance;
		string operandName;
		OverloadableOperatorType operatorType;
		AttributeSection section;
		List<ParameterDeclarationExpression> parameters = new List<ParameterDeclarationExpression>();
		List<AttributeSection> returnTypeAttributes = new List<AttributeSection>();
	.)
	OverloadableOperator<out operatorType>
	"(" [ "ByVal" ] Identifier (. operandName = t.val; .)
		[ "As" TypeName<out operandType> ]
		(. parameters.Add(new ParameterDeclarationExpression(operandType, operandName, ParamModifier.In)); .)
		
		{
			","
			[ "ByVal" ] Identifier (. operandName = t.val; .)
			[ "As" TypeName<out operandType> ]
			(. parameters.Add(new ParameterDeclarationExpression(operandType, operandName, ParamModifier.In)); .)
		}
	")"
	(. Point endPos = t.EndLocation; .)
	[ "As" { AttributeSection<out section> (. returnTypeAttributes.Add(section); .) } TypeName<out returnType> (. endPos = t.EndLocation; .) EOL ]
	Block<out stmt> "End" "Operator" EOL
	(.
		OperatorDeclaration operatorDeclaration = new OperatorDeclaration(m.Modifier, 
		                                                                  attributes, 
		                                                                  parameters, 
		                                                                  returnType,
		                                                                  operatorType
		                                                                  );
		operatorDeclaration.ConvertToType = returnType;
		operatorDeclaration.ReturnTypeAttributes = returnTypeAttributes;
		operatorDeclaration.Body = (BlockStatement)stmt;
		operatorDeclaration.StartLocation = m.GetDeclarationLocation(startPos);
		operatorDeclaration.EndLocation = endPos;
		operatorDeclaration.Body.StartLocation = startPos;
		operatorDeclaration.Body.EndLocation = t.Location;
		compilationUnit.AddChild(operatorDeclaration);
	.)
	.

OverloadableOperator<out OverloadableOperatorType operatorType>
	(. operatorType = OverloadableOperatorType.None; .)
	=
	"+"			(. operatorType = OverloadableOperatorType.Add; .)
	|
	"-"			(. operatorType = OverloadableOperatorType.Subtract; .)
	|
	"*"			(. operatorType = OverloadableOperatorType.Multiply; .)
	| 
	"/"			(. operatorType = OverloadableOperatorType.Divide; .)
	| 
	"\\"		(. operatorType = OverloadableOperatorType.DivideInteger; .)
	| 
	"&"			(. operatorType = OverloadableOperatorType.Concat; .)
	| 
	"Like"		(. operatorType = OverloadableOperatorType.Like; .)
	| 
	"Mod"		(. operatorType = OverloadableOperatorType.Modulus; .)
	| 
	"And"		(. operatorType = OverloadableOperatorType.BitwiseAnd; .)
	|
	"Or"		(. operatorType = OverloadableOperatorType.BitwiseOr; .)
	|
	"Xor"		(. operatorType = OverloadableOperatorType.ExclusiveOr; .)
	|
	"^"			(. operatorType = OverloadableOperatorType.Power; .)
	|
	"<<"		(. operatorType = OverloadableOperatorType.ShiftLeft; .)
	|
	">>"		(. operatorType = OverloadableOperatorType.ShiftRight; .)
	|
	"="			(. operatorType = OverloadableOperatorType.Equality; .)
	|
	"<>"		(. operatorType = OverloadableOperatorType.InEquality; .)
	|
	"<"			(. operatorType = OverloadableOperatorType.LessThan; .)
	|
	"<="		(. operatorType = OverloadableOperatorType.LessThanOrEqual; .)
	|
	">"			(. operatorType = OverloadableOperatorType.GreaterThan; .)
	|
	">="		(. operatorType = OverloadableOperatorType.GreaterThanOrEqual; .)
	|
	"CType"		(. operatorType = OverloadableOperatorType.CType; .)
	|
	Identifier
	(.
		string opName = t.val; 
		if (string.Equals(opName, "istrue", StringComparison.InvariantCultureIgnoreCase)) {
			operatorType = OverloadableOperatorType.IsTrue;
		} else if (string.Equals(opName, "isfalse", StringComparison.InvariantCultureIgnoreCase)) {
			operatorType = OverloadableOperatorType.IsFalse;
		} else {
			Error("Invalid operator. Possible operators are '+', '-', 'Not', 'IsTrue', 'IsFalse'.");
		}
	.)
	.

EventAccessorDeclaration<out EventAddRemoveRegion eventAccessorDeclaration>
	(.
		Statement stmt = null;
		List<ParameterDeclarationExpression> p = new List<ParameterDeclarationExpression>();
		AttributeSection section;
		List<AttributeSection> attributes = new List<AttributeSection>();
		eventAccessorDeclaration = null;
	.) =
	{ AttributeSection<out section> (. attributes.Add(section); .) }
	(
			"AddHandler" [ "(" [ FormalParameterList<p> ] ")" ] EOL
			Block<out stmt> "End" "AddHandler" EOL
			(.
				eventAccessorDeclaration = new EventAddRegion(attributes);
				eventAccessorDeclaration.Block = (BlockStatement)stmt;
				eventAccessorDeclaration.Parameters = p;
			.)
		|
			"RemoveHandler" [ "(" [ FormalParameterList<p> ] ")" ] EOL
			Block<out stmt> "End" "RemoveHandler" EOL
			(.
				eventAccessorDeclaration = new EventRemoveRegion(attributes);
				eventAccessorDeclaration.Block = (BlockStatement)stmt;
				eventAccessorDeclaration.Parameters = p;
			.)
		|
			"RaiseEvent" [ "(" [ FormalParameterList<p> ] ")" ] EOL
			Block<out stmt> "End" "RaiseEvent" EOL
			(.
				eventAccessorDeclaration = new EventRaiseRegion(attributes);
				eventAccessorDeclaration.Block = (BlockStatement)stmt;
				eventAccessorDeclaration.Parameters = p;
			.)
	)
	.

/* 9.7 */
AccessorDecls<out PropertyGetRegion getBlock, out PropertySetRegion setBlock>
	(.
		List<AttributeSection> attributes = new List<AttributeSection>();
		AttributeSection section;
		getBlock = null;
		setBlock = null; 
	.) =
	{ AttributeSection<out section> (. attributes.Add(section); .) }
	(
		GetAccessorDecl<out getBlock, attributes>
		[
			(. attributes = new List<AttributeSection>(); .)
			{ AttributeSection<out section> (. attributes.Add(section); .) }
			SetAccessorDecl<out setBlock, attributes>
		]
		|
		SetAccessorDecl<out setBlock, attributes>
		[
			(. attributes = new List<AttributeSection>(); .)
			{ AttributeSection<out section> (. attributes.Add(section); .) }
			GetAccessorDecl<out getBlock, attributes>
		]
	)
	.

/* 9.7.1 */
GetAccessorDecl<out PropertyGetRegion getBlock, List<AttributeSection> attributes>
	(. Statement stmt = null; .) =
	"Get"
	(. Point startLocation = t.Location; .)
	EOL
	Block<out stmt>
	(. getBlock = new PropertyGetRegion((BlockStatement)stmt, attributes); .)
	"End" "Get"
	(. getBlock.StartLocation = startLocation; getBlock.EndLocation = t.EndLocation; .)
	EOL
	.

/* 9.7.2 */
SetAccessorDecl<out PropertySetRegion setBlock, List<AttributeSection> attributes>
	(.
		Statement stmt = null; List<ParameterDeclarationExpression> p = new List<ParameterDeclarationExpression>();
	.) =
	"Set"
	(. Point startLocation = t.Location; .)
	[ "("	[ FormalParameterList<p> ] ")" ]
	EOL
	Block<out stmt>
	(.
		setBlock = new PropertySetRegion((BlockStatement)stmt, attributes);
		setBlock.Parameters = p;
	.)
	"End" "Set"
	(. setBlock.StartLocation = startLocation; setBlock.EndLocation = t.EndLocation; .)
	EOL
	.

/* 9.5 */
ConstantDeclarator<List<VariableDeclaration> constantDeclaration>
	(.
		Expression expr = null;
		TypeReference type = null;
		string name = String.Empty;
	.) =
	Identifier				(. name = t.val; .)
	["As" TypeName<out type> ]
	"=" Expr<out expr>
	(.
		VariableDeclaration f = new VariableDeclaration(name, expr);
		f.TypeReference = type;
		constantDeclaration.Add(f);
	.)
.

/* 9.6 */
VariableDeclarator<List<VariableDeclaration> fieldDeclaration>
	(.
		Expression expr = null;
		TypeReference type = null;
		ArrayList rank = null;
		List<Expression> dimension = null;
	.) =
	Identifier (. string name = t.val; .)
	[ IF(IsSize() && !IsDims()) ArrayInitializationModifier<out dimension> ]
	[ IF(IsDims())              ArrayNameModifier<out rank> ]
	(
		IF (IsObjectCreation()) "As" ObjectCreateExpression<out expr>
		(.
			if (expr is ObjectCreateExpression) {
				type = ((ObjectCreateExpression)expr).CreateType;
			} else {
				type = ((ArrayCreateExpression)expr).CreateType;
			}
		.)
	|
		[ "As" TypeName<out type> ]
		(.
			if (type != null && dimension != null) {
				if(type.RankSpecifier != null) {
					Error("array rank only allowed one time");
				} else {
					for (int i = 0; i < dimension.Count; i++)
						dimension[i] = Expression.AddInteger(dimension[i], 1);
					if (rank == null) {
						type.RankSpecifier = new int[] { dimension.Count - 1 };
					} else {
						rank.Insert(0, dimension.Count - 1);
						type.RankSpecifier = (int[])rank.ToArray(typeof(int));
					}
					expr = new ArrayCreateExpression(type, dimension);
				}
			} else if (type != null && rank != null) {
				if(type.RankSpecifier != null) {
					Error("array rank only allowed one time");
				} else {
					type.RankSpecifier = (int[])rank.ToArray(typeof(int));
				}
			}
		.)
		[ "=" VariableInitializer<out expr> ]
	)
	(. fieldDeclaration.Add(new VariableDeclaration(name, expr, type)); .)
.

/* 6.8 */
ArrayInitializationModifier<out List<Expression> arrayModifiers>
(.
	arrayModifiers = null;
.) =
	"(" InitializationRankList<out arrayModifiers> ")"
.

/* 7.5.4.3 */
InitializationRankList<out List<Expression> rank>
(.
	rank = new List<Expression>();
	Expression expr = null;
.) =
	Expr<out expr>
	[	"To"
		(.	if (!(expr is PrimitiveExpression) || (expr as PrimitiveExpression).StringValue != "0")
			Error("lower bound of array must be zero");
		.)
		Expr<out expr>
	]
	(. if (expr != null) { rank.Add(expr); } .)
	{	","
		Expr<out expr>
		[	"To"
			(.	if (!(expr is PrimitiveExpression) || (expr as PrimitiveExpression).StringValue != "0")
				Error("lower bound of array must be zero");
			.)
			Expr<out expr>
		]
		(. if (expr != null) { rank.Add(expr); } .)
	}
.

/* 9.6.3 */
VariableInitializer<out Expression initializerExpression>
	(.
		initializerExpression = null;
	.) =
	Expr<out initializerExpression>
	| ArrayInitializer<out initializerExpression>
	.

/* 9.6.3.4 */
ArrayInitializer<out Expression outExpr>
	(.
		Expression expr = null;
		ArrayInitializerExpression initializer = new ArrayInitializerExpression();
	.) =
	"{"
	[
		VariableInitializer<out expr>
		(.
			if (expr != null) { initializer.CreateExpressions.Add(expr); }
		.)
		{
			IF (NotFinalComma()) "," VariableInitializer<out expr>
			(. if (expr != null) { initializer.CreateExpressions.Add(expr); } .)
		}
	]
	"}" (. outExpr = initializer; .)
	.

Charset<out CharsetModifier charsetModifier>
	(. charsetModifier = CharsetModifier.None; .) =
	| "Ansi"		(. charsetModifier = CharsetModifier.ANSI; .)
	| "Auto"		(. charsetModifier = CharsetModifier.Auto; .)
	| "Unicode"		(. charsetModifier = CharsetModifier.Unicode; .)
	.

/* 9.2.6 */
HandlesClause<out ArrayList handlesClause>
	(.
		handlesClause = new ArrayList();
		string name;
	.) =
	"Handles" EventMemberSpecifier<out name>	(. handlesClause.Add(name); .)
	{ "," EventMemberSpecifier<out name>		(. handlesClause.Add(name); .) }
	.

/* 7.8. */
InterfaceBase <out List<TypeReference> bases>
	(.
		TypeReference type;
		bases = new List<TypeReference>();
	.) =
	"Inherits"
	TypeName<out type> (. bases.Add(type); .)
	{
		","
		TypeName<out type> (. bases.Add(type); .)
	}
	EOL
	.

/* 7.2 */
TypeImplementsClause<out List<TypeReference> baseInterfaces>
	(.
		baseInterfaces = new List<TypeReference>();
		TypeReference type = null;
	.) =
	"Implements" TypeName<out type>
	(.
		baseInterfaces.Add(type);
	.)
	{
		"," TypeName<out type>
		(. baseInterfaces.Add(type); .)
	}
	EndOfStmt
	.

/* 9.1 */
ImplementsClause<out List<InterfaceImplementation> baseInterfaces>
	(.
		baseInterfaces = new List<InterfaceImplementation>();
		TypeReference type = null;
		string memberName = null;
	.) =
	"Implements"
	NonArrayTypeName<out type, false>
	(. if (type != null) memberName = TypeReference.StripLastIdentifierFromType(ref type); .)
	(. baseInterfaces.Add(new InterfaceImplementation(type, memberName)); .)
	{ ","
		NonArrayTypeName<out type, false>
		(. if (type != null) memberName = TypeReference.StripLastIdentifierFromType(ref type); .)
		(. baseInterfaces.Add(new InterfaceImplementation(type, memberName)); .)
	}
.

EventMemberSpecifier<out string name>
	(. string type; name = String.Empty; .) =
	Identifier (. type = t.val; .)
	"."
	Identifier (. name = type + "." + t.val; .)
	| "MyBase" "."
	(
		Identifier (. name = "MyBase." + t.val; .)
		| "Error"  (. name = "MyBase.Error"; .)
	)
	.

Expr<out Expression expr>
=
	ConditionalOrExpr<out expr>
.

UnaryExpr<out Expression uExpr> 
	(.
		Expression expr;
		UnaryOperatorType uop = UnaryOperatorType.None;
		bool isUOp = false;
	.) =
	{ 	"+" 		(. uop = UnaryOperatorType.Plus; isUOp = true; .)
		| "-" 		(. uop = UnaryOperatorType.Minus; isUOp = true; .)
/*		| "Not"		(. uop = UnaryOperatorType.Not;  isUOp = true;.) */
		| "*" 		(. uop = UnaryOperatorType.Star;  isUOp = true;.)
	}
	SimpleExpr<out expr>
		(.
			if (isUOp) {
				uExpr = new UnaryOperatorExpression(expr, uop);
			} else {
				uExpr = expr;
			}
		.)
	.

AssignmentOperator<out AssignmentOperatorType op>
	(. op = AssignmentOperatorType.None; .) =
	"="		(. op = AssignmentOperatorType.Assign; .)
	| "&="	(. op = AssignmentOperatorType.ConcatString; .)
	| "+="	(. op = AssignmentOperatorType.Add; .)
	| "-="	(. op = AssignmentOperatorType.Subtract; .)
	| "*="	(. op = AssignmentOperatorType.Multiply; .)
	| "/="	(. op = AssignmentOperatorType.Divide; .)
	| "\\="	(. op = AssignmentOperatorType.DivideInteger; .)
	| "^="	(. op = AssignmentOperatorType.Power; .)
	| "<<="	(. op = AssignmentOperatorType.ShiftLeft; .)
	| ">>="	(. op = AssignmentOperatorType.ShiftRight; .)
	.

/* 11.4 */
SimpleExpr<out Expression pexpr>
(.
	Expression expr;
	TypeReference type = null;
	string name = String.Empty;
	pexpr = null;
.) =
	(
		(
			/* 11.4.1 */ 
			LiteralString							(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralCharacter						(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralSingle							(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralDouble							(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralInteger						(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralDate							(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
		|	LiteralDecimal						(.pexpr = new PrimitiveExpression(t.literalValue, t.val);  .)
			/* True, False and Nothing are handled as literals in the spec */
		|	"True"											(.pexpr = new PrimitiveExpression(true, "true");  .)
		|	"False"											(.pexpr = new PrimitiveExpression(false, "false"); .)
		|	"Nothing"											(.pexpr = new PrimitiveExpression(null, "null");  .)
		|	/* 11.4.2 */ "(" Expr<out expr> ")" 				(. pexpr = new ParenthesizedExpression(expr); .)
		|	/* 11.4.4 */ Identifier					(. pexpr = new IdentifierExpression(t.val); .)
		|	(. string val = String.Empty; .)
			PrimitiveTypeName<out val>
			"." (. t.val = ""; .) Identifier (. pexpr = new FieldReferenceExpression(new TypeReferenceExpression(val), t.val); .)
		|	"Me"							(. pexpr = new ThisReferenceExpression(); .)
		|	(. Expression retExpr = null; .)
			( "MyBase"										(. retExpr = new BaseReferenceExpression(); .)
			| "MyClass"										(. retExpr = new ClassReferenceExpression(); .)
			)
			"." IdentifierOrKeyword<out name>				(. pexpr = new FieldReferenceExpression(retExpr, name); .)
		|	"Global" "."
			Identifier (. type = new TypeReference(t.val ?? ""); .)
			/* fallback to "" is required if the token wasn't an identifier (->parser error but no exception) */
			(. type.IsGlobal = true; .)
			(. pexpr = new TypeReferenceExpression(type); .)
		|	ObjectCreateExpression<out expr>					(. pexpr = expr; .)
		|	/* 11.11 : Casts */
			(. CastType castType = CastType.Cast; .)
			( "DirectCast"
			| "CType"   (. castType = CastType.Conversion; .)
			| "TryCast" (. castType = CastType.TryCast; .)
			)
			"(" Expr<out expr> "," TypeName<out type> ")"
			(. pexpr = new CastExpression(type, expr, castType); .)
		|	/* 11.11 */ CastTarget<out type> "(" Expr<out expr> ")"	(. pexpr = new CastExpression(type, expr, CastType.PrimitiveConversion); .)
		|	/* 11.4.5 */ "AddressOf" Expr<out expr>			(. pexpr = new AddressOfExpression(expr); .)
		|	/* 11.5.1 */ "GetType" "(" GetTypeTypeName<out type> ")"	(. pexpr = new TypeOfExpression(type); .)
		|	/* 11.5.2 */ "TypeOf" SimpleExpr<out expr> "Is" TypeName<out type> (. pexpr = new TypeOfIsExpression(expr, type); .)
		)
		{ InvocationOrMemberReferenceExpression<ref pexpr> }
	|
		/* this form only occurs in WithStatements*/
		"." IdentifierOrKeyword<out name> (. pexpr = new FieldReferenceExpression(pexpr, name);.)
		{ InvocationOrMemberReferenceExpression<ref pexpr> }
	)
.

InvocationOrMemberReferenceExpression<ref Expression pexpr>
(. string name; .)
=
	"." IdentifierOrKeyword<out name> (. pexpr = new FieldReferenceExpression(pexpr, name); .)
|	InvocationExpression<ref pexpr>
.

InvocationExpression<ref Expression pexpr>
(. List<TypeReference> typeParameters = new List<TypeReference>();
   List<Expression> parameters = null;
   TypeReference type; .)
=
	"(" (. Point start = t.Location; .)
	(	"Of"
		TypeName<out type> (. if (type != null) typeParameters.Add(type); .)
		")"
		(
			"." Identifier
			(. pexpr = new FieldReferenceExpression(GetTypeReferenceExpression(pexpr, typeParameters), t.val); .)
		|	"("
			ArgumentList<out parameters>
			")"
			(. pexpr = new InvocationExpression(pexpr, parameters, typeParameters); .)
		)
	|	ArgumentList<out parameters>
		")"
		(. pexpr = new InvocationExpression(pexpr, parameters, typeParameters); .)
	)
	(. pexpr.StartLocation = start; pexpr.EndLocation = t.Location; .)
.

/* 11.11 */

CastTarget<out TypeReference type>
	(.
		type = null;
	.) =
	"CBool"		(. type = new TypeReference("System.Boolean"); .)
	| "CByte"	(. type = new TypeReference("System.Byte"); .)
	| "CSByte"	(. type = new TypeReference("System.SByte"); .)
	| "CChar"	(. type = new TypeReference("System.Char"); .)
	| "CDate"	(. type = new TypeReference("System.DateTime"); .)
	| "CDec"	(. type = new TypeReference("System.Decimal"); .)
	| "CDbl"	(. type = new TypeReference("System.Double"); .)
	| "CShort"	(. type = new TypeReference("System.Int16"); .)
	| "CInt"	(. type = new TypeReference("System.Int32"); .)
	| "CLng"	(. type = new TypeReference("System.Int64"); .)
	| "CUShort"	(. type = new TypeReference("System.UInt16"); .)
	| "CUInt"	(. type = new TypeReference("System.UInt32"); .)
	| "CULng"	(. type = new TypeReference("System.UInt64"); .)
	| "CObj"	(. type = new TypeReference("System.Object"); .)
	| "CSng"	(. type = new TypeReference("System.Single"); .)
	| "CStr"	(. type = new TypeReference("System.String"); .)
	.

ConditionalOrExpr<out Expression outExpr>
	(. Expression expr; .) =
	ConditionalAndExpr<out outExpr>  { "OrElse" ConditionalAndExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, BinaryOperatorType.LogicalOr, expr);  .) }
	.

ConditionalAndExpr<out Expression outExpr>
	(. Expression expr; .) =
	InclusiveOrExpr<out outExpr>  { "AndAlso" InclusiveOrExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, BinaryOperatorType.LogicalAnd, expr);  .) }
	.

InclusiveOrExpr<out Expression outExpr>
	(. Expression expr; .) =
	ExclusiveOrExpr<out outExpr>  { "Xor" ExclusiveOrExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, BinaryOperatorType.ExclusiveOr, expr);  .) }
	.

ExclusiveOrExpr<out Expression outExpr>
	(. Expression expr; .) =
	AndExpr<out outExpr>  { "Or" AndExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, BinaryOperatorType.BitwiseOr, expr);  .) }
	.

AndExpr<out Expression outExpr>
	(. Expression expr; .) =
	NotExpr<out outExpr> { "And" NotExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, BinaryOperatorType.BitwiseAnd, expr);  .) }
	.

NotExpr<out Expression outExpr> 
	(. UnaryOperatorType uop = UnaryOperatorType.None; .) =
	{	"Not" (. uop = UnaryOperatorType.Not; .) }
	EqualityExpr<out outExpr>
                (. if (uop != UnaryOperatorType.None)
	                   outExpr = new UnaryOperatorExpression(outExpr, uop);
                .)
	.

EqualityExpr<out Expression outExpr>
	(.
		Expression expr;
		BinaryOperatorType op = BinaryOperatorType.None;
	.) =
	RelationalExpr<out outExpr>
	{
		(
			"<>"		(. op = BinaryOperatorType.InEquality; .)
			| "=" 		(. op = BinaryOperatorType.Equality; .)
			| "Like"	(. op = BinaryOperatorType.Like; .)
		)
		RelationalExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, op, expr);  .) 
	}
	.

RelationalExpr<out Expression outExpr>
	(.
		Expression expr;
		BinaryOperatorType op = BinaryOperatorType.None;
	.) =
	ShiftExpr<out outExpr>
	{
		(
			"<"    (. op = BinaryOperatorType.LessThan; .)
			| ">"  (. op = BinaryOperatorType.GreaterThan; .)
			| "<=" (. op = BinaryOperatorType.LessThanOrEqual; .)
			| ">=" (. op = BinaryOperatorType.GreaterThanOrEqual; .)
		)
		ShiftExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, op, expr);  .)
		|
		/* 11.5.3 */
		("Is" (. op = BinaryOperatorType.ReferenceEquality; .) |
		"IsNot" (. op = BinaryOperatorType.ReferenceInequality; .) )
		Expr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, op, expr); .)
	}
	.

ShiftExpr<out Expression outExpr>
	(.
		Expression expr;
		BinaryOperatorType op = BinaryOperatorType.None;
	.) =
	AdditiveExpr<out outExpr> 
	{
		(
			"<<"   (. op = BinaryOperatorType.ShiftLeft; .)
			| ">>" (. op = BinaryOperatorType.ShiftRight; .)
		)
		AdditiveExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, op, expr);  .) 
	}
	.

AdditiveExpr<out Expression outExpr>
	(.
		Expression expr;
		BinaryOperatorType op = BinaryOperatorType.None;
	.) =
	MultiplicativeExpr<out outExpr>
	{
		(
			  "+"   (. op = BinaryOperatorType.Add; .)
			| "-" (. op = BinaryOperatorType.Subtract; .)
			| "&" (. op = BinaryOperatorType.Concat; .)
		)
		MultiplicativeExpr<out expr> (.  outExpr = new BinaryOperatorExpression(outExpr, op, expr);  .)
	}
	.

MultiplicativeExpr<out Expression outExpr>
(.
	Expression expr;
	BinaryOperatorType op = BinaryOperatorType.None;
.) =
	UnaryExpr<out outExpr>
	{
		(
			"*"   (. op = BinaryOperatorType.Multiply; .)
			| "/" (. op = BinaryOperatorType.Divide; .)
			| "\\" (. op = BinaryOperatorType.DivideInteger; .)
			| "Mod" (. op = BinaryOperatorType.Modulus; .)
			| "^"	(. op = BinaryOperatorType.Power; .)
		) 
		UnaryExpr<out expr> (. outExpr = new BinaryOperatorExpression(outExpr, op, expr); .) 
	}
.
	
ObjectCreateExpression<out Expression oce>
(.
	TypeReference type = null;
	Expression initializer = null;
	List<Expression> arguments = null;
	ArrayList dimensions = null;
	oce = null;
.) =
	"New" NonArrayTypeName<out type, false>
	["(" [ ArgumentList<out arguments> ] ")" ]
	[ IF (la.kind == Tokens.OpenParenthesis)
	  ArrayTypeModifiers<out dimensions>
	  ArrayInitializer<out initializer>
	| ArrayInitializer<out initializer> ]
	(.
		if (initializer == null) {
			oce = new ObjectCreateExpression(type, arguments);
		} else {
			if (dimensions == null) dimensions = new ArrayList();
			dimensions.Insert(0, (arguments == null) ? 0 : Math.Max(arguments.Count - 1, 0));
			type.RankSpecifier = (int[])dimensions.ToArray(typeof(int));
			ArrayCreateExpression ace = new ArrayCreateExpression(type, initializer as ArrayInitializerExpression);
			ace.Arguments = arguments;
			oce = ace;
		}
	.)
.

/* 9.3.2 */
ArgumentList<out List<Expression> arguments>
	(.
		arguments = new List<Expression>();
		Expression expr = null;
	.) =
	[
		Argument<out expr>			(. if (expr != null) { arguments.Add(expr); } .)
		{
			","
			Argument<out expr>		(. if (expr != null) { arguments.Add(expr); } .)
		}
	]
	.

/* Spec, 11.8 */
Argument<out Expression argumentexpr>
	(.
		Expression expr;
		argumentexpr = null;
		string name;
	.) =
	IF(IsNamedAssign()) Identifier (. name = t.val;  .) ":" "=" Expr<out expr>
	(.
		argumentexpr = new NamedArgumentExpression(name, expr);
	.)
	|
	Expr<out argumentexpr>
	.

/* 7.1. */
TypeName<out TypeReference typeref>
(. ArrayList rank = null; .)
=
	NonArrayTypeName<out typeref, false>
	ArrayTypeModifiers<out rank>
	(.	if (rank != null && typeref != null) {
			typeref.RankSpecifier = (int[])rank.ToArray(typeof(int));
		}
	.)
.

GetTypeTypeName<out TypeReference typeref>
(. ArrayList rank = null; .)
=
	NonArrayTypeName<out typeref, true>
	ArrayTypeModifiers<out rank>
	(.	if (rank != null && typeref != null) {
			typeref.RankSpecifier = (int[])rank.ToArray(typeof(int));
		}
	.)
.

/* 7.1 */
NonArrayTypeName<out TypeReference typeref, bool canBeUnbound>
(.
	string name;
	typeref = null;
	bool isGlobal = false;
.) =
	(
		[ "Global" "." (. isGlobal = true; .) ]
		QualIdentAndTypeArguments<out typeref, canBeUnbound>
		(. typeref.IsGlobal = isGlobal; .)
		{ "." (. TypeReference nestedTypeRef; .)
			QualIdentAndTypeArguments<out nestedTypeRef, canBeUnbound>
			(. typeref = new InnerClassTypeReference(typeref, nestedTypeRef.Type, nestedTypeRef.GenericTypes); .)
		}
	)
	| "Object" (. typeref = new TypeReference("System.Object"); .)
	| PrimitiveTypeName<out name> (. typeref = new TypeReference(name); .)
.

QualIdentAndTypeArguments<out TypeReference typeref, bool canBeUnbound>
(. string name; typeref = null; .)
=
	Qualident<out name>
	(. typeref = new TypeReference(name); .)
	[IF (la.kind == Tokens.OpenParenthesis && Peek(1).kind == Tokens.Of)
		"(" "Of"
		( IF (canBeUnbound && (la.kind == Tokens.CloseParenthesis || la.kind == Tokens.Comma))
			(. typeref.GenericTypes.Add(NullTypeReference.Instance); .)
			{ "," (. typeref.GenericTypes.Add(NullTypeReference.Instance); .) }
		  | TypeArgumentList<typeref.GenericTypes>
		)
		")"
	]
.

/* 7.9 */
ArrayNameModifier<out ArrayList arrayModifiers>
(.
	arrayModifiers = null;
.) =
	ArrayTypeModifiers<out arrayModifiers>
.


/* 7.9 */
ArrayTypeModifiers<out ArrayList arrayModifiers>
(.
	arrayModifiers = new ArrayList();
	int i = 0;
.) =
	{	IF (IsDims())
		"("
		[ RankList<out i>]
		(.
			arrayModifiers.Add(i);
		.)
		")"
	}
	(.
		if(arrayModifiers.Count == 0) {
			 arrayModifiers = null;
		}
	.)
.

/* 7.9 */
RankList<out int i>
(. i = 0; .) =
	{ "," (. ++i; .) }
.

/* 7.12 */
TypeArgumentList<List<TypeReference> typeArguments>
(.
	TypeReference typeref;
.) =
	TypeName<out typeref> (. if (typeref != null) typeArguments.Add(typeref); .)
	{
		","
		TypeName<out typeref> (. if (typeref != null) typeArguments.Add(typeref); .)
	}
.

GlobalAttributeSection =
	(. Point startPos = t.Location; .)
	"<" ("Assembly" | "Module")
		(.  string attributeTarget = t.val.ToLower(System.Globalization.CultureInfo.InvariantCulture);
			List<ASTAttribute> attributes = new List<ASTAttribute>();
			ASTAttribute attribute;
		.)
	":" Attribute<out attribute> (. attributes.Add(attribute); .)
	{ IF (NotFinalComma()) ["," ("Assembly" | "Module") ":"] Attribute<out attribute> (. attributes.Add(attribute); .)}
	[ "," ]
	">"
	EndOfStmt
		(.
			AttributeSection section = new AttributeSection(attributeTarget, attributes);
			section.StartLocation = startPos;
			section.EndLocation = t.EndLocation;
			compilationUnit.AddChild(section);
		.)
	.

/* Spec, 5. */
Attribute<out ICSharpCode.NRefactory.Parser.AST.Attribute attribute>
(. string name;
   List<Expression> positional = new List<Expression>();
   List<NamedArgumentExpression> named = new List<NamedArgumentExpression>();
.) =
	[ "Global" "." ]
	Qualident<out name>
	[ AttributeArguments<positional, named> ]
	(. attribute  = new ICSharpCode.NRefactory.Parser.AST.Attribute(name, positional, named); .)
.

/* Spec, 5.2.2 */
AttributeArguments<List<Expression> positional, List<NamedArgumentExpression> named>
	(.
		bool nameFound = false;
		string name = "";
		Expression expr;
	.) =
	"("
	[
		IF (IsNotClosingParenthesis()) ( 
			[
				IF (IsNamedAssign()) (. nameFound = true; .)
				IdentifierOrKeyword<out name>
				[":"] "="
			] Expr<out expr>
				(.
					if (expr != null) { if(name == "") positional.Add(expr);
					else { named.Add(new NamedArgumentExpression(name, expr)); name = ""; }
					}
				.)
			{
				","
					(
						IF (IsNamedAssign())	(. nameFound = true; .)
						IdentifierOrKeyword<out name>
						[ ":" ] "="
						| (. if (nameFound) Error("no positional argument after named argument"); .)
					) Expr<out expr>	(. 	if (expr != null) { if(name == "") positional.Add(expr);
											else { named.Add(new NamedArgumentExpression(name, expr)); name = ""; }
											}
										.)
			}
		)
	]
	")"
	.

/* Spec, 5. */
AttributeSection<out AttributeSection section>
	(.
		string attributeTarget = "";List<ASTAttribute> attributes = new List<ASTAttribute>();
		ASTAttribute attribute;
		
	.) =
	"<" (. Point startPos = t.Location; .)
	[ IF (IsLocalAttrTarget())
		( "Event"		(. attributeTarget = "event";.)
		| "Return"		(. attributeTarget = "return";.)
		| Identifier
			(.
				string val = t.val.ToLower(System.Globalization.CultureInfo.InvariantCulture);
				if (val != "field"	|| val != "method" ||
					val != "module" || val != "param"  ||
					val != "property" || val != "type")
				Error("attribute target specifier (event, return, field," +
						"method, module, param, property, or type) expected");
				attributeTarget = t.val;
			.)
		) ":" 
	]
	Attribute<out attribute>	(. attributes.Add(attribute); .)
	{ IF (NotFinalComma()) "," Attribute<out attribute> (. attributes.Add(attribute); .) }
	[ "," ]
	">"
		(.
			section = new AttributeSection(attributeTarget, attributes);
			section.StartLocation = startPos;
			section.EndLocation = t.EndLocation;
		.)
	.

/* 9.2.5 */
FormalParameterList<List<ParameterDeclarationExpression> parameter>
	(.
		ParameterDeclarationExpression p;
		AttributeSection section;
		List<AttributeSection> attributes = new List<AttributeSection>();
	.) =
	{ AttributeSection<out section> (.attributes.Add(section); .) }
	(
		FormalParameter<out p>
		(.
			bool paramsFound = false;
			p.Attributes = attributes;
			parameter.Add(p);
		.)
		{
			","	(. if (paramsFound) Error("params array must be at end of parameter list"); .)
			{ AttributeSection<out section> (.attributes.Add(section); .) }
			(
				FormalParameter <out p>	(. p.Attributes = attributes; parameter.Add(p); .)
			)
		}
	)
	.
/* 9.2.5 */
FormalParameter<out ParameterDeclarationExpression p>
	(.
		TypeReference type = null;
		ParamModifiers mod = new ParamModifiers(this);
		Expression expr = null;
		p = null;ArrayList arrayModifiers = null;
	.) =
	{ ParameterModifier<mod> }
	Identifier (. string parameterName = t.val; .)
	[ IF(IsDims()) ArrayTypeModifiers<out arrayModifiers> ]
	[ "As" TypeName<out type> ]
	(.
		if(type != null) {
			if (arrayModifiers != null) {
				if (type.RankSpecifier != null) {
					Error("array rank only allowed one time");
				} else {
					type.RankSpecifier = (int[])arrayModifiers.ToArray(typeof(int));
				}
			}
		} else {
			type = new TypeReference("System.Object", arrayModifiers == null ? null : (int[])arrayModifiers.ToArray(typeof(int)));
		}
	.)
	[ "=" Expr<out expr> ]
	(.
		mod.Check();
		p = new ParameterDeclarationExpression(type, parameterName, mod.Modifier, expr);
	.)
	.

/* 10.1 */
Block<out Statement stmt>
	=
	(.
		BlockStatement blockStmt = new BlockStatement();
		blockStmt.StartLocation = t.Location;
		compilationUnit.BlockStart(blockStmt);
	.)
	{	
			IF (IsEndStmtAhead()) "End" EndOfStmt (. compilationUnit.AddChild(new EndStatement()); .)
			| Statement EndOfStmt
/*	 	IF (!LeaveBlock()) { }*/
	}
	(.
		stmt = blockStmt;
		blockStmt.EndLocation = t.EndLocation;
		compilationUnit.BlockEnd();
	.)
	.

Statement
	(.
		Statement stmt = null;
		Point startPos = la.Location;
		string label = String.Empty;
		
	.) =
	(
		| IF (IsLabel()) LabelName<out label>
		(.
			compilationUnit.AddChild(new LabelStatement(t.val));
		.)
		":" Statement
		| EmbeddedStatement<out stmt>			(. compilationUnit.AddChild(stmt); .)
		| LocalDeclarationStatement<out stmt>	(. compilationUnit.AddChild(stmt); .)
	)
	(.
		if (stmt != null) {
			stmt.StartLocation = startPos;
			stmt.EndLocation = t.Location;
		}
	.)
.

/* 10.2 */
LocalDeclarationStatement<out Statement statement>
	(.
		Modifiers m = new Modifiers();
		LocalVariableDeclaration localVariableDeclaration;
		bool dimfound = false;
	.) =
	/* this differs from the spec: dim static x	compiles with vbc. */
	{
		"Const" 	(. m.Add(Modifier.Const, t.Location); .)
		| "Static"	(. m.Add(Modifier.Static, t.Location); .)
		| "Dim"		(. dimfound = true; .)
	}
	(.
		if(dimfound && (m.Modifier & Modifier.Const) != 0) {
			Error("Dim is not allowed on constants.");
		}
		
		if(m.isNone && dimfound == false) {
			Error("Const, Dim or Static expected");
		}
		
		localVariableDeclaration = new LocalVariableDeclaration(m.Modifier);
		localVariableDeclaration.StartLocation = t.Location;
	.)
	VariableDeclarator<localVariableDeclaration.Variables>
	{ "," VariableDeclarator<localVariableDeclaration.Variables> }
	(.
		statement = localVariableDeclaration;
	.)
	.

EmbeddedStatement<out Statement statement>
	(.
		Statement embeddedStatement = null;
		statement = null;
		Expression expr = null;
		string name = String.Empty;
		List<Expression> p = null;
	.) =
		"Exit"				(. ExitType exitType = ExitType.None; .)
		(
		"Sub"				(. exitType = ExitType.Sub; .)
		|
		"Function"			(. exitType = ExitType.Function; .)
		|
		"Property"			(. exitType = ExitType.Property; .)
		|
		"Do"				(. exitType = ExitType.Do; .)
		|
		"For"				(. exitType = ExitType.For; .)
		|
		"Try"				(. exitType = ExitType.Try; .)
		|
		"While"				(. exitType = ExitType.While; .)
		|
		"Select"			(. exitType = ExitType.Select; .)
		)
	(. statement = new ExitStatement(exitType); .)
	| TryStatement<out statement>
	| "Continue" (. ContinueType continueType = ContinueType.None; .) [ "Do" (. continueType = ContinueType.Do; .) | "For" (. continueType = ContinueType.For; .) | "While" (. continueType = ContinueType.While; .)] (. statement = new ContinueStatement(continueType); .)
	| /* 10.10.1.3 */
	"Throw" [ Expr<out expr> ]				(. statement = new ThrowStatement(expr); .)
	| /* 10.11 */
	"Return" [ Expr<out expr> ] 			(. statement = new ReturnStatement(expr); .)
	| /* 10.4 */
	"SyncLock" Expr<out expr> EndOfStmt Block<out embeddedStatement>
	"End" "SyncLock" 						(. statement = new LockStatement(expr, embeddedStatement); .)
	| /* 10.5.1 */
	"RaiseEvent" Identifier (. name = t.val; .)
	[ "(" [ ArgumentList<out p> ] ")" ]
	(. statement = new RaiseEventStatement(name, p); .)
	| /* 10.3 */
	WithStatement<out statement>
	| /* 10.5.2 */
	"AddHandler" (. Expression handlerExpr = null; .)
	Expr<out expr> "," Expr<out handlerExpr>
	(.
		statement = new AddHandlerStatement(expr, handlerExpr);
	.)
	| /* 10.5.2 */
	"RemoveHandler" (. Expression handlerExpr = null; .)
	Expr<out expr> "," Expr<out handlerExpr>
	(.
		statement = new RemoveHandlerStatement(expr, handlerExpr);
	.)
	| /* 10.9.1 */
	"While" Expr<out expr> EndOfStmt
	Block<out embeddedStatement> "End" "While"
	(.
		statement = new DoLoopStatement(expr, embeddedStatement, ConditionType.While, ConditionPosition.Start);
	.)
	| /* 10.9.1 */
	"Do"
	(.
		ConditionType conditionType = ConditionType.None;
	.)
	(
		WhileOrUntil<out conditionType> Expr<out expr> EndOfStmt
		Block<out embeddedStatement>
		"Loop"
		(.
			statement = new DoLoopStatement(expr, 
			                                embeddedStatement, 
			                                conditionType == ConditionType.While ? ConditionType.DoWhile : conditionType, 
			                                ConditionPosition.Start);
		.)
		|
		EndOfStmt
		Block<out embeddedStatement>
		"Loop" [WhileOrUntil<out conditionType> Expr<out expr>]
		(.
			statement = new DoLoopStatement(expr, embeddedStatement, conditionType, ConditionPosition.End);
		.)
	)
	| "For"
	(.
			Expression group = null;
			TypeReference typeReference;
			string        typeName;
			Point startLocation = t.Location;
	.)
	(
		/* 10.9.3  */
 		"Each" LoopControlVariable<out typeReference, out typeName>
		"In" Expr<out group> EndOfStmt
		Block<out embeddedStatement>
		"Next" [ Expr<out expr> ]
		(.
			statement = new ForeachStatement(typeReference, 
			                                 typeName,
			                                 group, 
			                                 embeddedStatement, 
			                                 expr);
			statement.StartLocation = startLocation;
			statement.EndLocation   = t.EndLocation;
			
		.)
		| /* 10.9.2 */
		(.
			Expression start = null;
			Expression end = null;
			Expression step = null;
			Expression nextExpr = null;ArrayList nextExpressions = null;
		.)
		LoopControlVariable<out typeReference, out typeName>
		"=" Expr<out start> "To" Expr<out end> [ "Step" Expr<out step> ]
		EndOfStmt Block<out embeddedStatement>
		"Next"
		[
			Expr<out nextExpr> (. nextExpressions = new ArrayList(); nextExpressions.Add(nextExpr); .) 
			{ "," Expr<out nextExpr> (. nextExpressions.Add(nextExpr); .) }
		]
		(.
			statement = new ForNextStatement(typeReference, typeName, start, end, step, embeddedStatement, nextExpressions);
		.)
	)
	| /* 10.10.2.1 */
	"Error" Expr<out expr> 				(. statement = new ErrorStatement(expr); .)
	| /* 10.12.1 */
	"ReDim" (. Expression redimclause = null; bool isPreserve = false; .) [ "Preserve" (. isPreserve = true; .) ]
	Expr<out redimclause>
	(.
		ReDimStatement reDimStatement = new ReDimStatement(isPreserve);
		statement = reDimStatement;
		reDimStatement.ReDimClauses.Add(redimclause as InvocationExpression);
	.)
	{ "," Expr<out redimclause> (. reDimStatement.ReDimClauses.Add(redimclause as InvocationExpression); .) }
	| /* 10.12.2 */
	"Erase"	
	Expr<out expr>
	(.ArrayList arrays = new ArrayList();
		if (expr != null) { arrays.Add(expr);}
		EraseStatement eraseStatement = new EraseStatement(arrays);
		
	.)
	{ "," Expr<out expr> (. if (expr != null) { arrays.Add(expr); }.) }
	(. statement = eraseStatement; .)
	| /* 10.11 */
	"Stop" (. statement = new StopStatement(); .)
	| /* 10.8.1 */
	"If" Expr<out expr> [ "Then" ] 
	(	
		IF (IsEndStmtAhead()) "End" (. statement = new IfElseStatement(expr, new EndStatement()); .) 
		|
		/* multiline if statement */
		EndOfStmt Block<out embeddedStatement>
		(.
			IfElseStatement ifStatement = new IfElseStatement(expr, embeddedStatement);
		.)
		{
			(
				IF(IsElseIf()) "Else" "If"
				| "ElseIf"
			)
			(. Expression condition = null; Statement block = null; .)
			Expr<out condition> [ "Then"] EndOfStmt
			Block<out block>
			(.
				ifStatement.ElseIfSections.Add(new ElseIfSection(condition, block));
			.)
		}
		[
			"Else" EndOfStmt
			Block<out embeddedStatement>
			(.
				ifStatement.FalseStatement.Add(embeddedStatement);
			.)
		] "End" "If"
		(.
			statement = ifStatement;
		.)
		| /* singleline if statement */
		EmbeddedStatement<out embeddedStatement>
		(.
			IfElseStatement ifStatement = new IfElseStatement(expr, embeddedStatement);
		.)
		{ ":" EmbeddedStatement<out embeddedStatement> (. ifStatement.TrueStatement.Add(embeddedStatement); .) }
		[
			"Else" [ EmbeddedStatement<out embeddedStatement> ]
			(.
				ifStatement.FalseStatement.Add(embeddedStatement);
			.)
			{
				":" EmbeddedStatement<out embeddedStatement>
				(. ifStatement.FalseStatement.Add(embeddedStatement); .)
			}
		]
		(. statement = ifStatement; .)
	)
	| /* 10.8.2 */
	"Select" [ "Case" ] Expr<out expr> EndOfStmt
	(.List<SwitchSection> selectSections = new List<SwitchSection>();
		Statement block = null;
	.)
	{
		(.List<CaseLabel> caseClauses = null; .)
		"Case" CaseClauses<out caseClauses> [ IF(IsNotStatementSeparator()) ":" ] EndOfStmt
		(.
			SwitchSection selectSection = new SwitchSection(caseClauses);
		.)
		Block<out block>
		(.
			selectSection.Children = block.Children;
			selectSections.Add(selectSection);
		.)
	}
	(. statement = new SwitchStatement(expr, selectSections); .)
	"End" "Select"
	| (. OnErrorStatement onErrorStatement = null; .)
	OnErrorStatement<out onErrorStatement> (. statement = onErrorStatement; .)
	| (. GotoStatement goToStatement = null; .)
	GotoStatement<out goToStatement> (. statement = goToStatement; .)
	| (. ResumeStatement resumeStatement = null; .)
	ResumeStatement<out resumeStatement> (. statement = resumeStatement; .)
	|/* Statement expression (invocation and assignment) 10.6.1, 10.6.2, 10.6.3 */
	(.
		Expression val = null;
		AssignmentOperatorType op;
		
		bool mustBeAssignment = la.kind == Tokens.Plus  || la.kind == Tokens.Minus ||
		                        la.kind == Tokens.Not   || la.kind == Tokens.Times;
	.)
	UnaryExpr<out expr>
		(
		AssignmentOperator<out op> Expr<out val>	(. expr = new AssignmentExpression(expr, op, val); .)
		| (. if (mustBeAssignment) Error("error in assignment."); .)
		)
		(.
			// a field reference expression that stands alone is a
			// invocation expression without parantheses and arguments
			if(expr is FieldReferenceExpression || expr is IdentifierExpression) {
				expr = new InvocationExpression(expr);
			}
			statement = new StatementExpression(expr);
		.)
	| "Call" UnaryExpr<out expr> (. statement = new StatementExpression(expr); .)
	| "Using" Identifier (. 
		string resourcename = t.val, typeName; 
		Statement resourceAquisition = null, block = null;
	.) "As" (
		"New" Qualident<out typeName>
		(. List<Expression> initializer = null; .)
		["(" [ ArgumentList<out initializer> ] ")" ]
		(.  
			resourceAquisition =  new LocalVariableDeclaration(new VariableDeclaration(resourcename, new ArrayInitializerExpression(initializer), new TypeReference(typeName)));
			
		.) |
		Qualident<out typeName> "=" Expr<out expr> 
		(.
			resourceAquisition =  new LocalVariableDeclaration(new VariableDeclaration(resourcename, expr, new TypeReference(typeName)));
		.) )
		
		Block<out block>
		"End" "Using"
		(. statement = new UsingStatement(resourceAquisition, block); .)
		
	.

/* 10.9.2 */
LoopControlVariable<out TypeReference type, out string name>
(.ArrayList arrayModifiers = null;
	type = null;
.)
=
	Qualident<out name>
	[ IF(IsDims()) ArrayTypeModifiers<out arrayModifiers> ]
	[ "As" TypeName<out type> (. if (name.IndexOf('.') > 0) { Error("No type def for 'for each' member indexer allowed."); } .) ]
	(.
		if (type != null) {
			if(type.RankSpecifier != null && arrayModifiers != null) {
				Error("array rank only allowed one time");
			} else if (arrayModifiers != null) {
				type.RankSpecifier = (int[])arrayModifiers.ToArray(typeof(int));
			}
		} else {
			if (arrayModifiers != null) {
				type = new TypeReference("Integer", (int[])arrayModifiers.ToArray(typeof(int)));
			} else {
				type = new TypeReference("Integer");
			}
		}
	.)
.

/* 10.2.2 */
OnErrorStatement<out OnErrorStatement stmt>
	(.
		stmt = null;
		GotoStatement goToStatement = null;
	.)
	=
	"On" "Error"
	(
		IF(IsNegativeLabelName())"GoTo" "-" LiteralInteger
		(.
			long intLabel = Int64.Parse(t.val);
			if(intLabel != 1) {
				Error("invalid label in on error statement.");
			}
			stmt = new OnErrorStatement(new GotoStatement((intLabel * -1).ToString()));
		.)
		| GotoStatement<out goToStatement>
		(.
			string val = goToStatement.Label;
			
			// if value is numeric, make sure that is 0
			try {
				long intLabel = Int64.Parse(val);
				if(intLabel != 0) {
					Error("invalid label in on error statement.");
				}
			} catch {
			}
			stmt = new OnErrorStatement(goToStatement);
		.)
		| "Resume" "Next"
		(.
			stmt = new OnErrorStatement(new ResumeStatement(true));
		.)
	)
	.

/* 10.11 */
GotoStatement<out ICSharpCode.NRefactory.Parser.AST.GotoStatement goToStatement>
	(.
		string label = String.Empty;
	.)
	=
	"GoTo" LabelName<out label>
	(.
		goToStatement = new ICSharpCode.NRefactory.Parser.AST.GotoStatement(label);
	.)
	.

/* 10.1 */
LabelName<out string name>
	(.
		name = String.Empty;
	.) =
	Identifier 				(. name = t.val; .)
	| LiteralInteger	(. name = t.val; .)
	.

/* 12.12.1 */
/*
ReDimClause<out ReDimClause clause>
	(.
		Expression initializer = null;
		Expression arrayInitializer = null;
		string name;
	.) =
	[Expr<out initializer> "." ]
	Qualident<out name>
	(.
		clause = new ReDimClause(name);
	.)
	"(" Expr<out initializer>
	(.
		clause.Initializers.Add(initializer);
	.)
	{ "," Expr<out initializer> (. clause.Initializers.Add(initializer); .) }
	")"
	[ ArrayInitializer<out arrayInitializer> ]
	.
*/

/* 10.10.2.3 */
ResumeStatement<out ResumeStatement resumeStatement>
	(.
		resumeStatement = null;
		string label = String.Empty;
	.) =
	IF(IsResumeNext())
	"Resume" "Next" 					(. resumeStatement = new ResumeStatement(true); .)
	| "Resume" [ LabelName<out label> ]	(. resumeStatement = new ResumeStatement(label); .)
	.

/* 18.8.2 */
CaseClauses<out List<CaseLabel> caseClauses>
	(.
		caseClauses = new List<CaseLabel>();
		CaseLabel caseClause = null;
	.) =
	CaseClause<out caseClause> (. caseClauses.Add(caseClause); .)
	{ "," CaseClause<out caseClause> (. caseClauses.Add(caseClause); .) }
	.

/* 19.8.2 */
CaseClause<out CaseLabel caseClause>
	(.
		Expression expr = null;
		Expression sexpr = null;
		BinaryOperatorType op = BinaryOperatorType.None;
		caseClause = null;
	.) =
	"Else"
	(. caseClause = new CaseLabel(); .)
	|
	[ "Is" ] 
	(
		"<"		(. op = BinaryOperatorType.LessThan; .)
		| ">"	(. op = BinaryOperatorType.GreaterThan; .)
		| "<="	(. op = BinaryOperatorType.LessThanOrEqual; .)
		| ">="	(. op = BinaryOperatorType.GreaterThanOrEqual; .)
		| "="	(. op = BinaryOperatorType.Equality; .)
		| "<>"	(. op = BinaryOperatorType.InEquality; .)
	)
	Expr<out expr>
	(.
		caseClause = new CaseLabel(op, expr);
	.)
	| Expr<out expr> [ "To" Expr<out sexpr> ]
	(.
		caseClause = new CaseLabel(expr, sexpr);
	.)
	.

/* 10.9.1 */
WhileOrUntil<out ConditionType conditionType>
	(. conditionType = ConditionType.None; .) =
	"While"		(. conditionType = ConditionType.While; .)
	| "Until"	(. conditionType = ConditionType.Until; .)
	.

/* 10.3 */
WithStatement<out Statement withStatement>
	(.
		Statement blockStmt = null;
		Expression expr = null;
	.) =
	"With" (. Point start = t.Location; .)
	Expr<out expr> EndOfStmt
	(.
		withStatement = new WithStatement(expr);
		withStatement.StartLocation = start;
		withStatements.Push(withStatement);
	.)
	Block<out blockStmt>
	(.
		((WithStatement)withStatement).Body = (BlockStatement)blockStmt;
		withStatements.Pop();
	.)
	"End" "With"
	(. withStatement.EndLocation = t.Location; .)
	.
	
/* 10.10.1 */
TryStatement<out Statement tryStatement>
	(.
		Statement blockStmt = null, finallyStmt = null;List<CatchClause> catchClauses = null;
	.) =
	"Try" EndOfStmt
	Block<out blockStmt>
	[CatchClauses<out catchClauses>]
	["Finally" EndOfStmt Block<out finallyStmt> ]
	"End" "Try"
	(.
		tryStatement = new TryCatchStatement(blockStmt, catchClauses, finallyStmt);
	.)
	.

/* 10.10.1.2 */
CatchClauses<out List<CatchClause> catchClauses>
	(.
		catchClauses = new List<CatchClause>();
		TypeReference type = null;
		Statement blockStmt = null;
		Expression expr = null;
		string name = String.Empty;
	.) =
	{
		"Catch"
		[ Identifier (. name = t.val; .) ["As" TypeName<out type>] ]
		[ "When" Expr<out expr> ]
		EndOfStmt
		Block<out blockStmt>
		(. catchClauses.Add(new CatchClause(type, name, blockStmt, expr)); .)
	}
	.

/* 4.7 */
Qualident<out string qualident>
(. 
	string name;
	qualidentBuilder.Length = 0; 
.)
=
	Identifier	(. qualidentBuilder.Append(t.val); .)
	{ IF (DotAndIdentOrKw()) "." IdentifierOrKeyword<out name> (. qualidentBuilder.Append('.'); qualidentBuilder.Append(name); .) }
	
	(. qualident = qualidentBuilder.ToString(); .)
.

/* This production handles pseudo keywords that are needed in the grammar */
Identifier	=
	ident
	| "Text"
	| "Binary"
	| "Compare"
	| "Assembly"
	| "Ansi"
	| "Auto"
	| "Preserve"
	| "Unicode"
	| "Until"
	.

/* 2.2 */

IdentifierOrKeyword<out string name>
=
	(. lexer.NextToken(); name = t.val;  .)
.


/* 7.3 */
PrimitiveTypeName<out string type>
	(. type = String.Empty; .) =
	"Boolean"		(. type = "Boolean"; .)
	| "Date"		(. type = "Date"; .)
	| "Char"		(. type = "Char"; .)
	| "String"		(. type = "String"; .)
	| "Decimal"		(. type = "Decimal"; .)
	| "Byte"		(. type = "Byte"; .)
	| "Short"		(. type = "Short"; .)
	| "Integer"		(. type = "Integer"; .)
	| "Long"		(. type = "Long"; .)
	| "Single"		(. type = "Single"; .)
	| "Double"		(. type = "Double"; .)
	| "UInteger"	(. type = "UInteger"; .)
	| "ULong"		(. type = "ULong"; .)
	| "UShort"		(. type = "UShort"; .)
	| "SByte"		(. type = "SByte"; .)
	.

ParameterModifier<ParamModifiers m>
	= "ByVal"			(. m.Add(ParamModifier.In); .)
	| "ByRef"			(. m.Add(ParamModifier.Ref); .)
	| "Optional"		(. m.Add(ParamModifier.Optional); .)
	| "ParamArray"		(. m.Add(ParamModifier.Params); .)
	.

TypeModifier<Modifiers m>
=	  "Public"			(. m.Add(Modifier.Public, t.Location); .)
	| "Protected"		(. m.Add(Modifier.Protected, t.Location); .)
	| "Friend"			(. m.Add(Modifier.Internal, t.Location); .)
	| "Private"			(. m.Add(Modifier.Private, t.Location); .)
	| "Shared"			(. m.Add(Modifier.Static, t.Location); .)
	| "Shadows"			(. m.Add(Modifier.New, t.Location); .)
	| "MustInherit"		(. m.Add(Modifier.Abstract, t.Location); .)
	| "NotInheritable"	(. m.Add(Modifier.Sealed, t.Location); .)
	| "Partial"			(. m.Add(Modifier.Partial, t.Location); .)
.

MemberModifier<Modifiers m> =
	  "MustInherit"		(.m.Add(Modifier.Abstract, t.Location);.)
	| "Default"			(.m.Add(Modifier.Default, t.Location);.)
	| "Friend"			(.m.Add(Modifier.Internal, t.Location);.)
	| "Shadows"			(.m.Add(Modifier.New, t.Location);.)
	| "Overrides"		(.m.Add(Modifier.Override, t.Location);.)
	| "MustOverride"	(.m.Add(Modifier.Abstract, t.Location);.)
	| "Private"			(.m.Add(Modifier.Private, t.Location);.)
	| "Protected"		(.m.Add(Modifier.Protected, t.Location);.)
	| "Public"			(.m.Add(Modifier.Public, t.Location);.)
	| "NotInheritable"	(.m.Add(Modifier.Sealed, t.Location);.)
	| "NotOverridable"	(.m.Add(Modifier.Sealed, t.Location);.)
	| "Shared"			(.m.Add(Modifier.Static, t.Location);.)
	| "Overridable"		(.m.Add(Modifier.Virtual, t.Location);.)
	| "Overloads"		(.m.Add(Modifier.Overloads, t.Location);.)
	| "ReadOnly"		(.m.Add(Modifier.ReadOnly, t.Location);.)
	| "WriteOnly"		(.m.Add(Modifier.WriteOnly, t.Location);.)
	| "WithEvents"		(.m.Add(Modifier.WithEvents, t.Location);.)
	| "Dim"				(.m.Add(Modifier.Dim, t.Location);.)
	| "Widening"		(.m.Add(Modifier.Widening, t.Location);.)
	| "Narrowing"		(.m.Add(Modifier.Narrowing, t.Location);.)
.

END VBNET.
