using System; using System.Diagnostics; using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using System.Collections; using Venus_Core; using Venus_RT.Modules; using MECF.Framework.Common.CommonData; using MECF.Framework.Common.Equipment; using MECF.Framework.Common.SubstrateTrackings; using Aitex.Sorter.Common; using Aitex.Core.Common; using Aitex.Core.RT.SCCore; using Aitex.Core.RT.Log; using Aitex.Core.Util; using MECF.Framework.RT.EquipmentLibrary.HardwareUnits.Robot; using Venus_RT.Devices.YASKAWA; using System.Collections.Concurrent; namespace Venus_RT.Devices.EFEM { class JetEfem : EfemBase { private RState _status; private bool _IsHomed; private string _waferPresence; private bool _bIsUnloadClamp; private RobotMoveInfo _robotMoveInfo = new RobotMoveInfo(); private readonly Loadport[] _LPMs = new Loadport[3]; private readonly SignalTower _signalT = new SignalTower(); private readonly AsyncSocket _socket; private EfemMessage _currentMsg; private EfemMessage _backroundMsg; private EfemMessage _revMsg; private bool _LiftIsUp = false; private bool _LiftIsDown = false; private R_TRIG _busyTrig = new R_TRIG(); private Stopwatch _busyWatch = new Stopwatch(); public override RState Status { get { _busyTrig.CLK = _status == RState.Running; if(_busyTrig.Q) { _busyWatch.Restart(); } else if(_busyTrig.M) { if(_busyWatch.ElapsedMilliseconds > 30000) { _busyWatch.Stop(); _status = RState.Timeout; } } return _status; } } public override bool IsHomed { get { return _IsHomed; } } public override RobotMoveInfo TMRobotMoveInfo { get { return _robotMoveInfo; } } public override ILoadport this[ModuleName mod] { get { if (!ModuleHelper.IsLoadPort(mod)) throw new ApplicationException($"{mod} is NOT Loadport"); return _LPMs[mod - ModuleName.LP1]; } } public override bool LiftIsUp { get { return _LiftIsUp; } } public override bool LiftIsDown { get { return _LiftIsDown; } } private BlockingCollection blockingCollection = new BlockingCollection(); public JetEfem() { _socket = new AsyncSocket(""); _socket.Connect(SC.GetStringValue($"EFEM.IPAddress")); _socket.OnDataChanged += OnReceiveMessage; _socket.OnErrorHappened += OnErrorHappen; _status = RState.Init; _IsHomed = false; _busyTrig.RST = true; _LPMs[0] = new Loadport(ModuleName.LP1, this); _LPMs[1] = new Loadport(ModuleName.LP2, this); _LPMs[2] = new Loadport(ModuleName.LP3, this); CarrierManager.Instance.SubscribeLocation(ModuleName.LP1.ToString(), 1); CarrierManager.Instance.SubscribeLocation(ModuleName.LP2.ToString(), 1); CarrierManager.Instance.SubscribeLocation(ModuleName.LP3.ToString(), 1); Action _subscribeLoc = (ModuleName module, int waferCount) => { if (ModuleHelper.IsInstalled(module)) { WaferManager.Instance.SubscribeLocation(module, waferCount); } }; WaferManager.Instance.SubscribeLocation(ModuleName.EfemRobot, 2); WaferManager.Instance.SubscribeLocation(ModuleName.Aligner1, 1); // _subscribeLoc(ModuleName.EfemRobot, 2); //_subscribeLoc(ModuleName.Aligner1, 1); _subscribeLoc(ModuleName.Aligner2, 1); _subscribeLoc(ModuleName.Cooling1, 1); _subscribeLoc(ModuleName.Cooling2, 1); _subscribeLoc(ModuleName.LP1, SC.GetValue("EFEM.LoadPort.SlotNumber")); _subscribeLoc(ModuleName.LP2, SC.GetValue("EFEM.LoadPort.SlotNumber")); _subscribeLoc(ModuleName.LP3, SC.GetValue("EFEM.LoadPort.SlotNumber")); Task.Run(() => { foreach (var data in blockingCollection.GetConsumingEnumerable()) { _robotMoveInfo.Action = data.Action; _robotMoveInfo.ArmTarget = data.Hand == Hand.Blade1 ? RobotArm.ArmA : (data.Hand == Hand.Both ? RobotArm.Both : RobotArm.ArmB); _robotMoveInfo.BladeTarget = $"{_robotMoveInfo.ArmTarget}.{data.Target}"; System.Threading.Thread.Sleep(600); } }); } public override void Monitor() { } public override void Terminate() { } public override void Reset() { _status = RState.End; } public override void SetOnline(bool online) { } public override void SetOnline(ModuleName mod, bool online) { } public override void SetBusy(ModuleName mod, bool online) { _status = RState.Running; } public override bool HomeAll() { if (_status == RState.Running) _backroundMsg = _currentMsg; _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.Home, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[ModuleName.EFEM] } }; _status = RState.Running; string data = _currentMsg.ToString(); SetRobotMovingInfo(RobotAction.Homing, Hand.Both, ModuleName.EFEM); return _socket.Write(data); } public override bool Home(ModuleName mod) { if (_status == RState.Running) _backroundMsg = _currentMsg; if (ModuleHelper.IsLoadPort(mod)) { _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Home, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } else { _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Home, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } } public override bool OriginalSearch(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.Orgsh, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool CheckWaferPresence() { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.StateTrack, Head = EfemMessage.MsgHead.GET, Parameters = new List { "TRACK" } }; _waferPresence = string.Empty; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override string GetWaferPresence() { return _waferPresence; } public override bool Halt() { if (_status == RState.Running) _backroundMsg = _currentMsg; _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.EmsStop, Head = EfemMessage.MsgHead.MOV, }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool ClearError() { _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.ClearError, Head = EfemMessage.MsgHead.SET, Parameters = new List { "CLEAR" } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool PickExtend(ModuleName chamber, int slot, Hand hand) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Extend, Head = EfemMessage.MsgHead.MOV, Parameters = new List { chamber.ToHWString(), ExtendPos.GB.ToString(), Constant.ArmString[hand], } }; SetRobotMovingInfo(RobotAction.Extending, hand, chamber); _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool PickRetract(ModuleName chamber, int slot, Hand hand) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Extend, Head = EfemMessage.MsgHead.MOV, Parameters = new List { chamber.ToHWString(), ExtendPos.G4.ToString(), Constant.ArmString[hand], } }; _status = RState.Running; SetRobotMovingInfo(RobotAction.Retracting, hand, chamber); return _socket.Write(_currentMsg.ToString()); } public override bool PlaceExtend(ModuleName chamber, int slot, Hand hand) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Extend, Head = EfemMessage.MsgHead.MOV, Parameters = new List { chamber.ToHWString(), ExtendPos.PB.ToString(), Constant.ArmString[hand], } }; _status = RState.Running; SetRobotMovingInfo(RobotAction.Extending, hand, chamber); return _socket.Write(_currentMsg.ToString()); } public override bool PlaceRetract(ModuleName chamber, int slot, Hand hand) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Extend, Head = EfemMessage.MsgHead.MOV, Parameters = new List { chamber.ToHWString(), ExtendPos.P4.ToString(), Constant.ArmString[hand], } }; _status = RState.Running; SetRobotMovingInfo(RobotAction.Retracting, hand, chamber); return _socket.Write(_currentMsg.ToString()); } public override bool Pick(ModuleName station, int slot, Hand hand) { if (!CheckEfemStatus()) return false; Position SrcPos = new Position { Module = station, Slot = (byte)slot }; _currentMsg = new EfemMessage { Operation = EfemOperation.Pick, Head = EfemMessage.MsgHead.MOV, Parameters = new List { SrcPos.ToHWString(), Constant.ArmString[hand], //WaferSize.WS12.ToString() } }; _status = RState.Running; SetRobotMovingInfo(RobotAction.Picking, hand, station); return _socket.Write(_currentMsg.ToString()); } public override bool Place(ModuleName station, int slot, Hand hand) { if (!CheckEfemStatus()) return false; Position DestPos = new Position { Module = station, Slot = (byte)slot }; _currentMsg = new EfemMessage { Operation = EfemOperation.Place, Head = EfemMessage.MsgHead.MOV, Parameters = new List { DestPos.ToHWString(), Constant.ArmString[hand], //WaferSize.WS12.ToString() } }; _status = RState.Running; SetRobotMovingInfo(RobotAction.Placing, hand, station); return _socket.Write(_currentMsg.ToString()); } public override bool Goto(ModuleName station, Hand hand) { if (!CheckEfemStatus()) return false; Position DestPos = new Position { Module = station, Slot = (byte)0 }; _currentMsg = new EfemMessage { Operation = EfemOperation.Goto, Head = EfemMessage.MsgHead.MOV, Parameters = new List { DestPos.ToHWString(), Constant.ArmString[hand], WaferSize.WS12.ToString() } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Grip(Hand blade, bool isGrip) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Grip, Head = EfemMessage.MsgHead.SET, Parameters = new List { isGrip ? "ON":"OFF", Constant.ArmString[blade] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Map(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Map, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool SetPinUp(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Lift, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod], "UP" } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool SetPinDown(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Lift, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod], "DOWN" } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Align(ModuleName mod, double angle, float delayTime, WaferSize size) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Operation = EfemOperation.Align, Head = EfemMessage.MsgHead.MOV, Parameters = new List { $"A{angle.ToString("000.00")}" } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool SetLamp(LightType light, LightStatus status) { if (Status == RState.Running) { LOG.Write(eEvent.ERR_EFEM_ROBOT, ModuleName.EFEM, "EFEM is busy, please wait a minute"); return false; } _currentMsg = new EfemMessage { Port = ModuleName.EFEM, Operation = EfemOperation.Light, Head = EfemMessage.MsgHead.SET, Parameters = new List { Constant.STOWER, light.ToString(), status.ToString() } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Load(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Load, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Unload(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Unload, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool ReadCarrierId(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.CarrierId, Head = EfemMessage.MsgHead.GET, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool WriteCarrierId(ModuleName mod, string id) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.CarrierId, Head = EfemMessage.MsgHead.SET, Parameters = new List { Constant.ModuleString[mod], id } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool ReadTagData(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.CarrierId, Head = EfemMessage.MsgHead.GET, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool WriteTagData(ModuleName mod, string tagData) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.CarrierId, Head = EfemMessage.MsgHead.SET, Parameters = new List { Constant.ModuleString[mod], tagData } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Dock(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Dock, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Undock(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Undock, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool Clamp(ModuleName mod, bool isUnloadClamp) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Clamp, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; _bIsUnloadClamp = isUnloadClamp; return _socket.Write(_currentMsg.ToString()); } public override bool Unclamp(ModuleName mod) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.Unclamp, Head = EfemMessage.MsgHead.MOV, Parameters = new List { Constant.ModuleString[mod] } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override bool SetThickness(ModuleName mod, string thickness) { if (!CheckEfemStatus()) return false; _currentMsg = new EfemMessage { Port = mod, Operation = EfemOperation.SetThickness, Head = EfemMessage.MsgHead.SET, Parameters = new List { Constant.ModuleString[mod], thickness.ToUpper() } }; _status = RState.Running; return _socket.Write(_currentMsg.ToString()); } public override void SetRobotMovingInfo(RobotAction action, Hand hand, ModuleName target) { blockingCollection.Add(new RobotAnimationData(action, hand, target)); } private void OnReceiveMessage(string RevMsg) { string[] msgs = RevMsg.Split('\r'); foreach (var msg in msgs) { if (string.IsNullOrWhiteSpace(msg)) continue; EfemMessage rec_msg = msg.ToMessage(); switch (rec_msg.Head) { case EfemMessage.MsgHead.ACK: if (msg.Contains("ERROR")) { _revMsg = rec_msg; } break; case EfemMessage.MsgHead.INF: // 收到INF之后发送ACK确认 string strACK = rec_msg.RawString.Replace("INF", "ACK"); SendBack(strACK); EfemMessage ack_msg = strACK.ToMessage(); ack_msg.Direct = MsgDirection.To; _revMsg = rec_msg; OnCommandUpdated(rec_msg); SetRobotMovingInfo(RobotAction.None, Hand.Both, ModuleName.EfemRobot); break; case EfemMessage.MsgHead.EVT: OnEventUpdated(new EfemEventArgs { EvtStr = rec_msg.ToParamString(), Module = rec_msg.Port, CommandType = rec_msg.Operation, DataList = rec_msg.Data }); if (rec_msg.Operation == EfemOperation.Home) { SetRobotMovingInfo(RobotAction.Homing, Hand.Both, ModuleName.EFEM); } break; case EfemMessage.MsgHead.NAK: case EfemMessage.MsgHead.CAN: case EfemMessage.MsgHead.ABS: OnErrorOccurred(rec_msg); break; } } } private void OnErrorHappen(ErrorEventArgs args) { _status = RState.Failed; Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } private void OnErrorOccurred(EfemMessage message) { string description = string.Empty; switch (message.Head) { case EfemMessage.MsgHead.NAK: description = Constant.FactorString[message.Factor]; break; case EfemMessage.MsgHead.CAN: description = Constant.FactorString.ContainsKey(message.Factor) ? Constant.FactorString[message.Factor] : message.Factor; break; case EfemMessage.MsgHead.ABS: description = $"{message.Data[0]}, {message.Data[1]}"; break; } _status = RState.Failed; Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, $"{description}, [{message.Data[0]}], [{message.Factor}]"); } private void OnEventUpdated(EfemEventArgs eArg) { switch (eArg.CommandType) { case EfemOperation.SigStatus: // EVT:SIGSTAT/Parameter/DATA1/DATA2; string sParam = eArg.DataList[0]; // "SYSTEM" or "Pn" // DATA1 & DATA2 int nData1 = Convert.ToInt32(eArg.DataList[1], 16); int nData2 = Convert.ToInt32(eArg.DataList[2], 16); BitArray baData1 = new BitArray(new int[] { nData1 }); BitArray baData2 = new BitArray(new int[] { nData2 }); if (0 == string.Compare(sParam, Constant.SYS, true)) { // EVT:SIGSTAT/System/00000000/00000004; // DATA1 // Post warning and alarm if (!baData1[0]) // Bit[0] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMVacuumPressureError); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM System vacuum source pressure low"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[1]) // Bit[1] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMIonizerAlarm); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM Ionizer compressed air error"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[2]) // Bit[2] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMCDAError); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM System compressed air pressure low"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[4]) // Bit[4] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMFlowGaugeSensorError); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM Flow gauge sensor error"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[5]) // Bit[5] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMLeakageAlarm); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM Leakage alarm"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[10]) // Bit[10] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMIonizerAlarm); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM Ionizer alarm"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[11]) // Bit[11] ON=Normal, OFF=Abnormal { //EV.Notify(EFEMFFUAlarm); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "FFU alarm"); Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.Error); } if (!baData1[8]) // Bit[13] ON=RUN, OFF=Maintain { //EV.Notify(EFEMOffline); LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EFEM, "EFEM switch to Maintain mode, HomeAll to recover"); } // DATA2 _signalT.ChangeLightStatus(LightType.RED, baData2[0] ? LightStatus.ON : baData2[5] ? LightStatus.BLINK : LightStatus.OFF); _signalT.ChangeLightStatus(LightType.GREEN, baData2[1] ? LightStatus.ON : baData2[6] ? LightStatus.BLINK : LightStatus.OFF); _signalT.ChangeLightStatus(LightType.YELLOW, baData2[2] ? LightStatus.ON : baData2[7] ? LightStatus.BLINK : LightStatus.OFF); _signalT.ChangeLightStatus(LightType.BLUE, baData2[3] ? LightStatus.ON : baData2[8] ? LightStatus.BLINK : LightStatus.OFF); _signalT.ChangeLightStatus(LightType.WHITE, baData2[4] ? LightStatus.ON : baData2[9] ? LightStatus.BLINK : LightStatus.OFF); _signalT.ChangeLightStatus(LightType.BUZZER1, baData2[10] ? LightStatus.ON : LightStatus.OFF); /* EFEM 程序中目前没有实现 _RobotErr.CLK = baData2[27]; // bit 27 bool bArmNotExtendLLA = baData2[30]; // bit 30 bool bArmNotExtendLLB = baData2[31]; // bit 31 */ } // system event else { _LPMs[eArg.Module - ModuleName.LP1].HandleEvent(eArg); } // FOUP EVENT break; case EfemOperation.GetWaferInfo: _LPMs[eArg.Module - ModuleName.LP1].HandleEvent(eArg); break; default: break; } } private void OnCommandUpdated(EfemMessage message) { if (message.Operation != EfemOperation.Ready) { if (_currentMsg.Operation != message.Operation && (_backroundMsg == null || _backroundMsg.Operation != message.Operation)) { LOG.Write(eEvent.ERR_EFEM_COMMON_FAILED, ModuleName.EfemRobot, $"OnCommandUpdated() unexpected return: {message.Operation}, expect: {_currentMsg.Operation}"); return; } } switch (message.Operation) { case EfemOperation.ClearError: case EfemOperation.Align: case EfemOperation.Map: case EfemOperation.Pick: case EfemOperation.Place: case EfemOperation.Extend: case EfemOperation.Goto: case EfemOperation.Orgsh: case EfemOperation.EmsStop: case EfemOperation.Light: _status = RState.End; break; case EfemOperation.StateTrack: { _waferPresence = message.Data.Count >= 1 ? message.Data.First() : string.Empty; _IsHomed = true; _status = RState.End; } break; case EfemOperation.Home: { if (_currentMsg.Port == ModuleName.EFEM) { _LPMs[0].OnHomed(); _LPMs[1].OnHomed(); _LPMs[2].OnHomed(); } else if (ModuleHelper.IsLoadPort(_currentMsg.Port)) { _LPMs[_currentMsg.Port - ModuleName.LP1].OnHomed(); } _status = RState.End; } break; case EfemOperation.Load: { _LPMs[message.Port - ModuleName.LP1].OnLoaded(); _status = RState.End; } break; case EfemOperation.Unload: { _LPMs[message.Port - ModuleName.LP1].OnUnloaded(); _status = RState.End; } break; case EfemOperation.CarrierId: { //if (message.Head == EfemMessage.MsgHead.GET) //{ _LPMs[message.Port - ModuleName.LP1].OnCarrierIDRead(message.Data.First()); //} //else //{ // _LPMs[message.Port - ModuleName.LP1].OnCarrierIDWrite(message.Data.First()); //} _status = RState.End; } break; case EfemOperation.Clamp: { _LPMs[message.Port - ModuleName.LP1].OnClamped(_bIsUnloadClamp); _status = RState.End; } break; case EfemOperation.Unclamp: { _LPMs[message.Port - ModuleName.LP1].OnUnclamped(); _status = RState.End; } break; case EfemOperation.Grip: { if (_currentMsg.Parameters[1] == "ARM2") { GripStateBlade1 = _currentMsg.Parameters[0]; } else { GripStateBlade2 = _currentMsg.Parameters[0]; } _status = RState.End; } break; case EfemOperation.Ready: { Singleton.Instance.EFEM.PostMsg(EfemEntity.MSG.CommReady); } break; case EfemOperation.Lift: { if (_currentMsg.Parameters[1] == "UP") { _LiftIsUp = true; _LiftIsDown = false; } else if (_currentMsg.Parameters[1] == "DOWN") { _LiftIsUp = false; _LiftIsDown = true; } _status = RState.End; } break; } } void SendBack(string data) { _socket.Write(data + '\r'); } } }