using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using Aitex.Core.RT.Event; using Aitex.Core.Util; using MECF.Framework.Common.Equipment; using MECF.Framework.Common.Jobs; using FurnaceRT.FAs; using Aitex.Core.RT.SCCore; using static MECF.Framework.Common.FAServices.Gem300Events; using MECF.Framework.Common.FAServices; using Aitex.Core.Common; using MECF.Framework.Common.SubstrateTrackings; using FabConnect.SecsGemInterface.Common; using Aitex.Core.RT.DataCenter; using MECF.Framework.FA.Core.FAControl; using FurnaceRT.Equipments.Systems; namespace FurnaceRT.Equipments.Schedulers { public class SchedulerFACallback : ISchedulerFACallback { private Dictionary PortJobStarted; private Dictionary PortJobStopped; private Dictionary PortJobPaused; private Dictionary PortJobResumed; private Dictionary PortJobAborted; private Dictionary PortJobFinished; private Dictionary PortJobFailed; private Dictionary PortSequenceSelected; private Dictionary PortSequenceSelectFailed; private Dictionary PortId; public SchedulerFACallback() { PortJobStarted = new Dictionary(); PortJobStopped = new Dictionary(); PortJobPaused = new Dictionary(); PortJobResumed = new Dictionary(); PortJobAborted = new Dictionary(); PortJobFinished = new Dictionary(); PortJobFailed = new Dictionary(); PortSequenceSelected = new Dictionary(); PortSequenceSelectFailed = new Dictionary(); PortId = new Dictionary(); for (int i = 1; i < 45; i++) { if (!SC.ContainsItem($"System.Stocker.Stocker{i}WaferType")) continue; var module = ModuleHelper.Converter($"Stocker{i}"); EV.Subscribe(new EventItem("Event", $"{module}JobStarted", $"{module}JobStarted")); EV.Subscribe(new EventItem("Event", $"{module}JobStopped", $"{module}JobStopped")); EV.Subscribe(new EventItem("Event", $"{module}JobPaused", $"{module}JobPaused")); EV.Subscribe(new EventItem("Event", $"{module}JobResumed", $"{module}JobResumed")); EV.Subscribe(new EventItem("Event", $"{module}JobAborted", $"{module}JobAborted")); EV.Subscribe(new EventItem("Event", $"{module}JobFinished", $"{module}JobFinished")); EV.Subscribe(new EventItem("Event", $"{module}JobFailed", $"{module}JobFailed")); EV.Subscribe(new EventItem("Event", $"{module}SequenceSelected", $"{module}SequenceSelected")); EV.Subscribe(new EventItem("Event", $"{module}SequenceSelectFailed", $"{module}SequenceSelectFailed")); EV.Subscribe(new EventItem("Event", UniversalEvents.EquipmentOFFLINE, $"EquipmentOFFLINE")); EV.Subscribe(new EventItem("Event", UniversalEvents.ControlStateLOCAL, $"ControlStateLOCAL")); EV.Subscribe(new EventItem("Event", UniversalEvents.ControlStateREMOTE, $"ControlStateREMOTE")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessingStarted, $"ProcessingStarted")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessingCompleted, $"ProcessingCompleted")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessingStopped, $"ProcessingStopped")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessingStateChanged, $"ProcessingStateChanged")); EV.Subscribe(new EventItem("Event", UniversalEvents.EquipmentConstantChanged, $"EquipmentConstantChanged")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessProgramChanged, $"ProcessProgramChanged")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessProgramSelected, $"ProcessProgramSelected")); EV.Subscribe(new EventItem("Event", UniversalEvents.ProcessProgramCreated, $"ProcessProgramCreated")); EV.Subscribe(new EventItem("Event", UniversalEvents.SpoolingActivated, $"SpoolingActivated")); EV.Subscribe(new EventItem("Event", UniversalEvents.SpoolingDeactivated, $"SpoolingDeactivated")); EV.Subscribe(new EventItem("Event", UniversalEvents.SpoolingFailed, $"SpoolingFailed")); EV.Subscribe(new EventItem("Event", UniversalEvents.SpoolingFailed, $"SpoolingFailed")); EV.Subscribe(new EventItem("Event", UniversalEvents.ChargeStart, $"ChargeStart")); EV.Subscribe(new EventItem("Event", UniversalEvents.ChargeEnd, $"ChargeEnd")); EV.Subscribe(new EventItem("Event", UniversalEvents.DischargeStart, $"DischargeStart")); EV.Subscribe(new EventItem("Event", UniversalEvents.DischargeEnd, $"DischargeEnd")); EV.Subscribe(new EventItem("Event", UniversalEvents.BatchLocOccupied, $"BatchLocOccupied")); EV.Subscribe(new EventItem("Event", UniversalEvents.BatchLocUnOccupied, $"BatchLocUnOccupied")); EV.Subscribe(new EventItem("Event", UniversalEvents.CarrierInEnd, $"CarrierInEnd")); EV.Subscribe(new EventItem("Event", UniversalEvents.CarrierInStart, $"CarrierInStart")); EV.Subscribe(new EventItem("Event", UniversalEvents.CarrierOutStart, $"CarrierOutStart")); EV.Subscribe(new EventItem("Event", UniversalEvents.CarrierOutEnd, $"CarrierOutEnd")); EV.Subscribe(new EventItem("Event", UniversalEvents.SideDummyStateAlarm, $"SideDummyStateAlarm")); EV.Subscribe(new EventItem("Event", UniversalEvents.ExtraDummyStateAlarm, $"ExtraDummyStateAlarm")); EV.Subscribe(new EventItem("Event", UniversalEvents.SideDummyStateWarning, $"SideDummyStateWarning")); EV.Subscribe(new EventItem("Event", UniversalEvents.ExtraDummyStateWarning, $"ExtraDummyStateWarning")); PortId[module] = i.ToString(); PortJobStarted[module] = $"{module}JobStarted"; PortJobStopped[module] = $"{module}JobStopped"; PortJobPaused[module] = $"{module}JobPaused"; PortJobResumed[module] = $"{module}JobResumed"; PortJobAborted[module] = $"{module}JobAborted"; PortJobFinished[module] = $"{module}JobFinished"; PortJobFailed[module] = $"{module}JobFailed"; PortSequenceSelected[module] = $"{module}SequenceSelected"; PortSequenceSelectFailed[module] = $"{module}SequenceSelectFailed"; } } public void JobCreated(ControlJobInfo cj) { if (cj != null) { EV.Notify(Gem300Events.CJ_CREATED, new SerializableDictionary() { {DataVariables.CJID, cj.Name}, }); } } public void JobCreated(ProcessJobInfo pj) { if (pj != null) { EV.Notify(Gem300Events.PJ_CREATED, new SerializableDictionary() { {DataVariables.PRJobID, pj.Name}, }); } } public void JobCreateFailed(string module, string lotID, string jobID, string sequenceID) { ModuleName moduleName = ModuleHelper.Converter(module); EV.Notify(PortSequenceSelectFailed[moduleName], new SerializableDictionary() { {DVIDName.LotID, lotID}, {DVIDName.JobID, jobID}, {DVIDName.PortID, PortId[moduleName] }, {DVIDName.SequenceID, sequenceID } }); } public void JobStarted(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobStarted[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobStopped(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobStopped[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobPaused(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobPaused[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobResumed(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobResumed[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobAborted(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobAborted[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobFinished(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobFinished[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void JobFailed(ControlJobInfo cj, ProcessJobInfo pj) { if (cj != null && pj != null) { foreach (var s in pj.Stockers) { var type = SC.GetStringValue($"System.Stocker.{s.Item1}WaferType"); if (!string.IsNullOrEmpty(type) && (type.Contains("P") || type.Contains("M"))) { ModuleName module = ModuleHelper.Converter(s.Item1); EV.Notify(PortJobFailed[module], new SerializableDictionary() { {DVIDName.LotID, cj.LotName}, {DVIDName.JobID, pj.ControlJobName}, {DVIDName.PortID, PortId[module] }, {DVIDName.SequenceID, pj.JobRecipe } }); } } } } public void StartCharge(ProcessJobInfo pj) { List crids = CarrierManager.Instance.GetStokerCarrierID(); SECsDataItem data = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { data.Add("CarrierID", _id); } if (pj != null) { EV.Notify(UniversalEvents.ChargeStart, new SerializableDictionary() { {DataVariables.PRJobID, pj.Name}, {DataVariables.BatchLocID, "BatchBuild1"}, {DataVariables.BoatID, "Boat1"}, {DataVariables.CarrierIDList, data}, }); } } public void EndCharge(ProcessJobInfo pj, List _slotmap) { List crids = CarrierManager.Instance.GetStokerCarrierID(); SECsDataItem data = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { data.Add("CarrierID", _id); } if (pj != null) { EV.Notify(UniversalEvents.ChargeEnd, new SerializableDictionary() { {DataVariables.PRJobID, pj.Name}, {DataVariables.BoatSlotMapList, _slotmap}, {DataVariables.WaferIDList, _slotmap}, {DataVariables.BatchLocID, "BatchBuild1"}, {DataVariables.BoatID, "Boat1"}, {DataVariables.CarrierIDList, data}, }); } } public void StartDischarge(ProcessJobInfo pj, List _slotmap) { List crids = CarrierManager.Instance.GetStokerCarrierID(); SECsDataItem data = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { data.Add("CarrierID", _id); } if (pj != null) { EV.Notify(UniversalEvents.DischargeStart, new SerializableDictionary() { {DataVariables.PRJobID, pj.Name}, {DataVariables.BoatSlotMapList, _slotmap}, {DataVariables.WaferIDList, _slotmap}, {DataVariables.BatchLocID, "BatchBuild1"}, {DataVariables.BoatID, "Boat1"}, {DataVariables.CarrierIDList, data}, }); } } public void EndDischarge(ProcessJobInfo pj) { if (pj != null) { EV.Notify(UniversalEvents.DischargeEnd, new SerializableDictionary() { {DataVariables.PRJobID, pj.Name}, }); } } public void CarrierInEnd(CarrierInfo carrier) { List crids = CarrierManager.Instance.GetBufferMaterialInfo(); SECsDataItem BufferMaterialInfos = new SECsDataItem(SECsFormat.List); SECsDataItem BufferMaterialInfo = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { BufferMaterialInfo = new SECsDataItem(SECsFormat.List); BufferMaterialInfo.Add("StockerName", _id.Split(';')[0], SECsFormat.Ascii); BufferMaterialInfo.Add("StockerCarrierID", _id.Split(';')[1].Replace("emptyid", ""), SECsFormat.Ascii); BufferMaterialInfos.Add(BufferMaterialInfo); } if (carrier != null) { EV.Notify(UniversalEvents.CarrierInEnd, new SerializableDictionary() { {DataVariables.Usage, carrier.CarrierType.ToString()}, {DataVariables.BufferCapacitiyList, GetBufferCapacitiyList()}, {DataVariables.BufferMaterialInfo, BufferMaterialInfos}, {DataVariables.CarrierID, carrier.CarrierId}, }); } } public void CarrierOutEnd(CarrierInfo carrier) { List crids = CarrierManager.Instance.GetBufferMaterialInfo(); SECsDataItem BufferMaterialInfos = new SECsDataItem(SECsFormat.List); SECsDataItem BufferMaterialInfo = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { BufferMaterialInfo = new SECsDataItem(SECsFormat.List); BufferMaterialInfo.Add("StockerName", _id.Split(';')[0], SECsFormat.Ascii); BufferMaterialInfo.Add("StockerCarrierID", _id.Split(';')[1].Replace("emptyid", ""), SECsFormat.Ascii); BufferMaterialInfos.Add(BufferMaterialInfo); } if (carrier != null) { EV.Notify(UniversalEvents.CarrierOutEnd, new SerializableDictionary() { {DataVariables.Usage, carrier.CarrierType.ToString()}, {DataVariables.BufferCapacitiyList, GetBufferCapacitiyList()}, {DataVariables.BufferMaterialInfo, BufferMaterialInfos}, {DataVariables.CarrierID, carrier.CarrierId}, }); } } public void CarrierInStart(CarrierType carrierType, string _carrierid) { List crids = CarrierManager.Instance.GetBufferMaterialInfo(); SECsDataItem BufferMaterialInfos = new SECsDataItem(SECsFormat.List); SECsDataItem BufferMaterialInfo = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { BufferMaterialInfo = new SECsDataItem(SECsFormat.List); BufferMaterialInfo.Add("StockerName", _id.Split(';')[0], SECsFormat.Ascii); BufferMaterialInfo.Add("StockerCarrierID", _id.Split(';')[1].Replace("emptyid", ""), SECsFormat.Ascii); BufferMaterialInfos.Add(BufferMaterialInfo); } EV.Notify(UniversalEvents.CarrierInStart, new SerializableDictionary() { {DataVariables.Usage, carrierType.ToString()}, {DataVariables.CarrierID, _carrierid}, {DataVariables.BufferCapacitiyList, GetBufferCapacitiyList()}, {DataVariables.BufferMaterialInfo, BufferMaterialInfos}, }); } public void CarrierOutStart(CarrierInfo carrier) { List crids = CarrierManager.Instance.GetBufferMaterialInfo(); SECsDataItem BufferMaterialInfos = new SECsDataItem(SECsFormat.List); SECsDataItem BufferMaterialInfo = new SECsDataItem(SECsFormat.List); foreach (var _id in crids) { BufferMaterialInfo = new SECsDataItem(SECsFormat.List); BufferMaterialInfo.Add("StockerName", _id.Split(';')[0], SECsFormat.Ascii); BufferMaterialInfo.Add("StockerCarrierID", _id.Split(';')[1].Replace("emptyid", ""), SECsFormat.Ascii); BufferMaterialInfos.Add(BufferMaterialInfo); } if (carrier != null) { EV.Notify(UniversalEvents.CarrierOutStart, new SerializableDictionary() { {DataVariables.Usage, carrier.CarrierType.ToString()}, {DataVariables.CarrierID, carrier.CarrierId}, {DataVariables.BufferCapacitiyList, GetBufferCapacitiyList()}, {DataVariables.BufferMaterialInfo, BufferMaterialInfos}, }); } } public void JobCreated(ControlJobInfo cj, ProcessJobInfo pj) { } public void SideDummyStateAlarm(CarrierInfo carrier) { EV.Notify(UniversalEvents.SideDummyStateAlarm, new SerializableDictionary() { {DataVariables.CarrierID, carrier.CarrierId}, }); } public void ExtraDummyStateAlarm(CarrierInfo carrier) { EV.Notify(UniversalEvents.ExtraDummyStateAlarm, new SerializableDictionary() { {DataVariables.CarrierID, carrier.CarrierId}, }); } public void SideDummyStateWarning(CarrierInfo carrier) { EV.Notify(UniversalEvents.SideDummyStateWarning, new SerializableDictionary() { {DataVariables.CarrierID, carrier.CarrierId}, }); } public void ExtraDummyStateWarning(CarrierInfo carrier) { EV.Notify(UniversalEvents.ExtraDummyStateWarning, new SerializableDictionary() { {DataVariables.CarrierID, carrier.CarrierId}, }); } public void CarrierInEnd(ModuleName module) { var carrier = CarrierManager.Instance.GetCarrier(module, 0); if (carrier == null || carrier.IsEmpty) return; List slotMapList = new List(); var wafers = WaferManager.Instance.GetWafers(module); if (wafers != null) { foreach (var wafer in wafers) { switch (wafer.Status) { case WaferStatus.Normal: slotMapList.Add(3); break; case WaferStatus.Empty: slotMapList.Add(1); break; case WaferStatus.Double: slotMapList.Add(2); break; case WaferStatus.Crossed: slotMapList.Add(4); break; case WaferStatus.Unknown: slotMapList.Add(5); break; } } } SerializableDictionary dvid = new SerializableDictionary(); string slotMap = ""; foreach (var item in slotMapList) { slotMap += item; } dvid["SlotMap"] = slotMap; dvid["SlotMapList"] = slotMapList; dvid["CarrierType"] = carrier.CarrierType; dvid["CarrierID"] = carrier.CarrierId; EV.Notify("SLOT_MAP_AVAILABLE", dvid); Singleton.Instance.Eqp_NoteCarrierSlotMapRead(carrier.PortID, slotMap, carrier.CarrierId); CarrierInEnd(carrier); } public SECsDataItem GetBufferCapacitiyList() { SECsDataItem bufinfo = new SECsDataItem(SECsFormat.List); bufinfo.Add("BUFPara", "Partition1"); bufinfo.Add("BUFPara", "General"); int emptyStocker = 0; int totalStocker = 0; foreach (var key in Singleton.Instance.Modules.Keys) { if (ModuleHelper.IsStocker(key)) totalStocker++; if (ModuleHelper.IsStocker(key) && CarrierManager.Instance.CheckNoCarrier(key, 0)) { var has = false; foreach (var key1 in Singleton.Instance.Modules.Keys) { if (CarrierManager.Instance.CheckHasCarrier(key1, 0) && CarrierManager.Instance.GetCarrier(key1, 0).InternalModuleName == key) { has = true; break; } } if (has) continue; emptyStocker++; } } bufinfo.Add("BUFPara", emptyStocker, SECsFormat.U1); bufinfo.Add("BUFPara", totalStocker, SECsFormat.U1); int unallocatedPartitionCapacity = 0; List checkList = new List() { ModuleName.LP1, ModuleName.LP2, ModuleName.FIMS1, ModuleName.FIMS2, }; foreach (var module in checkList) { if (CarrierManager.Instance.CheckHasCarrier(module, 0)) unallocatedPartitionCapacity++; } bufinfo.Add("BUFPara", unallocatedPartitionCapacity, SECsFormat.U1); return bufinfo; } } }