public override void visit(while_node wn)
        {
            var b = HasStatementVisitor <yield_node> .Has(wn);

            if (!b)
            {
                return;
            }

            var gotoBreak    = goto_statement.New;
            var gotoContinue = goto_statement.New;

            ReplaceBreakContinueWithGotoLabelVisitor replaceBreakContinueVis = new ReplaceBreakContinueWithGotoLabelVisitor(gotoContinue, gotoBreak);

            wn.statements.visit(replaceBreakContinueVis);

            ProcessNode(wn.statements);

            statement if0;

            //if (wn.expr is ident && (wn.expr as ident).name.ToLower() == "true")
            //    if0 = gotoBreak;
            //else
            if0 = new if_node(un_expr.Not(wn.expr), gotoBreak);
            var lb2 = new labeled_statement(gotoContinue.label, if0); // continue
            var lb1 = new labeled_statement(gotoBreak.label);         // break

            ReplaceStatement(wn, SeqStatements(lb2, wn.statements, gotoContinue, lb1));

            // в declarations ближайшего блока добавить описание labels
            block bl = listNodes.FindLast(x => x is block) as block;

            bl.defs.Add(new label_definitions(gotoBreak.label, gotoContinue.label));
        }
        public override void visit(repeat_node rn)
        {
            var b = HasStatementVisitor <yield_node> .Has(rn);

            if (!b)
            {
                return;
            }

            var gotoContinue = goto_statement.New;
            var gotoBreak    = goto_statement.New;

            ReplaceBreakContinueWithGotoLabelVisitor replaceBreakContinueVis = new ReplaceBreakContinueWithGotoLabelVisitor(gotoContinue, gotoBreak);

            rn.statements.visit(replaceBreakContinueVis);

            ProcessNode(rn.statements);

            var gotoContinueIfNotCondition = new if_node(un_expr.Not(rn.expr), gotoContinue);
            var continueLabeledStatement   = new labeled_statement(gotoContinue.label, new statement_list(rn.statements, gotoContinueIfNotCondition));

            var breakLabeledStatement = new labeled_statement(gotoBreak.label);


            ReplaceStatement(rn, SeqStatements(gotoContinue, continueLabeledStatement, breakLabeledStatement));

            // в declarations ближайшего блока добавить описание labels
            block bl = listNodes.FindLast(x => x is block) as block;

            bl.defs.Add(new label_definitions(gotoContinue.label, gotoBreak.label));
        }
        public override void visit(if_node ifn)
        {
            ProcessNode(ifn.then_body);
            ProcessNode(ifn.else_body);

            var b = HasStatementVisitor <yield_node> .Has(ifn);

            if (!b)
            {
                return;
            }

            var gtAfter = goto_statement.New;
            var lbAfter = new labeled_statement(gtAfter.label);

            if ((object)ifn.else_body == null)
            {
                var if0 = new if_node(un_expr.Not(ifn.condition), gtAfter);
                //Replace(ifn, SeqStatements(gotoStartIfCondition, ifn.then_body, lbAfter));
                ReplaceStatement(ifn, SeqStatements(if0, ifn.then_body, lbAfter));

                // в declarations ближайшего блока добавить описание labels
                block bl = listNodes.FindLast(x => x is block) as block;

                bl.defs.Add(new label_definitions(gtAfter.label));
            }
            else
            {
                var gtAlt = goto_statement.New;
                var lbAlt = new labeled_statement(gtAlt.label, ifn.else_body);

                var if0 = new if_node(un_expr.Not(ifn.condition), gtAlt);

                ReplaceStatement(ifn, SeqStatements(if0, ifn.then_body, gtAfter, lbAlt, lbAfter));

                // в declarations ближайшего блока добавить описание labels
                block bl = listNodes.FindLast(x => x is block) as block;

                bl.defs.Add(new label_definitions(gtAfter.label, gtAlt.label));
            }
        }
        public override void visit(for_node fn)
        {
            var b = HasStatementVisitor <yield_node> .Has(fn);

            if (!b)
            {
                return;
            }

            var gotoContinue = goto_statement.New;
            var gotoBreak    = goto_statement.New;
            var gotoStart    = goto_statement.New;

            ReplaceBreakContinueWithGotoLabelVisitor replaceBreakContinueVis = new ReplaceBreakContinueWithGotoLabelVisitor(gotoContinue, gotoBreak);

            fn.statements.visit(replaceBreakContinueVis);

            ProcessNode(fn.statements);

            var newNames = this.NewVarNames(fn.loop_variable);

            var newLoopVar = fn.create_loop_variable ? new ident(newNames.VarName) : fn.loop_variable;

            // Нужно заменить fn.loop_variable -> newLoopVar в теле цикла
            var replacerVis = new ReplaceVariableNameVisitor(fn.loop_variable, newLoopVar);

            fn.visit(replacerVis);

            fn.loop_variable = newLoopVar;

            var endtemp = new ident(newNames.VarEndName); //new ident(newVarName());

            //var ass1 = new var_statement(fn.loop_variable, fn.type_name, fn.initial_value);
            //var ass1 = new var_statement(fn.loop_variable, fn.type_name, fn.initial_value);
            //var ass2 = new var_statement(endtemp, fn.type_name, fn.finish_value);

            // frninja 05/06/16 - фиксим для !fn.create_variable
            var ass1 = fn.create_loop_variable
                ? new var_statement(fn.loop_variable, fn.type_name, fn.initial_value) as statement
                : new assign(fn.loop_variable, fn.initial_value) as statement;


            var if0 = new if_node((fn.cycle_type == for_cycle_type.to) ?
                                  bin_expr.Greater(fn.loop_variable, fn.finish_value) :
                                  bin_expr.Less(fn.loop_variable, fn.finish_value), gotoBreak);

            var lb2 = new labeled_statement(gotoStart.label, if0);
            var lb1 = new labeled_statement(gotoBreak.label);
            var Inc = new procedure_call(new method_call((fn.cycle_type == for_cycle_type.to) ?
                                                         new ident("Inc") :
                                                         new ident("Dec"), new expression_list(fn.loop_variable)));

            var lbInc = new labeled_statement(gotoContinue.label, Inc);

            ReplaceStatement(fn, SeqStatements(ass1, lb2, fn.statements, lbInc, gotoStart, lb1));

            // в declarations ближайшего блока добавить описание labels
            block bl = listNodes.FindLast(x => x is block) as block;

            bl.defs.Add(new label_definitions(gotoContinue.label, gotoBreak.label, gotoStart.label));
        }
        // frninja 30/05/16
        public override void visit(case_node csn)
        {
            var b = HasStatementVisitor <yield_node> .Has(csn);

            if (!b)
            {
                return;
            }

            /*
             *
             * case i of
             *   cv1: bla1;
             *   cv2: bla2;
             *   ..
             *   cvN: blaN;
             * else: bla_else;
             *
             * --->
             *
             * if i satisfy cv1
             *   then bla1
             * else if i satisfy cv2
             *   then bla2
             * ..
             * else if i satisfy cvN
             *   then blaN
             * else bla_else
             *
             */

            if_node   currentIfNode       = null;
            statement currentIfElseClause = (csn.else_statement != null) ? csn.else_statement :new statement_list(new empty_statement());;

            for (int i = csn.conditions.variants.Count - 1; i >= 0; --i)
            {
                case_variant cv = csn.conditions.variants[i];

                ProcessNode(cv.exec_if_true);

                var ifCondition = this.CreateConditionFromCaseVariant(csn.param, cv.conditions);
                currentIfNode       = new if_node(ifCondition, new statement_list(cv.exec_if_true), new statement_list(currentIfElseClause));
                currentIfElseClause = currentIfNode;
            }

            if_node finalIfNode = currentIfNode;

            if (finalIfNode == null) // SSM - значит, в цикл мы не заходили и у case отсутствуют все ветви кроме else - поскольку yieldы в case есть
            {
                ReplaceStatement(csn, csn.else_statement);
            }
            else
            {
                ReplaceStatement(csn, finalIfNode);
            }

            if (finalIfNode != null)
            {
                visit(finalIfNode);
            }
        }