Obsidean_VM/04-SIDEL/06 - E5.007363 - Modifica O.../Source/source/BlenderPID_PIDSPCalc.md

30 KiB

FUNCTION_BLOCK "BlenderPID_PIDSPCalc"
{ S7_Optimized_Access := 'FALSE' }
AUTHOR : 'Author'
FAMILY : TASK1
NAME : 'Name'
VERSION : 1.0
   VAR 
      mCriticalBlending : Bool;
      TimerConvDINT : DInt;
      TimerConvTIME : Time;
      TimerConvS5TIME : S5Time;
      mTargetRatioSlewOut : Real;
      mBevBrixDelta : Real;
      mTargetProdSlwd : "SlewLimit";
      mTargetFillerProdSlwd : "SlewLimit";
      mTargetRatioSlwd : "SlewLimit";
      mTargetSyrupLvlSlwd : "SlewLimit";
      mTargetDeairLvlSlwd : "SlewLimit";
      mTargetStorgLvlSlwd : "SlewLimit";
   END_VAR

   VAR_TEMP 
      ValBinTmr131 : Word;
      ValBcdTmr131 : S5Time;
   END_VAR


BEGIN
	
	
	IF "HMI_Blender_Parameters".Processor_Options.Blender_OPT._BrixMeter AND "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdMeterHighBrix > "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix
	   AND "AUX FALSE"  THEN
	    (* classic code: #mBevBrixDelta := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdMeterHighBrix - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix) / 2.0 ;*)
	    #mBevBrixDelta := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdMeterHighBrix - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix) / REAL#2.0 ;
	ELSE
	//    mBevBrixDelta := 0.1 ;    Pepsico Vitoria Plant - New Eurostar 2000 140 Valves 
	    (* classic code: #mBevBrixDelta := 0.06 ;*)
	    #mBevBrixDelta := REAL#0.06 ;   //Coca Cola Begano Plant - New Starcans 2000 91 Valves 
	END_IF;
	
	IF "Blender_Variables_Pers".gSugarBeverage AND "HMI_Blender_Parameters".Actual_Recipe_Parameters._SyrupBrix <> 0 THEN
	    IF "Procedure_Variables".First_Production.Latch THEN
	        "Blender_Variables".gActualSyrupPerc := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix + "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdBrixOffset + "Blender_Variables".gFirstProdExtraBrix)
	        / "Blender_Variables".gActualSyrupBrix ;
	    ELSE
	        "Blender_Variables".gActualSyrupPerc := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix + "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdBrixOffset + "Blender_Variables".gBrixTrackingCorr)
	        / "Blender_Variables".gActualSyrupBrix ;
	    END_IF;
	ELSE
	    IF "Procedure_Variables".First_Production.Latch THEN
	        "Blender_Variables".gActualSyrupPerc := 1 / ("HMI_Blender_Parameters".Actual_Recipe_Parameters._Ratio + 1 ) + "Blender_Variables".gFirstProdDietExtraSyr ;    // During First Production: syrup injection 1.2% more 
	    ELSE
	        "Blender_Variables".gActualSyrupPerc := 1 / ("HMI_Blender_Parameters".Actual_Recipe_Parameters._Ratio + 1 ) ;
	    END_IF;
	END_IF;
	
	IF "Blender_Variables_Pers".gWaterRecipe THEN
	    (* classic code: "Blender_Variables".gActualWaterPerc := 1.0 ;*)
	    "Blender_Variables".gActualWaterPerc := REAL#1.0 ;
	    (* classic code: "Blender_Variables".gActualSyrupPerc := 0.0 ;*)
	    "Blender_Variables".gActualSyrupPerc := REAL#0.0 ;
	ELSE
	    "Blender_Variables".gActualWaterPerc := 1 - "Blender_Variables".gActualSyrupPerc ;
	END_IF;
	
	IF "Blender_Variables".gActualSyrupPerc <> 0 THEN
	    (* classic code: IF "Blender_Variables".gActualSyrupDens > 0.99 AND NOT "Blender_Variables_Pers".gSugarBeverage THEN*)
	    IF "Blender_Variables".gActualSyrupDens > REAL#0.99 AND NOT "Blender_Variables_Pers".gSugarBeverage THEN
	        "Blender_Variables".gActual_RatioM := "Blender_Variables".gActualWaterPerc / ("Blender_Variables".gActualSyrupPerc * "Blender_Variables".gActualSyrupDens) ;
	    ELSE
	        "Blender_Variables".gActual_RatioM := "Blender_Variables".gActualWaterPerc / "Blender_Variables".gActualSyrupPerc ;
	    END_IF;
	END_IF;
	
	IF "Blender_Constants".gH2O_Density <> 0 THEN
	    "gActualSP_RatioVol" := "Blender_Variables".gActual_RatioM * "Blender_Variables".gActualSyrupDens / "Blender_Constants".gH2O_Density ;
	END_IF;
	
	IF "gActualSP_RatioVol" = 0 THEN
	    (* classic code: "gActualSP_RatioVol" := 0.01 ;*)
	    "gActualSP_RatioVol" := REAL#0.01 ;
	END_IF;
	
	IF "Blender_Constants".gModValveFullStrokeTime <> 0 THEN
	    "Blender_Variables".gBlenderProdSlewMax := "Blender_Variables".gBlenderNomSpeed / "Blender_Constants".gModValveFullStrokeTime ;
	    IF "Blender_Constants".gProductionSlewRate > "Blender_Variables".gBlenderProdSlewMax THEN
	         "Blender_Constants".gProductionSlewRate := "Blender_Variables".gBlenderProdSlewMax ;
	    END_IF;
	END_IF;
	
	//Limit the minimum and maximum recipe Production Rate 
	IF "Blender_Variables".gActual_Prod_SP > "Blender_Variables".gBlenderNomSpeed THEN
	    "Blender_Variables".gActual_Prod_SP := "Blender_Variables".gBlenderNomSpeed ;
	END_IF;
	
	IF "Blender_Variables".gActual_Prod_SP < "Blender_Variables".gMinProduction AND NOT "Procedure_Variables".Blender_Run.Wait THEN
	    "Blender_Variables".gActual_Prod_SP := "Blender_Variables".gMinProduction ;
	END_IF;
	
	IF "gBlenderProdMode" THEN
	//Calculates the CO2 Equilibrium Pressure plus 0.5 Atm, to Pressurize Product Tank 
	    IF "Blender_Variables_Pers".gCarboStillRecipe THEN
	        (* classic code: "Blender_Variables".gCO2EqPressure := LIMIT (MN:= 0, IN:= "CO2EqPress"(i_CO2Vol := "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols * "Blender_Variables".gFirstProdExtraCO2Fact
	                                                                                           * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact ,
	                                                                               i_Temp   := "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp ), MX:= "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdTankPress) + 0.3 ;*)
	        "Blender_Variables".gCO2EqPressure := LIMIT(MN := 0, IN := "CO2EqPress"(i_CO2Vol := "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols * "Blender_Variables".gFirstProdExtraCO2Fact
	                                                                                                                            * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact,
	                                                                                                                            i_Temp := "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp), MX := "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdTankPress) + REAL#0.8; // REAL#0.3 ;
	    ELSE
	        "Blender_Variables".gCO2EqPressure := "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdTankPress ;
	    END_IF;
	
	// Transfer the Set Point TO the PID's SP Input 
	    IF "gBlenderRinseMode" AND NOT "Procedure_Variables".TM301_Drain.Latch THEN 
	        "HMI_PID".RVM301.Sp := "HMI_Blender_Parameters".ProcessSetup._RinseTM301Press ;
	    ELSIF "Procedure_Variables".TM301_Drain.Latch THEN
	        "HMI_PID".RVM301.Sp := "HMI_Blender_Parameters".ProcessSetup._DrainTM301Press ;
	    ELSIF NOT "gWaitLevToHold_TankPress" AND NOT "Procedure_Variables".First_Production.Done  THEN
	        "HMI_PID".RVM301.Sp := "Blender_Variables".gCO2EqPressure ;
	    ELSE
	        "HMI_PID".RVM301.Sp := "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProdTankPress ;
	    END_IF;
	    
	    IF "Procedure_Variables".First_Production.Latch AND NOT "Procedure_Variables".Blender_Run.Wait THEN  //  During First Production set minimum speed 
	        "Blender_Variables".gActual_Prod_SP := "Blender_Variables".gMinProduction * "Blender_Constants".gFirstProdSpeedGain ;
	    END_IF;
	    IF "gBlenderStartPumps" AND NOT "gBlenderBlending" AND "gEnRampDownToStop" THEN  // Start blending with minimum speed
	        (* classic code: IF "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductionRate >= (0.5 * "Blender_Variables".gBlenderNomSpeed) THEN*)
	        IF "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductionRate >= (REAL#0.5 * "Blender_Variables".gBlenderNomSpeed) THEN 
	            (* classic code: "Blender_Variables".gActual_Prod_SP := 0.5 * "Blender_Variables".gBlenderNomSpeed ;*)
	            "Blender_Variables".gActual_Prod_SP := REAL#0.5 * "Blender_Variables".gBlenderNomSpeed ;
	        ELSE
	            "Blender_Variables".gActual_Prod_SP := "Blender_Variables".gMinProduction ;
	        END_IF;
	    ELSIF NOT "gEnRampDownToStop" THEN
	        "Blender_Variables".gActual_Prod_SP := "Blender_Variables".gSP_ProdTrackFiller ;
	    ELSE
	        IF NOT "Procedure_Variables".First_Production.Latch AND "gBlenderEnToRamp" THEN
	            #mTargetFillerProdSlwd(i_InValue := "Blender_Variables".gSP_ProdTrackFiller , 
	                                  i_SlewMax := "Blender_Constants".gFillerSpeedTrackSlew ,
	                                  i_Cycle   := "Time_300ms" ,
	                                  out       := "Blender_Variables".gActual_Prod_SP) ;
	        END_IF;
	        IF  "Procedure_Variables".Blender_Run.Wait THEN
	        // Stop Blender with the Maximum Slope 
	            (* classic code: #mTargetProdSlwd(i_InValue := 0.0 , 
	                            i_SlewMax := "Blender_Variables".gBlenderProdSlewMax ,
	                            i_Cycle   := "Time_300ms" ,
	                            out       := "Blender_Variables".gActual_Prod_SP ) ;*)
	            #mTargetProdSlwd(i_InValue := REAL#0.0 , 
	                            i_SlewMax := "Blender_Variables".gBlenderProdSlewMax ,
	                            i_Cycle   := "Time_300ms" ,
	                            out       := "Blender_Variables".gActual_Prod_SP ) ; // Slewed AT ""Blender_Variables".gBlenderProdSlewMax" L/sec 
	        END_IF;
	    END_IF;
	ELSE
	    (* classic code: "Blender_Variables".gActual_Prod_SP := 0.0 ;*)
	    "Blender_Variables".gActual_Prod_SP := REAL#0.0 ;
	END_IF;
	
	(* classic code: #mTargetRatioSlwd(i_InValue := "gActualSP_RatioVol",
	                 i_SlewMax := 0.02,
	                 i_Cycle   := "Time_300ms", 
	                 out       := #mTargetRatioSlewOut ) ;*)
	#mTargetRatioSlwd(i_InValue := "gActualSP_RatioVol",
	                 i_SlewMax := REAL#0.02,
	                 i_Cycle   := "Time_300ms", 
	                 out       := #mTargetRatioSlewOut ) ;    // Slewed AT 0.02 
	
	IF "Procedure_Variables".Blender_Run.Running AND NOT "gBlenderRinseMode" THEN
	    (* classic code: IF NOT "Blender_Variables_Pers".gWaterRecipe AND ("gActualSP_RatioVol" + 1.0) <> 0 THEN*)
	    IF NOT "Blender_Variables_Pers".gWaterRecipe AND ("gActualSP_RatioVol" + REAL#1.0) <> 0 THEN
	        (* classic code: "Blender_Variables".gSP_H2O := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + 1.0) * "gActualSP_RatioVol" ;*)
	        "Blender_Variables".gSP_H2O := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + REAL#1.0) * "gActualSP_RatioVol" ;
	    ELSE
	        "Blender_Variables".gSP_H2O := "Blender_Variables".gActual_Prod_SP ;
	    END_IF;
	ELSE
	    (* classic code: "Blender_Variables".gSP_H2O := 0.0 ;*)
	    "Blender_Variables".gSP_H2O := REAL#0.0 ;
	END_IF;
	
	IF "HMI_PID".RMM301.Sp > 0 THEN
	    (* classic code: IF ABS("Blender_Variables".gBlendError) > 0.5 AND ABS(("HMI_PID".RMM301.Sp - "HMI_PID".RMM301.Pv) / "HMI_PID".RMM301.Sp) > 0.2
	       AND ("Blender_Variables".gActual_Prod_SP >(0.6 * "Blender_Variables".gBlenderNomSpeed)) AND "gFlowToFiller" THEN*)
	    IF ABS("Blender_Variables".gBlendError) > REAL#0.5 AND ABS(("HMI_PID".RMM301.Sp - "HMI_PID".RMM301.Pv) / "HMI_PID".RMM301.Sp) > REAL#0.2
	       AND ("Blender_Variables".gActual_Prod_SP >(REAL#0.6 * "Blender_Variables".gBlenderNomSpeed)) AND "gFlowToFiller" THEN
	         #mCriticalBlending := TRUE ;
	    ELSE
	        #mCriticalBlending := FALSE ;
	    END_IF;
	ELSE
	    #mCriticalBlending := FALSE ;
	END_IF;
	
	#TimerConvDINT   := REAL_TO_DINT ("Blender_Constants".gModValveFullStrokeTime * 1000) ;
	#TimerConvTIME   := DINT_TO_TIME (#TimerConvDINT);
	#TimerConvS5TIME := TIME_TO_S5TIME(IN := #TimerConvTIME   // IN: TIME  FC40
	                            );                    // S5TIME
	   
	#ValBcdTmr131:= S_OFFDT (T_NO := "mCriticalBlendingTOF" ,
	                        S    := #mCriticalBlending ,
	                        TV   := #TimerConvS5TIME ,  // Timer in sec
	                        R    := "AUX FALSE" ,
	                        BI   => #ValBinTmr131 ,
	                        Q    => "gCriticalBlending" ) ;  
	
	IF ("gBlenderEnToRamp" AND ("HMI_PID".RMM301.Out > 95)) OR "gCriticalBlending" OR ("gBlenderStopping" AND "gBlenderBlending")
	    OR "HMI_Blender_Parameters".Processor_Options.Blender_OPT._TrackH2OEnable THEN
	    "PID_Variables".Track_H2O_Enable := TRUE ;
	ELSE
	    "PID_Variables".Track_H2O_Enable := FALSE ;
	END_IF;
	
	IF "Procedure_Variables".Blender_Run.Running AND NOT "Blender_Variables_Pers".gWaterRecipe AND NOT "gBlenderRinseMode" AND NOT "Procedure_Variables".FTP302Line_Preparation.Latch THEN
	    IF "gBlenderStableFlow" THEN
	        IF "PID_Variables".Track_H2O_Enable AND "gBlenderEnToRamp" THEN
	            "Blender_Variables".gSyrSPRef := "Blender_Variables".gH2O_Flow_Meas / "gActualSP_RatioVol" ;
	        ELSE
	            (* classic code: "Blender_Variables".gSyrSPRef := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + 1.0) ;*)
	            "Blender_Variables".gSyrSPRef := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + REAL#1.0) ;
	        END_IF;
	    ELSE
	        IF "PID_Variables".Track_H2O_Enable THEN
	            "Blender_Variables".gSyrSPRef := "Blender_Variables".gH2O_Flow_Meas / "gActualSP_RatioVol" ;
	        ELSE
	            (* classic code: "Blender_Variables".gSyrSPRef := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + 1.0) ;*)
	            "Blender_Variables".gSyrSPRef := "Blender_Variables".gActual_Prod_SP / ("gActualSP_RatioVol" + REAL#1.0) ;
	        END_IF;
	    END_IF;
	    (* classic code: "Blender_Variables".gSyrSPTemp := LIMIT(MN:= (-1.0 * "Blender_Variables".gSyrSPRef * "Blender_Constants".gSyrupSPRecFact), 
	                                            IN:= ("Blender_Variables".gBlendError * "Blender_Variables".gK_RecBlendError), 
	                                            MX:= ("Blender_Variables".gSyrSPRef * "Blender_Constants".gSyrupSPRecFact));*)
	    "Blender_Variables".gSyrSPTemp := LIMIT(MN:= (REAL#-1.0 * "Blender_Variables".gSyrSPRef * "Blender_Constants".gSyrupSPRecFact), 
	                                            IN:= ("Blender_Variables".gBlendError * "Blender_Variables".gK_RecBlendError), 
	                                            MX:= ("Blender_Variables".gSyrSPRef * "Blender_Constants".gSyrupSPRecFact));             
	                                            
	    "Blender_Variables".gSP_SYR := ("Blender_Variables".gSyrSPRef + "Blender_Variables".gSyrSPTemp) * "Blender_Variables".gActualSyrupDens ;
	ELSIF "Procedure_Variables".FTP302Line_Preparation.Latch OR "Procedure_Variables".FTP302_StartUp.Latch THEN
	    "Blender_Variables".gSP_SYR := "Blender_Constants".gTP301_FirstProdRate; 
	ELSIF  "gSyrupQcoRinse" THEN
	    "Blender_Variables".gSP_SYR := "Blender_Constants".gTP301_RinseRate;
	ELSE    
	    (* classic code: "Blender_Variables".gSP_SYR := 0.0 ;*)
	    "Blender_Variables".gSP_SYR := REAL#0.0 ;
	END_IF;
	
	"Blender_Variables".gDeairCO2Comp := "DeairCO2TempComp"(i_Temp   := "HMI_Instrument".TTN321.PVFiltered,
	                                                             i_CO2Off := "HMI_Blender_Parameters".Processor_Options.Blender_OPT._CO2_Offset) ;
	"Blender_Variables".gWaterO2 := "PPM O2"(i_Temp := "HMI_Instrument".TTN321.PVFiltered);
	"Blender_Variables".gSyrupO2 := "PPM O2"(i_Temp := "Profibus_Variables".gFTP302_Temp) * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._SyrupBrix / 100) ;
	IF ("Blender_Variables".gActual_RatioM + 1) <> 0 THEN
	    "Blender_Variables".gProductO2 := ("Blender_Variables".gActual_RatioM * "Blender_Variables".gDeairWaterO2 + "Blender_Variables".gSyrupO2) / ("Blender_Variables".gActual_RatioM + 1) ;
	END_IF;
	"Blender_Variables".gCO2Solubility := "CO2 Solubility"(i_Temp :="HMI_Instrument".TTN321.PVFiltered) *"Blender_Constants".gTN301Efficiency ;
	IF "gBlenderEnToRamp" OR "gBlenderRinseMode" OR "gBlenderCIPMode" OR "Procedure_Variables"."CarboWaterLine".Latch THEN
	    "Blender_Variables".gDeairCO2Vol := "MaxCarboCO2 Vol"(i_Temp  := "HMI_Instrument".TTN321.PVFiltered,
	                                                          i_Press := "Blender_Constants".gTN301Pressure) * "Blender_Constants".gTN301Efficiency ;
	END_IF;
	
	IF NOT "gOUT_PPN304_Run" THEN 
	    "Blender_Variables".gDeairCO2Comp := "Blender_Variables".gDeairCO2Vol - "HMI_Blender_Parameters".Processor_Options.Blender_OPT._CO2_Offset ;
	ELSE 
	    (* classic code: "Blender_Variables".gDeairCO2Comp := 0.0 ;*)
	    "Blender_Variables".gDeairCO2Comp := REAL#0.0 ;
	END_IF ;
	    
	"Blender_Variables".gFillerCO2Loss := "HMI_Blender_Parameters".Processor_Options.Blender_OPT._CO2_Offset ;
	
	IF "Procedure_Variables".First_Production.Latch THEN
	    (* classic code: "Blender_Variables".gActual_SP_CO2 := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols - "Blender_Variables".gDeairCO2Comp) * "Blender_Variables".gFirstProdExtraCO2Fact
	     * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / 100.0) ;*)
	    "Blender_Variables".gActual_SP_CO2 := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols - "Blender_Variables".gDeairCO2Comp) * "Blender_Variables".gFirstProdExtraCO2Fact
	     * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / REAL#100.0) ;    // nL/MIN 
	ELSE
	    (* classic code: "Blender_Variables".gActual_SP_CO2 := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols - "Blender_Variables".gDeairCO2Comp + "Blender_Variables".gCO2TrackingCorr) * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact
	                                          * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / 100.0) ;*)
	    "Blender_Variables".gActual_SP_CO2 := ("HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Vols - "Blender_Variables".gDeairCO2Comp + "Blender_Variables".gCO2TrackingCorr) * "HMI_Blender_Parameters".Actual_Recipe_Parameters._CO2Fact
	                                          * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / REAL#100.0) ;    // nL/MIN 
	END_IF;
	
	IF "gBlenderBlending" AND "Blender_Variables_Pers".gCarboStillProduct AND "gBlenderStableFlow" AND NOT "gBlenderRinseMode" THEN
	    "Blender_Variables".gCO2SPRef := "Blender_Variables".gActual_SP_CO2 * "Blender_Variables".gActual_Prod_Flow ;
	    "Blender_Variables".gCO2SPTemp2 := "Blender_Variables".gCarboCO2Error * "Blender_Variables".gK_RecCarboCO2Error ;
	ELSIF "gBlenderBlending" AND NOT "gBlenderStableFlow" AND "Blender_Variables_Pers".gCarboStillProduct AND NOT "gBlenderRinseMode" THEN
	    "Blender_Variables".gCO2SPRef := "Blender_Variables".gActual_SP_CO2 * "Blender_Variables".gActual_Prod_SP ;
	    "Blender_Variables".gCO2SPTemp2 := "Blender_Variables".gCarboCO2Error * "Blender_Variables".gK_RecCarboCO2Error ;
	ELSIF "gP_CarboPipe_En" AND "Blender_Variables_Pers".gCarboStillProduct AND NOT "gBlenderRinseMode" THEN
	    IF "gActualSP_RatioVol" <> 0 AND NOT "Blender_Variables_Pers".gWaterRecipe THEN
	        "Blender_Variables".gCO2SPRef := "Blender_Variables".gActual_SP_CO2 *("Blender_Variables".gH2O_Flow_Meas +
	                                         "Blender_Variables".gH2O_Flow_Meas / "gActualSP_RatioVol") ;
	        (* classic code: "Blender_Variables".gCO2SPTemp2 := 0.0 ;*)
	        "Blender_Variables".gCO2SPTemp2 := REAL#0.0 ;
	    ELSE
	        "Blender_Variables".gCO2SPRef := ("Blender_Variables".gActual_SP_CO2 * "Blender_Variables".gActual_Prod_Flow) ;
	        (* classic code: "Blender_Variables".gCO2SPTemp2 := 0.0 ;*)
	        "Blender_Variables".gCO2SPTemp2 := REAL#0.0 ;
	    END_IF;
	(*ELSIF "HMI_Service".Workshop_Test.CO2TestRequest AND "gWorkshopTest" THEN
	    "Blender_Variables".gCO2SPRef := "HMI_Service".Workshop_Test.SIMCO2_Test_SP ;
	    (* classic code: "Blender_Variables".gCO2SPTemp2 := 0.0 ;*)
	    "Blender_Variables".gCO2SPTemp2 := REAL#0.0 ;*)
	ELSE
	    (* classic code: "Blender_Variables".gCO2SPRef := 0.0 ;*)
	    "Blender_Variables".gCO2SPRef := REAL#0.0 ;
	    (* classic code: "Blender_Variables".gCO2SPTemp2 := 0.0 ;*)
	    "Blender_Variables".gCO2SPTemp2 := REAL#0.0 ;
	END_IF;
	
	(* classic code: "Blender_Variables".gCO2SPTemp := LIMIT(MN:= (-1.0 * "Blender_Variables".gCO2SPRef * "Blender_Constants".gCO2SPRecFact), 
	                                        IN:= ("Blender_Variables".gCO2SPTemp2), 
	                                        MX:= ("Blender_Variables".gCO2SPRef * "Blender_Constants".gCO2SPRecFact));*)
	"Blender_Variables".gCO2SPTemp := LIMIT(MN:= (REAL#-1.0 * "Blender_Variables".gCO2SPRef * "Blender_Constants".gCO2SPRecFact), 
	                                        IN:= ("Blender_Variables".gCO2SPTemp2), 
	                                        MX:= ("Blender_Variables".gCO2SPRef * "Blender_Constants".gCO2SPRecFact));
	
	"Blender_Variables".gSP_CO2 := "Blender_Variables".gCO2SPRef + "Blender_Variables".gCO2SPTemp ;
	
	// SECOND GAS INJECTION
	IF "HMI_Blender_Parameters".Processor_Options.Blender_OPT._CO2_GAS2_Injection THEN
	    (* classic code: "Blender_Variables".gActual_SP_GAS2 := "HMI_Blender_Parameters".Actual_Recipe_Parameters._Gas2Vols * "HMI_Blender_Parameters".Actual_Recipe_Parameters._Gas2Fact 
	                                           * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / 100.0) ;*)
	    "Blender_Variables".gActual_SP_GAS2 := "HMI_Blender_Parameters".Actual_Recipe_Parameters._Gas2Vols * "HMI_Blender_Parameters".Actual_Recipe_Parameters._Gas2Fact 
	                                           * (1 - "HMI_Blender_Parameters".Actual_Recipe_Parameters._ProductBrix / REAL#100.0) ;    // nL/MIN 
	    IF "gBlenderBlending" AND "gBlenderStableFlow" AND NOT "gBlenderRinseMode" THEN
	        "Blender_Variables".gSP_GAS2 := "Blender_Variables".gActual_SP_GAS2 * "Blender_Variables".gActual_Prod_Flow ;
	    ELSIF "gBlenderBlending" AND NOT "gBlenderStableFlow" AND NOT "gBlenderRinseMode" THEN
	        "Blender_Variables".gSP_GAS2 := "Blender_Variables".gActual_SP_GAS2 * "Blender_Variables".gActual_Prod_SP ;
	    ELSE
	        (* classic code: "Blender_Variables".gSP_GAS2 := 0.0 ;*)
	        "Blender_Variables".gSP_GAS2 := REAL#0.0 ;
	    END_IF ;
	ELSE
	    (* classic code: "Blender_Variables".gSP_GAS2 := 0.0 ;*)
	    "Blender_Variables".gSP_GAS2 := REAL#0.0 ;    
	END_IF ;
	
	//"HMI_PID".RMM301.SP := "Blender_Variables".gSP_H2O ;
	//"HMI_PID".RMP302.SP := "Blender_Variables".gSP_SYR ;
	
	(* classic code: "Blender_Variables".gMaxCarboCO2_V := "MaxCarboCO2 Vol"(i_Temp  := "HMI_Instrument".TTN321.PVFiltered ,
	                                                        i_Press := "HMI_Blender_Parameters".ProcessSetup._PPN301Pressure - 1.5 ) ;*)
	"Blender_Variables".gMaxCarboCO2_V := "MaxCarboCO2 Vol"(i_Temp  := "HMI_Instrument".TTN321.PVFiltered ,
	                                                        i_Press := "HMI_Blender_Parameters".ProcessSetup._PPN301Pressure - REAL#1.5 ) ;
	IF NOT ("gP_CarboPipe_En" OR ("HMI_Service".Workshop_Test.CO2TestRequest AND "gWorkshopTest")) THEN
	    "Blender_Variables".gSP_CO2 := LIMIT(MN:= 0, IN:= "Blender_Variables".gSP_CO2, MX:= ("Blender_Variables".gMaxCarboCO2_V * "Blender_Variables".gSP_H2O)) ;
	END_IF;
	
	IF "gBlenderProdMode" THEN
	    IF "gBlenderRinseMode" AND NOT "System_RunOut_Variables".FastChangeOverActivated THEN
	        "Blender_Variables".gSP_SYR_Level  := "Blender_Constants".gTP301FirstProdLvl;
	    ELSIF "Procedure_Variables".FTP302Line_Preparation.Latch OR "Procedure_Variables".FTP302_StartUp.Latch THEN
	        "Blender_Variables".gSP_SYR_Level := "Blender_Constants".gTP301FirstProdLvl;
	    ELSIF "Procedure_Variables".First_Production.Running AND "gBlenderBlending" THEN
	         #mTargetSyrupLvlSlwd(i_InValue:="Blender_Constants".gTP301ProdLvl , 
	                             i_SlewMax:="Blender_Constants".gTP301_LvlSlewRate , 
	                             i_Cycle:="Time_300ms" , 
	                             out:="Blender_Variables".gSP_SYR_Level ) ;
	    ELSIF "Procedure_Variables".Syr_RunOut.Latch AND "gBlenderBlending" THEN
	        #mTargetSyrupLvlSlwd(i_InValue:="Blender_Constants".gTP301FirstProdLvl , 
	                             i_SlewMax:="Blender_Constants".gTP301_LvlSlewRate , 
	                             i_Cycle:="Time_300ms" , 
	                             out:="Blender_Variables".gSP_SYR_Level ) ;
	        "Blender_Variables".gSP_SYR_Level := "Blender_Constants".gTP301ProdLvl;
	    ELSIF "System_RunOut_Variables".FastChangeOverActivated AND "gSyrupQcoRinse" THEN
	        "Blender_Variables".gSP_SYR_Level  := "HMI_Blender_Parameters".ProcessSetup._CIPTP301MinLevel;
	    ELSIF "Procedure_Variables".First_Production.Done AND NOT "Procedure_Variables".Syr_RunOut.Latch THEN
	        "Blender_Variables".gSP_SYR_Level := "Blender_Constants".gTP301ProdLvl;
	    END_IF ;
	ELSE
	    IF "HMI_Variables_Status".Procedures.CIP_SyrTankFloodRun THEN
	        (* classic code: "Blender_Variables".gSP_SYR_Level := 100.0 ;*)
	        "Blender_Variables".gSP_SYR_Level := REAL#100.0 ;
	    ELSE
	        "Blender_Variables".gSP_SYR_Level := "HMI_Blender_Parameters".ProcessSetup._CIPTP301MinLevel;
	    END_IF ;
	END_IF;
	
	IF "gBlenderProdMode" THEN
	    IF "gBlenderRinseMode" THEN
	        "Blender_Variables".gSP_DEAIR_Level  := "HMI_Blender_Parameters".ProcessSetup._CIPTN301MinLevel;
	    ELSIF "Procedure_Variables".TN301_StartUp.Latch OR ("Procedure_Variables".First_Production.Running AND "gBlenderBlending") THEN
	         #mTargetDeairLvlSlwd(i_InValue:="Blender_Constants".gTN301ProdLvl , 
	                             i_SlewMax:="Blender_Constants".gTN301_LvlSlewRate , 
	                             i_Cycle:="Time_300ms" , 
	                             out:="Blender_Variables".gSP_DEAIR_Level ) ;
	    ELSIF "Procedure_Variables".First_Production.Done THEN
	        "Blender_Variables".gSP_DEAIR_Level := "Blender_Constants".gTN301ProdLvl;
	    END_IF ;
	ELSE
	    IF "HMI_Variables_Status".Procedures.CIP_DeairTankFloodRun THEN
	        (* classic code: "Blender_Variables".gSP_DEAIR_Level := 100.0 ;*)
	        "Blender_Variables".gSP_DEAIR_Level := REAL#100.0 ;
	    ELSE
	        "Blender_Variables".gSP_DEAIR_Level := "HMI_Blender_Parameters".ProcessSetup._CIPTN301MinLevel;
	    END_IF ;
	END_IF;
	
	IF "gBlenderProdMode" THEN
	    IF "Procedure_Variables".BlendFill_StartUp.Latch THEN
	         #mTargetStorgLvlSlwd(i_InValue:="Blender_Variables".gProdTankTargetLvl , 
	                             i_SlewMax:="Blender_Constants".gTM301_LvlSlewRate , 
	                             i_Cycle:="Time_300ms" , 
	                             out:="Blender_Variables".gSP_STORAGE_Level ) ;
	    ELSIF "Procedure_Variables".First_Production.Done THEN
	        "Blender_Variables".gSP_STORAGE_Level := "Blender_Variables".gProdTankTargetLvl ;
	    END_IF ;
	END_IF;
	
	IF "gBlenderProdMode" THEN
	    IF "gProductChillerEn" OR "gProdDoubleChillerEn" THEN
	        "Blender_Variables".gSP_H2O_Temperature := "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp ;
	        "Blender_Variables".gSP_Prod_Temperature := "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp ;
	    ELSIF "gWaterChillerEn" THEN
	        "Blender_Variables".gSP_H2O_Temperature := "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp - ("Blender_Constants".gCpSyrup
	            * ("Blender_Variables".gMeterSyrTemp - "HMI_Blender_Parameters".Actual_Recipe_Parameters._SP_ProdTemp) * "Blender_Variables".gActualSyrupDens / "Blender_Constants".gCpH2O) ;
	    END_IF;
	    IF "HMI_Variables_Status".Procedures.ColdRinseRun OR "Procedure_Variables".First_Production.Latch OR "Procedure_Variables"."CarboWaterLine".Latch  THEN
	        "Blender_Variables".gSP_H2O_Temperature := "Blender_Constants".gFirstProdRinseTempSP ;
	        "Blender_Variables".gSP_Prod_Temperature := "Blender_Constants".gFirstProdRinseTempSP ;
	    END_IF;
	ELSIF "gBlenderCIPMode" AND "gGencoldChillerEn" THEN
	    (* classic code: "Blender_Variables".gSP_H2O_Temperature := 0.0 ;*)
	    "Blender_Variables".gSP_H2O_Temperature := REAL#0.0 ;
	    (* classic code: "Blender_Variables".gSP_Prod_Temperature := 0.0 ;*)
	    "Blender_Variables".gSP_Prod_Temperature := REAL#0.0 ;
	ELSE
	    (* classic code: "Blender_Variables".gSP_H2O_Temperature := 100.0 ;*)
	    "Blender_Variables".gSP_H2O_Temperature := REAL#100.0 ;
	    (* classic code: "Blender_Variables".gSP_Prod_Temperature := 100.0 ;*)
	    "Blender_Variables".gSP_Prod_Temperature := REAL#100.0 ;
	END_IF;
	
	IF "gBlenderProdMode" AND "HMI_Device".RVN301.Out OR "Procedure_Variables".TN301_StartUp.Latch THEN
	    IF "gBlenderRinseMode" OR "Procedure_Variables"."CarboWaterLine".Running THEN
	        (*"HMI_PID".RVN304.Sp := "Blender_Variables".gH2O_Flow_Meas *"HMI_Blender_Parameters".Actual_Recipe_Parameters._DeareationFactor;*)
	        "HMI_PID".RVN304.Sp := "Blender_Variables".gH2O_Flow_Meas *0.7 ;
	       ;
	    ELSE
	        "HMI_PID".RVN304.Sp := "Blender_Variables".gH2O_Flow_Meas * "HMI_Blender_Parameters".Actual_Recipe_Parameters._DeareationFactor;
	    END_IF ;
	    IF  "gDeairTank_Loading" OR (NOT "HMI_Digital".LSN301L.Filtered  AND NOT "Procedure_Variables".TN301_StartUp.Done) THEN
	        "HMI_PID".RVN304.Sp := "Blender_Variables".gBlenderNomSpeed * "HMI_Blender_Parameters".Actual_Recipe_Parameters._DeareationFactor;
	    ELSIF "HMI_Digital".LSN301L.Filtered AND NOT "Procedure_Variables".TN301_StartUp.Done THEN
	        "HMI_PID".RVN304.Sp := "Blender_Variables".gMinProduction ;
	    END_IF ;
	    IF NOT "Blender_Variables_Pers".gCarboStillRecipe OR NOT "HMI_Blender_Parameters".Processor_Options.Blender_OPT._Deaireation THEN
	        "HMI_PID".RVN304.Sp := "HMI_PID".RVN304.Sp / 10 ;
	    END_IF ;
	ELSE
	    (* classic code: "HMI_PID".RVN304.Sp := 0.0;*)
	    "HMI_PID".RVN304.Sp := REAL#0.0;
	END_IF ;
	
	IF NOT "HMI_Device".AVN347.Out AND NOT "HMI_Blender_Parameters".Processor_Options.Blender_OPT._Flowtronic THEN
	    "HMI_PID".RVN304.Sp := "HMI_Instrument".RVN304.PVFiltered ;
	END_IF ;
	
	
END_FUNCTION_BLOCK