Ejemplo n.º 1
0
        public override void GenCode(ICodeGenerator cg)
        {
            //Creamos los campos y asignamos los fieldBuilder a los simbolos
            var gen     = cg.GetGenerator;
            var iterVar = cg.TypeBuilder.DefineField(IterationVar + "_" + Scope.Id, typeof(int), FieldAttributes.Static | FieldAttributes.Public);

            IterationInstr.Scope.MappingDeclaration <FieldSymbol>(IterationVar).FieldBuilder = iterVar;

            //Inicializamos la variable de iteracion
            InitValue.GenCode(cg);
            gen.Emit(OpCodes.Stsfld, iterVar);

            //Creamos una variable local y le asignamos el valor de la cota superior para usarlo en las repetidas iteraciones
            var upperBound = gen.DeclareLocal(typeof(int));

            ConditionExp.GenCode(cg);
            gen.Emit(OpCodes.Stloc, upperBound);

            //Creamos los labels de inicio y fin del ciclo
            var startLoopLabel = gen.DefineLabel();
            var endLoopLabel   = gen.DefineLabel();

            //Ponemos la etiqueta del final en la pila por si hay un break dentro del ciclo
            cg.LoopsEndLabels.Push(endLoopLabel);

            //Comprobamos la condicion del ciclo
            gen.MarkLabel(startLoopLabel);
            gen.Emit(OpCodes.Ldsfld, iterVar);
            gen.Emit(OpCodes.Ldloc, upperBound);
            gen.Emit(OpCodes.Bgt, endLoopLabel);

            //Generamos el cuerpo del For
            IterationInstr.GenCode(cg);


            //Aumentamos en 1 la variable de iteracion
            gen.Emit(OpCodes.Ldsfld, iterVar);
            gen.Emit(OpCodes.Ldc_I4_1);
            gen.Emit(OpCodes.Add);
            gen.Emit(OpCodes.Stsfld, iterVar);

            //Saltamos al chequeo de la condicion nuevamente
            gen.Emit(OpCodes.Br, startLoopLabel);

            //Se termina el ciclo y se quita la etiqueta de la pila
            gen.MarkLabel(endLoopLabel);
            cg.LoopsEndLabels.Pop();
        }
Ejemplo n.º 2
0
        public override void GenCode(ICodeGenerator cg)
        {
            var gen       = cg.GetGenerator;
            var endLabel  = gen.DefineLabel();
            var loopLabel = gen.DefineLabel();

            //ponemos en la pila la etiqueta de fin de ciclo por si necesitamos hacer break dentro del ciclo saber donde saltar
            cg.LoopsEndLabels.Push(endLabel);
            gen.MarkLabel(loopLabel);            //Inicio del ciclo
            ConditionExp.GenCode(cg);
            gen.Emit(OpCodes.Brfalse, endLabel); //Si la condicion es false terminamos el ciclo

            IterationInstr.GenCode(cg);

            gen.Emit(OpCodes.Br, loopLabel);
            gen.MarkLabel(endLabel);
            cg.LoopsEndLabels.Pop();//Retiramos la etiqueta de la pila
        }