123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681 |
- using System;
- using Aitex.Core.Equipment.SusceptorDefine;
- using Aitex.Core.RT.Event;
- using Aitex.Core.RT.Routine;
- using Aitex.Core.RT.SCCore;
- using MECF.Framework.Common.DBCore;
- using VirgoCommon;
- //using Virgo.Common;
- using VirgoRT.Devices;
- namespace VirgoRT.Modules.PMs
- {
- public enum MonitorStepState
- {
- Continue,
- Failed,
- Break,
- }
- class PMRoutineBase : ModuleRoutine
- {
- // ----------------------------Fields--------------------------
- //
- //private SCConfigItem scOpenGasValveTimeout = null;
- private int dOpenGasValveTimeout = 1; //1S
- //private SCConfigItem scCloseGasValveTimeout = null;
- public int dCloseGasValveTimeout = 2; //2s
- //private SCConfigItem scOpenCloseSlitValveTimeout = null;
- protected int valveOpenCloseTimeout = 2; //2s
- protected int _PressureTrip1 = 80;
- protected bool bUINotify;
- protected readonly JetPM _chamber;
- // --------------------------Properties------------------------
- //
- public string Display { get; set; }
- public string WaferID { get; set; }
- // Constructor
- protected PMRoutineBase(JetPM chamber)
- {
- this.Module = chamber.Module.ToString();
- _chamber = chamber;
- bUINotify = true;
- dOpenGasValveTimeout = SC.GetValue<int>($"{Module}.OpenGasValveTimeout");
- dCloseGasValveTimeout = SC.GetValue<int>($"{Module}.TimeLimitOfCloseGasValve");
- valveOpenCloseTimeout = SC.GetValue<int>($"{Module}.OpenCloseSlitValveTimeout");
- }
- public Result CheckLid()
- {
- if (!_chamber.IsLidClosed)
- {
- this.Stop("Chamber 盖子必须关");
- return Result.FAIL;
- }
- return Result.RUN;
- }
- protected Result CheckSlitDoor()
- {
- if (!_chamber.IsSlitDoorClosed)
- {
- Stop("传送门必须关");
- return Result.FAIL;
- }
- return Result.RUN;
- }
- protected Result CheckDryPump()
- {
- if (!_chamber.IsPumpRunning)
- {
- Stop("泵没有启动");
- return Result.FAIL;
- }
- if (_chamber.HasPumpError)
- {
- Stop("泵状态有错误");
- return Result.FAIL;
- }
- return Result.RUN;
- }
- public void CheckThrottleValveFullOpen(int id)
- {
- bool execute()
- {
- Notify("完全打开蝶阀");
- _chamber.FullOpenTV();
- return true;
- }
- bool? Check1()
- {
- if (_chamber.TVPosition >= 98)
- {
- Notify("蝶阀已经完全打开");
- return true;
- }
- return false;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, execute, Check1, 20 * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- Stop("无法打开蝶阀");
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- Stop("启动蝶阀超时");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected Result CheckCDA()
- {
- if (!_chamber.IsCDA_OK)
- {
- Stop("CDA 压力信号不正确");
- return Result.FAIL;
- }
- return Result.RUN;
- }
- protected void CloseAllValve(int id, int time)
- {
- bool execute()
- {
- Notify("关闭所有的阀门");
- _chamber.CloseValves();
- return true;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, execute, () => true, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void SetValve(int id, ValveType vlv, bool bOpen)
- {
- bool exec()
- {
- _chamber.SetValveOnOff(vlv, bOpen);
- Notify($"{(bOpen ? "打开" : "关闭")} {vlv} 阀");
- return true;
- }
- bool? Check1()
- {
- if (vlv == ValveType.FAST_PUMP && bOpen)
- return _chamber.IsFastPumpOpened;
- else if (vlv == ValveType.FAST_PUMP && !bOpen)
- return !_chamber.IsFastPumpOpened;
- else if (vlv == ValveType.SOFT_PUMP && bOpen)
- return _chamber.IsSoftPumpOpened;
- else if (vlv == ValveType.SOFT_PUMP && !bOpen)
- return !_chamber.IsSoftPumpOpened;
- else
- return true;
- }
- var res = ExecuteAndWait(id, exec, Check1, 500);
- if (res.Item1)
- {
- throw new RoutineBreakException();
- }
- }
- protected void CheckATM2(int id, bool on, int time)
- {
- bool? check()
- {
- //if (!_chamber.IsATM)
- //{
- // Notify("ATM is OFF");
- //}
- return on ? _chamber.IsATM : !_chamber.IsATM;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
- {
- Notify($"等待 ATM 信号 {(on ? "ON" : "OFF")}");
- return true;
- }, check, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL || ret.Item2 == Result.TIMEOUT)
- {
- Stop($"ATM 信号仍然 {(_chamber.IsATM ? "ON" : "OFF")}");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckPressure(int id, int targetPressure, bool morethan, int time)
- {
- bool? Check1()
- {
- bool res = morethan ? _chamber.ChamberPressure > targetPressure : _chamber.ChamberPressure < targetPressure;
- if (res)
- {
- Notify($"压力已经到达 {targetPressure:N} mTorr");
- }
- return res;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
- {
- Notify($"等待压力{(morethan ? "上升" : "下降")} 到 {targetPressure:N} mTorr");
- return true;
- }, Check1, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- Stop($"当前压力 [{_chamber.ChamberPressure}], 无法到达 [{targetPressure}]");
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- Stop($"检测压力超时, 当前压力 [{_chamber.ChamberPressure*0.001:F2}] Torr");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckForeline(int id, uint target, int time)
- {
- bool Func()
- {
- Notify($"Check foreline pressure, 目标 {target} mTorr");
- return true;
- }
- bool? Check1()
- {
- return _chamber.ForelinePressure < target;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, Func, Check1, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- Stop($"检查Foreline 压力超时, 当前Foreline 压力值 {_chamber.ForelinePressure}");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckVAC(int id, double targetPressure, int time)
- {
- bool? Check1()
- {
- if (_chamber.ChamberPressure < targetPressure)
- {
- Notify($"Pump below [{targetPressure}]");
- return true;
- }
- return false;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, () => true, Check1, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT) //timeout
- {
- //Warning($"Can not pump to base pressure {target} in {time} seconds");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckVAC(int id, int time)
- {
- Tuple<bool, Result> ret = ExecuteAndWait(id, () => true, () => _chamber.IsVAC, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- Stop("VAC真空信号 NOT ON");
- throw new RoutineFaildException();
- }
- if (Result.TIMEOUT == ret.Item2)
- {
- Stop($"VAC 真空信号超时, 当前压力 {_chamber.ChamberPressure}");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- public void SetLiftPinUpDown(int id, bool isUp, int timeout)
- {
- Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
- {
- Notify($"设置 lift pin {_chamber.Name} " + (isUp ? "升" : "降"));
- if (!_chamber.SetLiftPin(isUp ? MovementPosition.Up : MovementPosition.Down, out string reason))
- {
- Stop(reason);
- return false;
- }
- return true;
- }, () => isUp ? _chamber.CheckLiftUp() : _chamber.CheckLiftDown(), timeout * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- else if (ret.Item2 == Result.TIMEOUT) //timeout
- {
- Stop($"无法 {(isUp ? "Up" : "Down")} lift pin in {timeout} seconds");
- throw new RoutineFaildException();
- }
- else
- throw new RoutineBreakException();
- }
- }
- protected void End(int id)
- {
- bool Func()
- {
- double duration_min = counter.GetElapseTime();
- TimeSpan ts = TimeSpan.FromMilliseconds(duration_min);
- string info = $"完成 in {ts.Minutes} minutes {ts.Seconds} seconds";
- Notify(info);
- //if (bUINotify)
- // EV.PostPopDialogMessage(EventLevel.Information, Name, $"{Module} {info} Finished");
- return true;
- }
- Tuple<bool, Result> ret = Execute(id, Func);
- }
- public virtual void Abort()
- {
- _chamber.GeneratorPowerOn(false);
- _chamber.GeneratorBiasPowerOn(false);
- _chamber.StopAllGases();
- //ProcessDataRecorder.UpdateStatus(RecipeRunGuid.ToString(), SusceptorStatus.Failed.ToString(), Module);
- }
- /// <summary>
- ///
- /// </summary>
- /// <param name="stepId"></param>
- /// <param name="delayTime">单位:秒</param>
- public void CloseValve(int stepId, float delayTime)
- {
- bool Func()
- {
- Notify("Vent End Close Vent Valve");
- _chamber.SetValveOnOff(ValveType.PURGE, false);
- _chamber.SetValveOnOff(ValveType.FAST_VENT, false);
- _chamber.SetValveOnOff(ValveType.PROCESS, false);
- //_chamber.OpenValve(ValveType.SOFT_PUMP, true);
- //_chamber.OpenValve(ValveType.FAST_PUMP, true);
- return true;
- }
- Tuple<bool, Result> ret = Delay(stepId, Func, delayTime * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
-
- protected void StartLoop(int id, string name, int count, Action<string> notify, Action<string> error)
- {
- bool Func()
- {
- Notify($"{name} 循环 {LoopCounter + 1}");
- return true;
- }
- Tuple<bool, Result> ret = Loop(id, Func, count);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- throw new RoutineFaildException();
- }
- }
- protected void EndLoop(int id, Action<string> notify, Action<string> error)
- {
- Tuple<bool, Result> ret = EndLoop(id, () => true);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- throw new RoutineFaildException();
- throw new RoutineBreakException();
- }
- }
- protected void CyclePump(int id, int target, int timeLimit, bool isStopPumpOnceDone)
- {
- bool Func()
- {
- Notify($"Pumping to {target} mTorr");
- _chamber.SetValveOnOff(ValveType.PROCESS, false);
- _chamber.SetValveOnOff(ValveType.PURGE, false);
- _chamber.SetValveOnOff(ValveType.FAST_VENT, false);
- _chamber.SetValveOnOff(ValveType.FAST_PUMP, true);
- return true;
- }
- bool? Check1()
- {
- if (_chamber.ChamberPressure < target)
- {
- if (isStopPumpOnceDone)
- {
- _chamber.SetValveOnOff(ValveType.FAST_PUMP, false);
- }
- return true;
- }
- return true;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, Func, Check1, timeLimit * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- Stop($"Pump 压力无法到达 {target} in time {timeLimit}");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CycleVent(int id, int target, int timeLimit, bool isStopVentOnceDone)
- {
- bool Func()
- {
- Notify($"Venting to {target} mTorr");
- _chamber.SetValveOnOff(ValveType.FAST_PUMP, false);
- _chamber.SetValveOnOff(ValveType.PROCESS, true);
- _chamber.SetValveOnOff(ValveType.PURGE, true);
- return true;
- }
- bool? Check1()
- {
- if (_chamber.ChamberPressurePressure > target)
- {
- if (isStopVentOnceDone)
- {
- _chamber.SetValveOnOff(ValveType.PROCESS, false);
- _chamber.SetValveOnOff(ValveType.PURGE, false);
- _chamber.SetValveOnOff(ValveType.FAST_VENT, false);
- }
- return true;
- }
- return false;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, Func, Check1, timeLimit * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT) //timeout
- {
- Stop($"Purge 压力无法到达 {target} in purge time {timeLimit}");
- if (isStopVentOnceDone)
- {
- _chamber.SetValveOnOff(ValveType.PROCESS, false);
- _chamber.SetValveOnOff(ValveType.PURGE, false);
- _chamber.SetValveOnOff(ValveType.FAST_VENT, false);
- }
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckSubstrateTemp(int id, double target, int time, double tolerance)
- {
- bool Func()
- {
- if (_chamber.SubstrateTempFB > target)
- {
- Notify($"当前温度{_chamber.SubstrateTempFB} ℃, 大于目标 {target.ToString()} ℃");
- //return true;
- }
- _chamber.HeatSubstrate(target);
- Notify($"检查底座温度值,当前温度{_chamber.SubstrateTempFB} ℃, 目标 {target.ToString()} ℃");
- return true;
- }
- bool? Check1()
- {
- if (Math.Abs( target) <= 0.1)
- return true;
- if (Math.Abs(_chamber.SubstrateTempFB - target) <= tolerance)
- return true;
-
- return false;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, Func, Check1, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- Stop($"检查底座温度超时, 当前底座温度值 {_chamber.SubstrateTempFB}");
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void CheckCoolantTemp(int id, double target, double offset, int time, double tolerance)
- {
- bool Func()
- {
- if (_chamber.CoolantOutletTempFB > target)
- {
- Notify($"水冷当前温度{_chamber.CoolantOutletTempFB} ℃, 大于目标 {target.ToString()} ℃");
- //return true;
- }
- _chamber.HeatChiller(target, offset);
- Notify($"检查水冷温度值,当前温度{_chamber.CoolantOutletTempFB} ℃, 目标 {target.ToString()} ℃");
- return true;
- }
- bool? Check1()
- {
- if (!_chamber.CheckChillerStatus())
- return false;
-
- return Math.Abs(_chamber.CoolantOutletTempFB - target) <= tolerance;
- }
- Tuple<bool, Result> ret = ExecuteAndWait(id, Func, Check1, time * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- if (ret.Item2 == Result.TIMEOUT)
- {
- if (!_chamber.CheckChillerStatus())
- {
- Stop($"Chiller not connected or in error");
- }
- else
- {
- Stop($"检查水冷温度超时, 当前水冷温度值 {_chamber.CoolantOutletTempFB}");
- }
-
- throw new RoutineFaildException();
- }
- throw new RoutineBreakException();
- }
- }
- protected void SetSlitDoor(int id, bool isOpen, int timeout)
- {
- Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
- {
- Notify($"设置传送门 {_chamber.Name} " + (isOpen ? "开" : "关"));
- _chamber.SetSlitDoor(isOpen, out _);
- return true;
- }, () => isOpen ? _chamber.CheckSlitDoorOpen() : _chamber.CheckSlitDoorClose(), timeout * 1000);
- if (ret.Item1)
- {
- if (ret.Item2 == Result.FAIL)
- {
- throw new RoutineFaildException();
- }
- else if (ret.Item2 == Result.TIMEOUT) //timeout
- {
- Stop($"无法 {(isOpen ? "开" : "关")} 传送门 in {timeout} seconds");
- throw new RoutineFaildException();
- }
- else
- throw new RoutineBreakException();
- }
- }
- }
- }
|