public override object Execute(Ambit ambit) { try { var val = this.value.Execute(ambit); if (val == null || val.getDataType == DataType.ERROR) { return(null); } Identifier variable = ambit.getVariable(id); /** * VALIDAR EXISTENCIA */ if (!variable.IsNull) { /** * VERIFICA QUE NO SEA CONSTABTE */ if (variable.Esconstante) { setError("No se puede cambiar el valor a una constante", row, column); return(null); } else { /** * VALIDAR VALOR: VERIFICA SI EL TIPO DE LA VARIABLE ES IGUAL AL DEL VALOR A ASIGNAR */ if (variable.DataType == val.getDataType) { ambit.setVariable(id, val.Value, val.getDataType, false, "Variable"); return(variable.Value); } else { setError("El tipo " + val.getDataType + " no es asignable con " + variable.DataType, row, column); return(null); } } } else { Function function = ambit.getFuncion(id); if (function != null) { if (function.IsProcedure) { setError("No puede asignarse ningun valor al procedimiento '" + id + "' ", row, column); return(null); } /** * VALIDAR VALOR: VERIFICA SI EL TIPO DE LA VARIABLE ES IGUAL AL DEL VALOR A ASIGNAR */ if (function.Tipe == val.getDataType) { function.Retorno = val.Value.ToString(); ambit.setFunction(Id, function); return(new Returned(function.Retorno, function.Tipe)); } else { setError("El tipo " + val.getDataType + " no es asignable con " + variable.DataType, row, column); return(null); } } else { setError("La variable '" + id + "' no esta declara", row, column); return(null); } } } catch (Exception e) { Console.WriteLine(e); ConsolaController.Instance.Add("Recuperado de error, Row:" + row + " Col: " + column); return(null); } }
public override object Execute(Ambit ambit) { try { var val = this.value.Execute(ambit); Identifier variableAmbit = ambit.getVariable(id); var generator = C3DController.Instance; /** * VALIDAR EXISTENCIA */ if (!variableAmbit.IsNull) { /** * VERIFICA QUE NO SEA CONSTABTE */ if (variableAmbit.Esconstante) { setError("No se puede cambiar el valor a una constante", row, column); return(null); } else { assignation_string += val.Texto_anterior; if (val == null || val.getDataType == DataType.ERROR) { return(null); } /** * VALIDAR VALOR: VERIFICA SI EL TIPO DE LA VARIABLE ES IGUAL AL DEL VALOR A ASIGNAR */ if (variableAmbit.DataType == val.getDataType) { if (val.IsTemporal) { ambit.free_temp(val.Value); } if (variableAmbit.IsGlobal) { if (variableAmbit.DataType == DataType.BOOLEAN) { var templabel = generator.newLabel(); assignation_string += generator.addLabel(val.TrueLabel, tabs); assignation_string += generator.set_stack(variableAmbit.Position.ToString(), "1", tabs); assignation_string += generator.add_Goto(templabel, tabs + 1); assignation_string += generator.addLabel(val.FalseLabel, tabs); assignation_string += generator.set_stack(variableAmbit.Position.ToString(), "0", tabs); assignation_string += generator.addLabel(templabel, tabs); } else { var tempAux = variableAmbit.Position_global.ToString(); if (variableAmbit.IsReference) { var temp = generator.newTemporal(); assignation_string += generator.get_stack(temp, variableAmbit.Position_global.ToString(), tabs); generator.freeTemp(temp); tempAux = temp; } assignation_string += generator.set_stack(tempAux, val.getValue(), tabs); } } else { var temp = generator.newTemporal(); ambit.set_temp(temp); assignation_string += generator.addExpression(temp, "SP", variableAmbit.Position.ToString(), "+", tabs); if (variableAmbit.IsReference) { var newTemp = generator.newTemporal(); ambit.set_temp(newTemp); ambit.free_temp(temp); generator.freeTemp(temp); assignation_string += generator.get_stack(newTemp, temp, tabs); temp = newTemp; } if (variableAmbit.DataType == DataType.BOOLEAN) { generator.freeTemp(temp); var templabel = generator.newLabel(); assignation_string += generator.addLabel(val.TrueLabel, tabs); assignation_string += generator.set_stack(temp, "1", tabs); assignation_string += generator.add_Goto(templabel, tabs + 1); assignation_string += generator.addLabel(val.FalseLabel, tabs); assignation_string += generator.set_stack(temp, "0", tabs); assignation_string += generator.addLabel(templabel, tabs); } else { generator.freeTemp(temp); assignation_string += generator.set_stack(temp, val.getValue(), tabs); } } return(assignation_string); } else { setError("El tipo " + val.getDataType + " no es asignable con " + variableAmbit.DataType, row, column); return(null); } } } else { Function function = ambit.getFuncion(id); if (function != null) { if (function.IsProcedure) { setError("No puede asignarse ningun valor al procedimiento '" + id + "' ", row, column); return(null); } /** * VALIDAR VALOR: VERIFICA SI EL TIPO DE LA VARIABLE ES IGUAL AL DEL VALOR A ASIGNAR */ if (function.Tipe == val.getDataType) { function.Retorno = val.getValue(); ambit.setFunction(Id, function); assignation_string += val.Texto_anterior; assignation_string += generator.set_stack("T13", function.Retorno, tabs); } else { setError("El tipo " + val.getDataType + " no es asignable con " + function.Tipo, row, column); return(null); } } else { setError("La variable '" + id + "' no esta declara", row, column); return(null); } } } catch (Exception e) { Console.WriteLine(e); ConsolaController.Instance.Add("Recuperado de error, Row:" + row + " Col: " + column); return(null); } return(assignation_string); }
public override Returned Execute(Ambit ambit) { { var funcion_llamada = ambit.getFuncion(this.id); if (funcion_llamada == null) { set_error("La funcion '" + this.id + "' no esta definido", row, column); return(new Returned()); } if (funcion_llamada.Parametos.Count != parametros.Count) { set_error("La funcion '" + this.id + "' no recibe la misma cantidad de parametros", row, column); return(new Returned()); } //GUARDAR LOS PARAMETROS EN LA TABLA DE SIMBOLOS Ambit function_ambit = new Ambit(); if (funcion_llamada.IsProcedure) { set_error("El procedimiento'" + this.id + "' no puede asignarse como valor de retorno", row, column); return(new Returned()); } else { function_ambit = new Ambit(ambit, "Function_" + funcion_llamada.Id, "Function", false); } //FOREACH PARA GUARDAR LOS PARAMETROS EN EL AMBITO, //LOS PARAMETROS QUE RECIBE LA FUNCION CUANDO SE DECLARA SON 'DECLARACIONES' //POR TANTO AL HACER EL EXECUTE LA VARIABLE SE GUARDA EN EL AMBITO QUE SE ENVIA foreach (var param in funcion_llamada.Parametos) { param.Execute(function_ambit); } //SE ASIGNAN LOS VALORES RECIBIDOS A LOS PARAMETROS DE LA FUNCION for (int i = 0; i < parametros.Count; i++) { var variable = (Declaration)(funcion_llamada.getParameterAt(i)); if (variable.Referencia) { if (parametros[i] is Access) { Access acceso = (Access)parametros[i]; funcion_llamada.Parametros_referencia.Add(new SimboloReferencia(variable.Id, acceso.Id)); } else if (parametros[i] is Access_array) { } } var result = ((Expression)parametros[i]).Execute(ambit); if (variable.getDataType == result.getDataType) { function_ambit.setVariableFuncion(variable.Id, result.Value, result.getDataType, false, "Parametro"); } else { set_error("El tipo " + result.getDataType + " no es asignable con " + variable.getDataType, row, column); return(new Returned()); } } //GUARDA LAS VARIABLES QUE ESTEN DECLARADAS EN LA FUNCION if (funcion_llamada.Declaraciones.Count > 0) { foreach (var declaracion in funcion_llamada.Declaraciones) { declaracion.Execute(function_ambit); } } //EJECUCION DEL CODIGO var funcion_Elementos = funcion_llamada.Sentences.Execute(function_ambit); //si viene null significa que viene error if (funcion_Elementos == null) { return(new Returned()); } else { if (funcion_llamada.IsProcedure) { if (funcion_Elementos is Instruction) { var inst = (Instruction)funcion_Elementos; if (inst.Name.Equals("Exit")) { Exit ex = (Exit)funcion_Elementos; set_error("Los procediminetos no pueden retornar ningun valor", ex.Row, ex.Column); return(new Returned()); } } if (funcion_Elementos is Break) { var r = (Break)funcion_Elementos; set_error("La sentencia Break solo puede aparece en ciclos o en la sentencia CASE", r.Row, r.Column); } else if (funcion_Elementos is Continue) { var r = (Continue)funcion_Elementos; set_error("La sentencia Continue solo puede aparece en ciclos", r.Row, r.Column); } } else { if (funcion_Elementos is Instruction) { var inst = (Instruction)funcion_Elementos; if (inst.Name.Equals("Exit")) { var response = ((Exit)funcion_Elementos); if (response.Return_func_return) { GraphController.Instance.getAmbitoGraficar(function_ambit, false); //SINTETIZA LOS PARAMETROS POR REFERENCIA sintetizar_referencia(function_ambit, funcion_llamada); switch (funcion_llamada.Tipe) { case DataType.INTEGER: return(new Returned(int.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.STRING: return(new Returned((funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.BOOLEAN: return(new Returned(bool.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.REAL: return(new Returned(double.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); } } else { var ext = (Exit)funcion_Elementos; var result = (ext).Value.Execute(function_ambit); //HAY ERROR if (result.getDataType == DataType.ERROR || result == null) { return(new Returned()); } //VERIFICA QUE EL TIPO DE RETORNO SEA VALIDO if (result.getDataType == funcion_llamada.Tipe) { //SINTETIZA LOS PARAMETROS POR REFERENCIA sintetizar_referencia(function_ambit, funcion_llamada); GraphController.Instance.getAmbitoGraficar(function_ambit, false); switch (funcion_llamada.Tipe) { case DataType.INTEGER: return(new Returned((int)result.Value, result.getDataType)); case DataType.STRING: return(new Returned((string)result.Value, result.getDataType)); case DataType.BOOLEAN: return(new Returned((bool)result.Value, result.getDataType)); case DataType.REAL: return(new Returned((double)result.Value, result.getDataType)); } } else { set_error("Tipos incompatibles, la funcion '" + funcion_llamada.Id + "' retorna " + funcion_llamada.Tipe + " en lugar de" + result.getDataType, ext.Row, ext.Column); return(new Returned()); } } } } else if (funcion_Elementos is Returned) { //SINTETIZA LOS PARAMETROS POR REFERENCIA sintetizar_referencia(function_ambit, funcion_llamada); GraphController.Instance.getAmbitoGraficar(function_ambit, false); return((Returned)funcion_Elementos); } else { //SINTETIZA LOS PARAMETROS POR REFERENCIA sintetizar_referencia(function_ambit, funcion_llamada); GraphController.Instance.getAmbitoGraficar(function_ambit, false); switch (funcion_llamada.Tipe) { case DataType.INTEGER: return(new Returned(int.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.STRING: return(new Returned((funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.BOOLEAN: return(new Returned(bool.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); case DataType.REAL: return(new Returned(double.Parse(funcion_llamada.Retorno), funcion_llamada.Tipe)); } } } } return(new Returned()); } }