//procedimiento recursivo que genera el arbol private void generar(NodoArbol nodoActual) { //Valido nodos nulos para evitar incluir condicionales en generacion de nodos cuando es nulo if (nodoActual == null) { return; } if (nodoActual.GetType() == typeof(Programa)) { Programa n = (Programa)nodoActual; generar(n.Sentencias); } else if (nodoActual.GetType() == typeof(ListaSentencia)) { ListaSentencia ls = (ListaSentencia)nodoActual; foreach (Sentencia sent in ls.getLista()) { generar(sent); } } else if (nodoActual.GetType() == typeof(Condicional)) { Emit.LocalBuilder tmpVarLogico; Condicional n = (Condicional)nodoActual; generar(n.Condicion); this.il.Emit(Emit.OpCodes.Ldc_I4_0); //Ingreso constante 0 this.il.Emit(Emit.OpCodes.Ceq); //Comparo si es falso (es 0) //Almaceno este resultado en una variable temporal tmpVarLogico = this.il.DeclareLocal(typeof(bool)); this.il.Emit(Emit.OpCodes.Stloc, tmpVarLogico); //cargo el resultado de la variable temporal this.il.Emit(Emit.OpCodes.Ldloc, tmpVarLogico); Emit.Label bloqueFalso = this.il.DefineLabel(); //salto en caso que sea verdadero el resultado es decir es cero la evaluacion del (pila==0) hago el sino this.il.Emit(Emit.OpCodes.Brtrue, bloqueFalso); generar(n.Entonces); Emit.Label finSi = this.il.DefineLabel(); this.il.Emit(Emit.OpCodes.Br, finSi); this.il.MarkLabel(bloqueFalso); generar(n.Sino); this.il.MarkLabel(finSi); } else if (nodoActual.GetType() == typeof(RepitaHasta)) { RepitaHasta n = (RepitaHasta)nodoActual; Emit.LocalBuilder tmpCondicion; tmpCondicion = this.il.DeclareLocal(typeof(bool)); Emit.Label sentenciasRepita = this.il.DefineLabel(); this.il.MarkLabel(sentenciasRepita); this.il.Emit(Emit.OpCodes.Nop); //emito primera sentencia vacia generar(n.Sentencias); generar(n.Condicion); this.il.Emit(Emit.OpCodes.Stloc, tmpCondicion); //almaceno resultado de condicion del mientras this.il.Emit(Emit.OpCodes.Ldloc, tmpCondicion); //cargo resultado de condicion del mientras this.il.Emit(Emit.OpCodes.Brfalse, sentenciasRepita); } else if (nodoActual.GetType() == typeof(Asignacion)) { Asignacion n = (Asignacion)nodoActual; generar(n.Expr); Almacenar(n.Id.Nombre.Texto, this.il); } else if (nodoActual.GetType() == typeof(LLamadaFuncion)) //Leer, Escribir { LLamadaFuncion n = (LLamadaFuncion)nodoActual; List <FuncionDef> funs = NucleoLenguaje.Instancia.getFuncBasicas(); //En la lista de definiciones de funciones estandar busco la definicion de la llamada para funcion deseada foreach (FuncionDef fun in funs) { if (n.Id.Texto.Equals(fun.Nombre.Texto)) { fun.ejecutarMetodo(il, n.Params); } } } else if (nodoActual.GetType() == typeof(NumeroEntero)) { NumeroEntero n = (NumeroEntero)nodoActual; this.il.Emit(Emit.OpCodes.Ldc_I4, convertir_a_entero(n.Token.Texto)); } else if (nodoActual.GetType() == typeof(Variable)) { Variable n = (Variable)nodoActual; if (!TablaDireccionesSimbolos.ContainsKey(n.Nombre.Texto)) { throw new System.Exception("ERROR-0008 fallo en analisis semantico Variable no declarada encontrada durante generacion '" + n.Nombre.Texto + "'"); } else { this.il.Emit(Emit.OpCodes.Ldloc, TablaDireccionesSimbolos[n.Nombre.Texto]); } } else if (nodoActual.GetType() == typeof(Suma)) { Suma n = (Suma)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Add); } else if (nodoActual.GetType() == typeof(Resta)) { Resta n = (Resta)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Sub); } else if (nodoActual.GetType() == typeof(Multiplicacion)) { Multiplicacion n = (Multiplicacion)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Mul); } else if (nodoActual.GetType() == typeof(Division)) { Division n = (Division)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Div); } else if (nodoActual.GetType() == typeof(Menor)) { Menor n = (Menor)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Clt); } else if (nodoActual.GetType() == typeof(Igual)) { Igual n = (Igual)nodoActual; generar(n.ExprIzq); generar(n.ExprDer); this.il.Emit(Emit.OpCodes.Ceq); } else { Console.WriteLine("ERROR-0006 Error tipo de Nodo no identificado"); } }