//------------------------------------------------------------------------------
// <autogenerated>
//     This code was generated by a tool.
//     Runtime Version: 1.0.3705.288
//
//     Changes to this file may cause incorrect behavior and will be lost if 
//     the code is regenerated.
// </autogenerated>
//------------------------------------------------------------------------------

namespace BC.Core.Passes {
    
    
    public abstract class Pass : object {
        
        public abstract void Execute(ref BC.Core.ASTs.Elements _, object o);
        
        public void Execute(ref BC.Core.ASTs.Elements _) {
            this.Execute(ref _, null);
        }
    }
    
    public abstract class Walker : Pass {
        
        protected System.Collections.ArrayList Context;
        
        public override void Execute(ref BC.Core.ASTs.Elements _, object o) {
            System.Console.Write("PASS: {0}... ", this.GetType().Name);
            this.Context = new System.Collections.ArrayList();
            this.VisitElements(_, o);
            System.Console.WriteLine("Done!");
        }
        
        protected virtual void VisitElements(BC.Core.ASTs.Elements _, object o) {
            if ((_.Element != null)) {
                for (int i = 0; (i < _.Element.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Element[i], o);
                }
            }
        }
        
        protected virtual void VisitDeclaration(BC.Core.ASTs.Declaration _, object o) {
            this.VisitAbstractNode(_.Value, o);
            this.VisitAbstractNode(_.Type, o);
        }
        
        protected virtual void VisitMethodDefinition(BC.Core.ASTs.MethodDefinition _, object o) {
            this.VisitAbstractNode(_.Body, o);
            this.VisitAbstractNode(_.Type, o);
        }
        
        protected virtual void VisitAbstractLinkableElement(BC.Core.ASTs.AbstractLinkableElement _, object o) {
            if (_ is BC.Core.ASTs.MethodDefinition) {
                this.VisitMethodDefinition(((BC.Core.ASTs.MethodDefinition)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.Declaration) {
                    this.VisitDeclaration(((BC.Core.ASTs.Declaration)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractLinkableElement");
                }
            }
        }
        
        protected virtual void VisitTypeDefinition(BC.Core.ASTs.TypeDefinition _, object o) {
            this.VisitAbstractNode(_.Type, o);
        }
        
        protected virtual void VisitAbstractSemanticElement(BC.Core.ASTs.AbstractSemanticElement _, object o) {
            if (_ is BC.Core.ASTs.TypeDefinition) {
                this.VisitTypeDefinition(((BC.Core.ASTs.TypeDefinition)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractLinkableElement) {
                    this.VisitAbstractLinkableElement(((BC.Core.ASTs.AbstractLinkableElement)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractSemanticElement");
                }
            }
        }
        
        protected virtual void VisitCommentElement(BC.Core.ASTs.CommentElement _, object o) {
        }
        
        protected virtual void VisitAbstractElement(BC.Core.ASTs.AbstractElement _, object o) {
            if (_ is BC.Core.ASTs.CommentElement) {
                this.VisitCommentElement(((BC.Core.ASTs.CommentElement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractSemanticElement) {
                    this.VisitAbstractSemanticElement(((BC.Core.ASTs.AbstractSemanticElement)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractElement");
                }
            }
        }
        
        protected virtual void VisitEnumerationItem(BC.Core.ASTs.EnumerationItem _, object o) {
            this.VisitAbstractNode(_.Value, o);
        }
        
        protected virtual void VisitCompositeExpression(BC.Core.ASTs.CompositeExpression _, object o) {
            this.VisitAbstractNode(_.Type, o);
            this.VisitAbstractNode(_.Operand, o);
        }
        
        protected virtual void VisitFunctionExpression(BC.Core.ASTs.FunctionExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
            if ((_.Argument != null)) {
                for (int i = 0; (i < _.Argument.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Argument[i], o);
                }
            }
        }
        
        protected virtual void VisitArrayExpression(BC.Core.ASTs.ArrayExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
            if ((_.Index != null)) {
                for (int i = 0; (i < _.Index.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Index[i], o);
                }
            }
        }
        
        protected virtual void VisitFieldExpression(BC.Core.ASTs.FieldExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
        }
        
        protected virtual void VisitSizeOfTypeExpression(BC.Core.ASTs.SizeOfTypeExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
        }
        
        protected virtual void VisitSizeOfExpression(BC.Core.ASTs.SizeOfExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
        }
        
        protected virtual void VisitCastExpression(BC.Core.ASTs.CastExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
            this.VisitAbstractNode(_.Type, o);
        }
        
        protected virtual void VisitTrinaryExpression(BC.Core.ASTs.TrinaryExpression _, object o) {
            this.VisitAbstractNode(_.Condition, o);
            this.VisitAbstractNode(_.TrueResult, o);
            this.VisitAbstractNode(_.FalseResult, o);
        }
        
        protected virtual void VisitUnaryExpression(BC.Core.ASTs.UnaryExpression _, object o) {
            this.VisitAbstractNode(_.Operand, o);
        }
        
        protected virtual void VisitBinaryExpression(BC.Core.ASTs.BinaryExpression _, object o) {
            this.VisitAbstractNode(_.LeftOperand, o);
            this.VisitAbstractNode(_.RightOperand, o);
        }
        
        protected virtual void VisitAbstractOperatorExpression(BC.Core.ASTs.AbstractOperatorExpression _, object o) {
            if (_ is BC.Core.ASTs.BinaryExpression) {
                this.VisitBinaryExpression(((BC.Core.ASTs.BinaryExpression)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.UnaryExpression) {
                    this.VisitUnaryExpression(((BC.Core.ASTs.UnaryExpression)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractOperatorExpression");
                }
            }
        }
        
        protected virtual void VisitStringConstant(BC.Core.ASTs.StringConstant _, object o) {
        }
        
        protected virtual void VisitCharacterConstant(BC.Core.ASTs.CharacterConstant _, object o) {
        }
        
        protected virtual void VisitRealConstant(BC.Core.ASTs.RealConstant _, object o) {
        }
        
        protected virtual void VisitIntegerConstant(BC.Core.ASTs.IntegerConstant _, object o) {
        }
        
        protected virtual void VisitAbstractConstantExpression(BC.Core.ASTs.AbstractConstantExpression _, object o) {
            if (_ is BC.Core.ASTs.IntegerConstant) {
                this.VisitIntegerConstant(((BC.Core.ASTs.IntegerConstant)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.RealConstant) {
                    this.VisitRealConstant(((BC.Core.ASTs.RealConstant)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.CharacterConstant) {
                        this.VisitCharacterConstant(((BC.Core.ASTs.CharacterConstant)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.StringConstant) {
                            this.VisitStringConstant(((BC.Core.ASTs.StringConstant)(_)), o);
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractConstantExpression");
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitNamedExpression(BC.Core.ASTs.NamedExpression _, object o) {
        }
        
        protected virtual void VisitAbstractExpression(BC.Core.ASTs.AbstractExpression _, object o) {
            if (_ is BC.Core.ASTs.NamedExpression) {
                this.VisitNamedExpression(((BC.Core.ASTs.NamedExpression)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractConstantExpression) {
                    this.VisitAbstractConstantExpression(((BC.Core.ASTs.AbstractConstantExpression)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.AbstractOperatorExpression) {
                        this.VisitAbstractOperatorExpression(((BC.Core.ASTs.AbstractOperatorExpression)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.TrinaryExpression) {
                            this.VisitTrinaryExpression(((BC.Core.ASTs.TrinaryExpression)(_)), o);
                        }
                        else {
                            if (_ is BC.Core.ASTs.CastExpression) {
                                this.VisitCastExpression(((BC.Core.ASTs.CastExpression)(_)), o);
                            }
                            else {
                                if (_ is BC.Core.ASTs.SizeOfExpression) {
                                    this.VisitSizeOfExpression(((BC.Core.ASTs.SizeOfExpression)(_)), o);
                                }
                                else {
                                    if (_ is BC.Core.ASTs.SizeOfTypeExpression) {
                                        this.VisitSizeOfTypeExpression(((BC.Core.ASTs.SizeOfTypeExpression)(_)), o);
                                    }
                                    else {
                                        if (_ is BC.Core.ASTs.FieldExpression) {
                                            this.VisitFieldExpression(((BC.Core.ASTs.FieldExpression)(_)), o);
                                        }
                                        else {
                                            if (_ is BC.Core.ASTs.ArrayExpression) {
                                                this.VisitArrayExpression(((BC.Core.ASTs.ArrayExpression)(_)), o);
                                            }
                                            else {
                                                if (_ is BC.Core.ASTs.FunctionExpression) {
                                                    this.VisitFunctionExpression(((BC.Core.ASTs.FunctionExpression)(_)), o);
                                                }
                                                else {
                                                    if (_ is BC.Core.ASTs.CompositeExpression) {
                                                        this.VisitCompositeExpression(((BC.Core.ASTs.CompositeExpression)(_)), o);
                                                    }
                                                    else {
                                                        System.Diagnostics.Debug.Assert(false, "invalid AbstractExpression");
                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitVarArgType(BC.Core.ASTs.VarArgType _, object o) {
        }
        
        protected virtual void VisitEnumerationType(BC.Core.ASTs.EnumerationType _, object o) {
            if ((_.Item != null)) {
                for (int i = 0; (i < _.Item.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Item[i], o);
                }
            }
        }
        
        protected virtual void VisitCompositeType(BC.Core.ASTs.CompositeType _, object o) {
            if ((_.Field != null)) {
                for (int i = 0; (i < _.Field.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Field[i], o);
                }
            }
        }
        
        protected virtual void VisitNamedType(BC.Core.ASTs.NamedType _, object o) {
        }
        
        protected virtual void VisitFunctionType(BC.Core.ASTs.FunctionType _, object o) {
            if ((_.Argument != null)) {
                for (int i = 0; (i < _.Argument.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Argument[i], o);
                }
            }
            this.VisitAbstractNode(_.Base, o);
        }
        
        protected virtual void VisitArrayType(BC.Core.ASTs.ArrayType _, object o) {
            if ((_.Dimension != null)) {
                for (int i = 0; (i < _.Dimension.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Dimension[i], o);
                }
            }
            this.VisitAbstractNode(_.Base, o);
        }
        
        protected virtual void VisitIndirectType(BC.Core.ASTs.IndirectType _, object o) {
            this.VisitAbstractNode(_.Base, o);
        }
        
        protected virtual void VisitAbstractCompoundType(BC.Core.ASTs.AbstractCompoundType _, object o) {
            if (_ is BC.Core.ASTs.IndirectType) {
                this.VisitIndirectType(((BC.Core.ASTs.IndirectType)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.ArrayType) {
                    this.VisitArrayType(((BC.Core.ASTs.ArrayType)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.FunctionType) {
                        this.VisitFunctionType(((BC.Core.ASTs.FunctionType)(_)), o);
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractCompoundType");
                    }
                }
            }
        }
        
        protected virtual void VisitComplexType(BC.Core.ASTs.ComplexType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitImaginaryType(BC.Core.ASTs.ImaginaryType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitRealType(BC.Core.ASTs.RealType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitAbstractRealType(BC.Core.ASTs.AbstractRealType _, object o) {
            if (_ is BC.Core.ASTs.RealType) {
                this.VisitRealType(((BC.Core.ASTs.RealType)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.ImaginaryType) {
                    this.VisitImaginaryType(((BC.Core.ASTs.ImaginaryType)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.ComplexType) {
                        this.VisitComplexType(((BC.Core.ASTs.ComplexType)(_)), o);
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractRealType");
                    }
                }
            }
        }
        
        protected virtual void VisitIntegerType(BC.Core.ASTs.IntegerType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitBoolType(BC.Core.ASTs.BoolType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitVoidType(BC.Core.ASTs.VoidType _, object o) {
            this.VisitAbstractNode(_.PrecisionExpression, o);
        }
        
        protected virtual void VisitAbstractPrimitiveType(BC.Core.ASTs.AbstractPrimitiveType _, object o) {
            if (_ is BC.Core.ASTs.VoidType) {
                this.VisitVoidType(((BC.Core.ASTs.VoidType)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.BoolType) {
                    this.VisitBoolType(((BC.Core.ASTs.BoolType)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.IntegerType) {
                        this.VisitIntegerType(((BC.Core.ASTs.IntegerType)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractRealType) {
                            this.VisitAbstractRealType(((BC.Core.ASTs.AbstractRealType)(_)), o);
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractPrimitiveType");
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitAbstractType(BC.Core.ASTs.AbstractType _, object o) {
            if (_ is BC.Core.ASTs.AbstractPrimitiveType) {
                this.VisitAbstractPrimitiveType(((BC.Core.ASTs.AbstractPrimitiveType)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractCompoundType) {
                    this.VisitAbstractCompoundType(((BC.Core.ASTs.AbstractCompoundType)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.NamedType) {
                        this.VisitNamedType(((BC.Core.ASTs.NamedType)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.CompositeType) {
                            this.VisitCompositeType(((BC.Core.ASTs.CompositeType)(_)), o);
                        }
                        else {
                            if (_ is BC.Core.ASTs.EnumerationType) {
                                this.VisitEnumerationType(((BC.Core.ASTs.EnumerationType)(_)), o);
                            }
                            else {
                                if (_ is BC.Core.ASTs.VarArgType) {
                                    this.VisitVarArgType(((BC.Core.ASTs.VarArgType)(_)), o);
                                }
                                else {
                                    System.Diagnostics.Debug.Assert(false, "invalid AbstractType");
                                }
                            }
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitInitializerList(BC.Core.ASTs.InitializerList _, object o) {
            if ((_.Initializer != null)) {
                for (int i = 0; (i < _.Initializer.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Initializer[i], o);
                }
            }
            if ((_.Designator != null)) {
                for (int i = 0; (i < _.Designator.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Designator[i], o);
                }
            }
        }
        
        protected virtual void VisitInitializer(BC.Core.ASTs.Initializer _, object o) {
            this.VisitAbstractNode(_.Expression, o);
            if ((_.Designator != null)) {
                for (int i = 0; (i < _.Designator.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Designator[i], o);
                }
            }
        }
        
        protected virtual void VisitAbstractInitializer(BC.Core.ASTs.AbstractInitializer _, object o) {
            if (_ is BC.Core.ASTs.Initializer) {
                this.VisitInitializer(((BC.Core.ASTs.Initializer)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.InitializerList) {
                    this.VisitInitializerList(((BC.Core.ASTs.InitializerList)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractInitializer");
                }
            }
        }
        
        protected virtual void VisitFieldDesignator(BC.Core.ASTs.FieldDesignator _, object o) {
        }
        
        protected virtual void VisitIndexDesignator(BC.Core.ASTs.IndexDesignator _, object o) {
            this.VisitAbstractNode(_.Index, o);
        }
        
        protected virtual void VisitAbstractDesignator(BC.Core.ASTs.AbstractDesignator _, object o) {
            if (_ is BC.Core.ASTs.IndexDesignator) {
                this.VisitIndexDesignator(((BC.Core.ASTs.IndexDesignator)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.FieldDesignator) {
                    this.VisitFieldDesignator(((BC.Core.ASTs.FieldDesignator)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractDesignator");
                }
            }
        }
        
        protected virtual void VisitCompoundStatement(BC.Core.ASTs.CompoundStatement _, object o) {
            if ((_.Statement != null)) {
                for (int i = 0; (i < _.Statement.Length); i = (i + 1)) {
                    this.VisitAbstractNode(_.Statement[i], o);
                }
            }
        }
        
        protected virtual void VisitContinueStatement(BC.Core.ASTs.ContinueStatement _, object o) {
        }
        
        protected virtual void VisitBreakStatement(BC.Core.ASTs.BreakStatement _, object o) {
        }
        
        protected virtual void VisitGotoStatement(BC.Core.ASTs.GotoStatement _, object o) {
        }
        
        protected virtual void VisitCommentStatement(BC.Core.ASTs.CommentStatement _, object o) {
        }
        
        protected virtual void VisitDeclarationStatement(BC.Core.ASTs.DeclarationStatement _, object o) {
            this.VisitAbstractNode(_.Declaration, o);
        }
        
        protected virtual void VisitReturnStatement(BC.Core.ASTs.ReturnStatement _, object o) {
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitForStatement(BC.Core.ASTs.ForStatement _, object o) {
            this.VisitAbstractNode(_.Init, o);
            this.VisitAbstractNode(_.Update, o);
            this.VisitAbstractNode(_.Statement, o);
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitLoopStatement(BC.Core.ASTs.LoopStatement _, object o) {
            this.VisitAbstractNode(_.Statement, o);
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitAbstractLoopStatement(BC.Core.ASTs.AbstractLoopStatement _, object o) {
            if (_ is BC.Core.ASTs.LoopStatement) {
                this.VisitLoopStatement(((BC.Core.ASTs.LoopStatement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.ForStatement) {
                    this.VisitForStatement(((BC.Core.ASTs.ForStatement)(_)), o);
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractLoopStatement");
                }
            }
        }
        
        protected virtual void VisitIfStatement(BC.Core.ASTs.IfStatement _, object o) {
            this.VisitAbstractNode(_.ElseStatement, o);
            this.VisitAbstractNode(_.Statement, o);
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitSwitchStatement(BC.Core.ASTs.SwitchStatement _, object o) {
            this.VisitAbstractNode(_.Statement, o);
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitLabeledStatement(BC.Core.ASTs.LabeledStatement _, object o) {
            this.VisitAbstractNode(_.Statement, o);
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitAbstractCombinationStatement(BC.Core.ASTs.AbstractCombinationStatement _, object o) {
            if (_ is BC.Core.ASTs.LabeledStatement) {
                this.VisitLabeledStatement(((BC.Core.ASTs.LabeledStatement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.SwitchStatement) {
                    this.VisitSwitchStatement(((BC.Core.ASTs.SwitchStatement)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.IfStatement) {
                        this.VisitIfStatement(((BC.Core.ASTs.IfStatement)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractLoopStatement) {
                            this.VisitAbstractLoopStatement(((BC.Core.ASTs.AbstractLoopStatement)(_)), o);
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractCombinationStatement");
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitExpressionStatement(BC.Core.ASTs.ExpressionStatement _, object o) {
            this.VisitAbstractNode(_.Expression, o);
        }
        
        protected virtual void VisitAbstractExpressionStatement(BC.Core.ASTs.AbstractExpressionStatement _, object o) {
            if (_ is BC.Core.ASTs.ExpressionStatement) {
                this.VisitExpressionStatement(((BC.Core.ASTs.ExpressionStatement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractCombinationStatement) {
                    this.VisitAbstractCombinationStatement(((BC.Core.ASTs.AbstractCombinationStatement)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.ReturnStatement) {
                        this.VisitReturnStatement(((BC.Core.ASTs.ReturnStatement)(_)), o);
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractExpressionStatement");
                    }
                }
            }
        }
        
        protected virtual void VisitAbstractStatement(BC.Core.ASTs.AbstractStatement _, object o) {
            if (_ is BC.Core.ASTs.AbstractExpressionStatement) {
                this.VisitAbstractExpressionStatement(((BC.Core.ASTs.AbstractExpressionStatement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.DeclarationStatement) {
                    this.VisitDeclarationStatement(((BC.Core.ASTs.DeclarationStatement)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.CommentStatement) {
                        this.VisitCommentStatement(((BC.Core.ASTs.CommentStatement)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.GotoStatement) {
                            this.VisitGotoStatement(((BC.Core.ASTs.GotoStatement)(_)), o);
                        }
                        else {
                            if (_ is BC.Core.ASTs.BreakStatement) {
                                this.VisitBreakStatement(((BC.Core.ASTs.BreakStatement)(_)), o);
                            }
                            else {
                                if (_ is BC.Core.ASTs.ContinueStatement) {
                                    this.VisitContinueStatement(((BC.Core.ASTs.ContinueStatement)(_)), o);
                                }
                                else {
                                    if (_ is BC.Core.ASTs.CompoundStatement) {
                                        this.VisitCompoundStatement(((BC.Core.ASTs.CompoundStatement)(_)), o);
                                    }
                                    else {
                                        System.Diagnostics.Debug.Assert(false, "invalid AbstractStatement");
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
        
        protected virtual void VisitAbstractNode(BC.Core.ASTs.AbstractNode _, object o) {
            this.Context.Add(_);
            if (_ is BC.Core.ASTs.AbstractStatement) {
                this.VisitAbstractStatement(((BC.Core.ASTs.AbstractStatement)(_)), o);
            }
            else {
                if (_ is BC.Core.ASTs.AbstractDesignator) {
                    this.VisitAbstractDesignator(((BC.Core.ASTs.AbstractDesignator)(_)), o);
                }
                else {
                    if (_ is BC.Core.ASTs.AbstractInitializer) {
                        this.VisitAbstractInitializer(((BC.Core.ASTs.AbstractInitializer)(_)), o);
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractType) {
                            this.VisitAbstractType(((BC.Core.ASTs.AbstractType)(_)), o);
                        }
                        else {
                            if (_ is BC.Core.ASTs.AbstractExpression) {
                                this.VisitAbstractExpression(((BC.Core.ASTs.AbstractExpression)(_)), o);
                            }
                            else {
                                if (_ is BC.Core.ASTs.EnumerationItem) {
                                    this.VisitEnumerationItem(((BC.Core.ASTs.EnumerationItem)(_)), o);
                                }
                                else {
                                    if (_ is BC.Core.ASTs.AbstractElement) {
                                        this.VisitAbstractElement(((BC.Core.ASTs.AbstractElement)(_)), o);
                                    }
                                    else {
                                        if (_ is BC.Core.ASTs.Elements) {
                                            this.VisitElements(((BC.Core.ASTs.Elements)(_)), o);
                                        }
                                        else {
                                            System.Diagnostics.Debug.Assert(false, "invalid AbstractNode");
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
            this.Context.RemoveAt((this.Context.Count - 1));
        }
    }
    
    public abstract class AbstractRenderer : Pass {
        
        public abstract string RenderElements(BC.Core.ASTs.Elements _);
        
        public abstract string RenderDeclaration(BC.Core.ASTs.Declaration _);
        
        public abstract string RenderMethodDefinition(BC.Core.ASTs.MethodDefinition _);
        
        public virtual string RenderAbstractLinkableElement(BC.Core.ASTs.AbstractLinkableElement _) {
            if (_ is BC.Core.ASTs.MethodDefinition) {
                return this.RenderMethodDefinition(((BC.Core.ASTs.MethodDefinition)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.Declaration) {
                    return this.RenderDeclaration(((BC.Core.ASTs.Declaration)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractLinkableElement");
                    return null;
                }
            }
        }
        
        public abstract string RenderTypeDefinition(BC.Core.ASTs.TypeDefinition _);
        
        public virtual string RenderAbstractSemanticElement(BC.Core.ASTs.AbstractSemanticElement _) {
            if (_ is BC.Core.ASTs.TypeDefinition) {
                return this.RenderTypeDefinition(((BC.Core.ASTs.TypeDefinition)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractLinkableElement) {
                    return this.RenderAbstractLinkableElement(((BC.Core.ASTs.AbstractLinkableElement)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractSemanticElement");
                    return null;
                }
            }
        }
        
        public abstract string RenderCommentElement(BC.Core.ASTs.CommentElement _);
        
        public virtual string RenderAbstractElement(BC.Core.ASTs.AbstractElement _) {
            if (_ is BC.Core.ASTs.CommentElement) {
                return this.RenderCommentElement(((BC.Core.ASTs.CommentElement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractSemanticElement) {
                    return this.RenderAbstractSemanticElement(((BC.Core.ASTs.AbstractSemanticElement)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractElement");
                    return null;
                }
            }
        }
        
        public abstract string RenderEnumerationItem(BC.Core.ASTs.EnumerationItem _);
        
        public abstract string RenderCompositeExpression(BC.Core.ASTs.CompositeExpression _);
        
        public abstract string RenderFunctionExpression(BC.Core.ASTs.FunctionExpression _);
        
        public abstract string RenderArrayExpression(BC.Core.ASTs.ArrayExpression _);
        
        public abstract string RenderFieldExpression(BC.Core.ASTs.FieldExpression _);
        
        public abstract string RenderSizeOfTypeExpression(BC.Core.ASTs.SizeOfTypeExpression _);
        
        public abstract string RenderSizeOfExpression(BC.Core.ASTs.SizeOfExpression _);
        
        public abstract string RenderCastExpression(BC.Core.ASTs.CastExpression _);
        
        public abstract string RenderTrinaryExpression(BC.Core.ASTs.TrinaryExpression _);
        
        public abstract string RenderUnaryExpression(BC.Core.ASTs.UnaryExpression _);
        
        public abstract string RenderBinaryExpression(BC.Core.ASTs.BinaryExpression _);
        
        public virtual string RenderAbstractOperatorExpression(BC.Core.ASTs.AbstractOperatorExpression _) {
            if (_ is BC.Core.ASTs.BinaryExpression) {
                return this.RenderBinaryExpression(((BC.Core.ASTs.BinaryExpression)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.UnaryExpression) {
                    return this.RenderUnaryExpression(((BC.Core.ASTs.UnaryExpression)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractOperatorExpression");
                    return null;
                }
            }
        }
        
        public abstract string RenderStringConstant(BC.Core.ASTs.StringConstant _);
        
        public abstract string RenderCharacterConstant(BC.Core.ASTs.CharacterConstant _);
        
        public abstract string RenderRealConstant(BC.Core.ASTs.RealConstant _);
        
        public abstract string RenderIntegerConstant(BC.Core.ASTs.IntegerConstant _);
        
        public virtual string RenderAbstractConstantExpression(BC.Core.ASTs.AbstractConstantExpression _) {
            if (_ is BC.Core.ASTs.IntegerConstant) {
                return this.RenderIntegerConstant(((BC.Core.ASTs.IntegerConstant)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.RealConstant) {
                    return this.RenderRealConstant(((BC.Core.ASTs.RealConstant)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.CharacterConstant) {
                        return this.RenderCharacterConstant(((BC.Core.ASTs.CharacterConstant)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.StringConstant) {
                            return this.RenderStringConstant(((BC.Core.ASTs.StringConstant)(_)));
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractConstantExpression");
                            return null;
                        }
                    }
                }
            }
        }
        
        public abstract string RenderNamedExpression(BC.Core.ASTs.NamedExpression _);
        
        public virtual string RenderAbstractExpression(BC.Core.ASTs.AbstractExpression _) {
            if (_ is BC.Core.ASTs.NamedExpression) {
                return this.RenderNamedExpression(((BC.Core.ASTs.NamedExpression)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractConstantExpression) {
                    return this.RenderAbstractConstantExpression(((BC.Core.ASTs.AbstractConstantExpression)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.AbstractOperatorExpression) {
                        return this.RenderAbstractOperatorExpression(((BC.Core.ASTs.AbstractOperatorExpression)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.TrinaryExpression) {
                            return this.RenderTrinaryExpression(((BC.Core.ASTs.TrinaryExpression)(_)));
                        }
                        else {
                            if (_ is BC.Core.ASTs.CastExpression) {
                                return this.RenderCastExpression(((BC.Core.ASTs.CastExpression)(_)));
                            }
                            else {
                                if (_ is BC.Core.ASTs.SizeOfExpression) {
                                    return this.RenderSizeOfExpression(((BC.Core.ASTs.SizeOfExpression)(_)));
                                }
                                else {
                                    if (_ is BC.Core.ASTs.SizeOfTypeExpression) {
                                        return this.RenderSizeOfTypeExpression(((BC.Core.ASTs.SizeOfTypeExpression)(_)));
                                    }
                                    else {
                                        if (_ is BC.Core.ASTs.FieldExpression) {
                                            return this.RenderFieldExpression(((BC.Core.ASTs.FieldExpression)(_)));
                                        }
                                        else {
                                            if (_ is BC.Core.ASTs.ArrayExpression) {
                                                return this.RenderArrayExpression(((BC.Core.ASTs.ArrayExpression)(_)));
                                            }
                                            else {
                                                if (_ is BC.Core.ASTs.FunctionExpression) {
                                                    return this.RenderFunctionExpression(((BC.Core.ASTs.FunctionExpression)(_)));
                                                }
                                                else {
                                                    if (_ is BC.Core.ASTs.CompositeExpression) {
                                                        return this.RenderCompositeExpression(((BC.Core.ASTs.CompositeExpression)(_)));
                                                    }
                                                    else {
                                                        System.Diagnostics.Debug.Assert(false, "invalid AbstractExpression");
                                                        return null;
                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
        
        public abstract string RenderVarArgType(BC.Core.ASTs.VarArgType _);
        
        public abstract string RenderEnumerationType(BC.Core.ASTs.EnumerationType _);
        
        public abstract string RenderCompositeType(BC.Core.ASTs.CompositeType _);
        
        public abstract string RenderNamedType(BC.Core.ASTs.NamedType _);
        
        public abstract string RenderFunctionType(BC.Core.ASTs.FunctionType _);
        
        public abstract string RenderArrayType(BC.Core.ASTs.ArrayType _);
        
        public abstract string RenderIndirectType(BC.Core.ASTs.IndirectType _);
        
        public virtual string RenderAbstractCompoundType(BC.Core.ASTs.AbstractCompoundType _) {
            if (_ is BC.Core.ASTs.IndirectType) {
                return this.RenderIndirectType(((BC.Core.ASTs.IndirectType)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.ArrayType) {
                    return this.RenderArrayType(((BC.Core.ASTs.ArrayType)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.FunctionType) {
                        return this.RenderFunctionType(((BC.Core.ASTs.FunctionType)(_)));
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractCompoundType");
                        return null;
                    }
                }
            }
        }
        
        public abstract string RenderComplexType(BC.Core.ASTs.ComplexType _);
        
        public abstract string RenderImaginaryType(BC.Core.ASTs.ImaginaryType _);
        
        public abstract string RenderRealType(BC.Core.ASTs.RealType _);
        
        public virtual string RenderAbstractRealType(BC.Core.ASTs.AbstractRealType _) {
            if (_ is BC.Core.ASTs.RealType) {
                return this.RenderRealType(((BC.Core.ASTs.RealType)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.ImaginaryType) {
                    return this.RenderImaginaryType(((BC.Core.ASTs.ImaginaryType)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.ComplexType) {
                        return this.RenderComplexType(((BC.Core.ASTs.ComplexType)(_)));
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractRealType");
                        return null;
                    }
                }
            }
        }
        
        public abstract string RenderIntegerType(BC.Core.ASTs.IntegerType _);
        
        public abstract string RenderBoolType(BC.Core.ASTs.BoolType _);
        
        public abstract string RenderVoidType(BC.Core.ASTs.VoidType _);
        
        public virtual string RenderAbstractPrimitiveType(BC.Core.ASTs.AbstractPrimitiveType _) {
            if (_ is BC.Core.ASTs.VoidType) {
                return this.RenderVoidType(((BC.Core.ASTs.VoidType)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.BoolType) {
                    return this.RenderBoolType(((BC.Core.ASTs.BoolType)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.IntegerType) {
                        return this.RenderIntegerType(((BC.Core.ASTs.IntegerType)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractRealType) {
                            return this.RenderAbstractRealType(((BC.Core.ASTs.AbstractRealType)(_)));
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractPrimitiveType");
                            return null;
                        }
                    }
                }
            }
        }
        
        public virtual string RenderAbstractType(BC.Core.ASTs.AbstractType _) {
            if (_ is BC.Core.ASTs.AbstractPrimitiveType) {
                return this.RenderAbstractPrimitiveType(((BC.Core.ASTs.AbstractPrimitiveType)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractCompoundType) {
                    return this.RenderAbstractCompoundType(((BC.Core.ASTs.AbstractCompoundType)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.NamedType) {
                        return this.RenderNamedType(((BC.Core.ASTs.NamedType)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.CompositeType) {
                            return this.RenderCompositeType(((BC.Core.ASTs.CompositeType)(_)));
                        }
                        else {
                            if (_ is BC.Core.ASTs.EnumerationType) {
                                return this.RenderEnumerationType(((BC.Core.ASTs.EnumerationType)(_)));
                            }
                            else {
                                if (_ is BC.Core.ASTs.VarArgType) {
                                    return this.RenderVarArgType(((BC.Core.ASTs.VarArgType)(_)));
                                }
                                else {
                                    System.Diagnostics.Debug.Assert(false, "invalid AbstractType");
                                    return null;
                                }
                            }
                        }
                    }
                }
            }
        }
        
        public abstract string RenderInitializerList(BC.Core.ASTs.InitializerList _);
        
        public abstract string RenderInitializer(BC.Core.ASTs.Initializer _);
        
        public virtual string RenderAbstractInitializer(BC.Core.ASTs.AbstractInitializer _) {
            if (_ is BC.Core.ASTs.Initializer) {
                return this.RenderInitializer(((BC.Core.ASTs.Initializer)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.InitializerList) {
                    return this.RenderInitializerList(((BC.Core.ASTs.InitializerList)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractInitializer");
                    return null;
                }
            }
        }
        
        public abstract string RenderFieldDesignator(BC.Core.ASTs.FieldDesignator _);
        
        public abstract string RenderIndexDesignator(BC.Core.ASTs.IndexDesignator _);
        
        public virtual string RenderAbstractDesignator(BC.Core.ASTs.AbstractDesignator _) {
            if (_ is BC.Core.ASTs.IndexDesignator) {
                return this.RenderIndexDesignator(((BC.Core.ASTs.IndexDesignator)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.FieldDesignator) {
                    return this.RenderFieldDesignator(((BC.Core.ASTs.FieldDesignator)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractDesignator");
                    return null;
                }
            }
        }
        
        public abstract string RenderCompoundStatement(BC.Core.ASTs.CompoundStatement _);
        
        public abstract string RenderContinueStatement(BC.Core.ASTs.ContinueStatement _);
        
        public abstract string RenderBreakStatement(BC.Core.ASTs.BreakStatement _);
        
        public abstract string RenderGotoStatement(BC.Core.ASTs.GotoStatement _);
        
        public abstract string RenderCommentStatement(BC.Core.ASTs.CommentStatement _);
        
        public abstract string RenderDeclarationStatement(BC.Core.ASTs.DeclarationStatement _);
        
        public abstract string RenderReturnStatement(BC.Core.ASTs.ReturnStatement _);
        
        public abstract string RenderForStatement(BC.Core.ASTs.ForStatement _);
        
        public abstract string RenderLoopStatement(BC.Core.ASTs.LoopStatement _);
        
        public virtual string RenderAbstractLoopStatement(BC.Core.ASTs.AbstractLoopStatement _) {
            if (_ is BC.Core.ASTs.LoopStatement) {
                return this.RenderLoopStatement(((BC.Core.ASTs.LoopStatement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.ForStatement) {
                    return this.RenderForStatement(((BC.Core.ASTs.ForStatement)(_)));
                }
                else {
                    System.Diagnostics.Debug.Assert(false, "invalid AbstractLoopStatement");
                    return null;
                }
            }
        }
        
        public abstract string RenderIfStatement(BC.Core.ASTs.IfStatement _);
        
        public abstract string RenderSwitchStatement(BC.Core.ASTs.SwitchStatement _);
        
        public abstract string RenderLabeledStatement(BC.Core.ASTs.LabeledStatement _);
        
        public virtual string RenderAbstractCombinationStatement(BC.Core.ASTs.AbstractCombinationStatement _) {
            if (_ is BC.Core.ASTs.LabeledStatement) {
                return this.RenderLabeledStatement(((BC.Core.ASTs.LabeledStatement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.SwitchStatement) {
                    return this.RenderSwitchStatement(((BC.Core.ASTs.SwitchStatement)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.IfStatement) {
                        return this.RenderIfStatement(((BC.Core.ASTs.IfStatement)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractLoopStatement) {
                            return this.RenderAbstractLoopStatement(((BC.Core.ASTs.AbstractLoopStatement)(_)));
                        }
                        else {
                            System.Diagnostics.Debug.Assert(false, "invalid AbstractCombinationStatement");
                            return null;
                        }
                    }
                }
            }
        }
        
        public abstract string RenderExpressionStatement(BC.Core.ASTs.ExpressionStatement _);
        
        public virtual string RenderAbstractExpressionStatement(BC.Core.ASTs.AbstractExpressionStatement _) {
            if (_ is BC.Core.ASTs.ExpressionStatement) {
                return this.RenderExpressionStatement(((BC.Core.ASTs.ExpressionStatement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractCombinationStatement) {
                    return this.RenderAbstractCombinationStatement(((BC.Core.ASTs.AbstractCombinationStatement)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.ReturnStatement) {
                        return this.RenderReturnStatement(((BC.Core.ASTs.ReturnStatement)(_)));
                    }
                    else {
                        System.Diagnostics.Debug.Assert(false, "invalid AbstractExpressionStatement");
                        return null;
                    }
                }
            }
        }
        
        public virtual string RenderAbstractStatement(BC.Core.ASTs.AbstractStatement _) {
            if (_ is BC.Core.ASTs.AbstractExpressionStatement) {
                return this.RenderAbstractExpressionStatement(((BC.Core.ASTs.AbstractExpressionStatement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.DeclarationStatement) {
                    return this.RenderDeclarationStatement(((BC.Core.ASTs.DeclarationStatement)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.CommentStatement) {
                        return this.RenderCommentStatement(((BC.Core.ASTs.CommentStatement)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.GotoStatement) {
                            return this.RenderGotoStatement(((BC.Core.ASTs.GotoStatement)(_)));
                        }
                        else {
                            if (_ is BC.Core.ASTs.BreakStatement) {
                                return this.RenderBreakStatement(((BC.Core.ASTs.BreakStatement)(_)));
                            }
                            else {
                                if (_ is BC.Core.ASTs.ContinueStatement) {
                                    return this.RenderContinueStatement(((BC.Core.ASTs.ContinueStatement)(_)));
                                }
                                else {
                                    if (_ is BC.Core.ASTs.CompoundStatement) {
                                        return this.RenderCompoundStatement(((BC.Core.ASTs.CompoundStatement)(_)));
                                    }
                                    else {
                                        System.Diagnostics.Debug.Assert(false, "invalid AbstractStatement");
                                        return null;
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
        
        public virtual string RenderAbstractNode(BC.Core.ASTs.AbstractNode _) {
            if (_ is BC.Core.ASTs.AbstractStatement) {
                return this.RenderAbstractStatement(((BC.Core.ASTs.AbstractStatement)(_)));
            }
            else {
                if (_ is BC.Core.ASTs.AbstractDesignator) {
                    return this.RenderAbstractDesignator(((BC.Core.ASTs.AbstractDesignator)(_)));
                }
                else {
                    if (_ is BC.Core.ASTs.AbstractInitializer) {
                        return this.RenderAbstractInitializer(((BC.Core.ASTs.AbstractInitializer)(_)));
                    }
                    else {
                        if (_ is BC.Core.ASTs.AbstractType) {
                            return this.RenderAbstractType(((BC.Core.ASTs.AbstractType)(_)));
                        }
                        else {
                            if (_ is BC.Core.ASTs.AbstractExpression) {
                                return this.RenderAbstractExpression(((BC.Core.ASTs.AbstractExpression)(_)));
                            }
                            else {
                                if (_ is BC.Core.ASTs.EnumerationItem) {
                                    return this.RenderEnumerationItem(((BC.Core.ASTs.EnumerationItem)(_)));
                                }
                                else {
                                    if (_ is BC.Core.ASTs.AbstractElement) {
                                        return this.RenderAbstractElement(((BC.Core.ASTs.AbstractElement)(_)));
                                    }
                                    else {
                                        if (_ is BC.Core.ASTs.Elements) {
                                            return this.RenderElements(((BC.Core.ASTs.Elements)(_)));
                                        }
                                        else {
                                            System.Diagnostics.Debug.Assert(false, "invalid AbstractNode");
                                            return null;
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}

