IoLP.cs 43 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919
  1. using Aitex.Core.Common;
  2. using Aitex.Core.RT.DataCenter;
  3. using Aitex.Core.RT.Device;
  4. using Aitex.Core.RT.Device.Unit;
  5. using Aitex.Core.RT.Event;
  6. using Aitex.Core.RT.IOCore;
  7. using Aitex.Core.RT.OperationCenter;
  8. using Aitex.Core.RT.SCCore;
  9. using Aitex.Core.Util;
  10. using Aitex.Sorter.Common;
  11. using FabConnect.SecsGemInterface.Common.ToolModel;
  12. using log4net.Repository.Hierarchy;
  13. using MECF.Framework.Common.Equipment;
  14. using MECF.Framework.Common.SubstrateTrackings;
  15. using MECF.Framework.RT.EquipmentLibrary.HardwareUnits.CarrierIdReaders.CarrierIDReaderBase;
  16. using MECF.Framework.RT.EquipmentLibrary.HardwareUnits.LoadPorts;
  17. using MECF.Framework.RT.EquipmentLibrary.HardwareUnits.LoadPorts.LoadPortBase;
  18. using MECF.Framework.RT.EquipmentLibrary.HardwareUnits.LoadPorts.TDK;
  19. using System;
  20. using System.Collections.Generic;
  21. using System.Linq;
  22. using System.Text;
  23. using System.Threading.Tasks;
  24. using System.Xml;
  25. using static Aitex.Core.RT.Device.Unit.IOE84Passive;
  26. namespace FurnaceRT.Devices
  27. {
  28. public class IoLP : BaseDevice, IDevice, ILoadPort
  29. {
  30. private DIAccessor _diLeftClamp;
  31. private DIAccessor _diRightClamp;
  32. private DIAccessor _diLeftRelease;
  33. private DIAccessor _diRightRelease;
  34. private DIAccessor _diInPosition1;
  35. private DIAccessor _diInPosition2;
  36. private DIAccessor _diInPosition3;
  37. private DIAccessor _diDetect;
  38. private DOAccessor _doClamp;
  39. private DOAccessor _doRelease;
  40. private DOAccessor _doPresenceLight;
  41. private DOAccessor _doPlacementLight;
  42. private DOAccessor _doLoadLight;
  43. private DOAccessor _doUnloadLight;
  44. private DOAccessor _doManualLight;
  45. private IoSensor _foupPresentSensor;
  46. private bool _isSimulatorMode;
  47. private string _previousAccessMode = "";
  48. public bool IsFoupPresent
  49. {
  50. get
  51. {
  52. if(_isSimulatorMode)
  53. return CarrierManager.Instance.CheckHasCarrier(LPModuleName.ToString(), 0);
  54. if (_diInPosition1 != null && _diInPosition2 != null && _diInPosition3 != null && _doPresenceLight != null)
  55. {
  56. // _doPresenceLight.Value = _diInPosition1.Value && _diInPosition2.Value && _diInPosition3.Value;
  57. _doPlacementLight.Value = _diInPosition1.Value && _diInPosition2.Value && _diInPosition3.Value;
  58. }
  59. if (_diInPosition1 != null && _diInPosition2 != null && _diInPosition3 != null && _diDetect != null && _doPlacementLight != null)
  60. {
  61. // _doPlacementLight.Value = _diDetect.Value && _diInPosition1.Value && _diInPosition2.Value && _diInPosition3.Value;
  62. _doPresenceLight.Value = _diDetect.Value;
  63. }
  64. if (_diInPosition1 != null && _diInPosition2 != null && _diInPosition3 != null && _diDetect != null)
  65. return _diInPosition1.Value && _diInPosition2.Value && _diInPosition3.Value && _diDetect.Value;
  66. return false;
  67. }
  68. }
  69. public DeviceStatus Status
  70. {
  71. get
  72. {
  73. if (_diLeftClamp != null && _diRightClamp != null && _diLeftRelease != null && _diRightRelease != null &&
  74. _diLeftClamp.Value && _diRightClamp.Value && !_diLeftRelease.Value && !_diRightRelease.Value)
  75. return DeviceStatus.Clamp;
  76. if (_diLeftClamp != null && _diRightClamp != null && _diLeftRelease != null && _diRightRelease != null &&
  77. !_diLeftClamp.Value && !_diRightClamp.Value && _diLeftRelease.Value && _diRightRelease.Value)
  78. return DeviceStatus.Release;
  79. return DeviceStatus.Unknown;
  80. }
  81. }
  82. public bool IsLoadCompleted { get; set; }
  83. public bool IsUnloadCompleted { get; set; }
  84. public bool IsInitCompleted { get; set; }
  85. public IoLP(string module, XmlElement node, string ioModule = "")
  86. {
  87. base.Module = string.IsNullOrEmpty(node.GetAttribute("module")) ? module : node.GetAttribute("module");
  88. base.Name = node.GetAttribute("id");
  89. base.Display = node.GetAttribute("display");
  90. base.DeviceID = node.GetAttribute("schematicId");
  91. LPModuleName = (ModuleName)Enum.Parse(typeof(ModuleName), Name);
  92. _diLeftClamp = ParseDiNode("diLeftClamp", node, ioModule);
  93. _diRightClamp = ParseDiNode("diRightClamp", node, ioModule);
  94. _diLeftRelease = ParseDiNode("diLeftRelease", node, ioModule);
  95. _diRightRelease = ParseDiNode("diRightRelease", node, ioModule);
  96. _diInPosition1 = ParseDiNode("diInPosition1", node, ioModule);
  97. _diInPosition2 = ParseDiNode("diInPosition2", node, ioModule);
  98. _diInPosition3 = ParseDiNode("diInPosition3", node, ioModule);
  99. _diDetect = ParseDiNode("diDetect", node, ioModule);
  100. _doClamp = ParseDoNode("doClamp", node, ioModule);
  101. _doRelease = ParseDoNode("doRelease", node, ioModule);
  102. _doPresenceLight = ParseDoNode("doPresence", node, ioModule);
  103. _doPlacementLight = ParseDoNode("doPlacement", node, ioModule);
  104. _doLoadLight = ParseDoNode("doLoad", node, ioModule);
  105. _doUnloadLight = ParseDoNode("doUnload", node, ioModule);
  106. _doManualLight = ParseDoNode("doManual", node, ioModule);
  107. }
  108. public bool Initialize()
  109. {
  110. _isSimulatorMode = SC.GetValue<bool>("System.IsSimulatorMode");
  111. var foupSensorID = Name == "LP1" ? "17" : "18";
  112. if (SC.GetStringValue("LoadPort.LoadPortPosition") == "Upper")
  113. {
  114. foupSensorID += "A";
  115. }
  116. _foupPresentSensor = DEVICE.GetDevice<IoSensor>($"System.SensorStation{foupSensorID}Presence");
  117. OP.Subscribe($"{Module}.{Name}.SetClamp", (string cmd, object[] param) =>
  118. {
  119. Clamp(out string reason);
  120. return true;
  121. });
  122. OP.Subscribe($"{Module}.{Name}.SetRelease", (string cmd, object[] param) =>
  123. {
  124. Unclamp(out string reason);
  125. return true;
  126. });
  127. SubscribeDataVariable();
  128. SubscribeAlarm();
  129. return true;
  130. }
  131. public void Monitor()
  132. {
  133. var accessMode = DATA.Poll($"{Name}.AccessMode");
  134. if (accessMode != null)
  135. {
  136. if (accessMode.ToString().ToUpper() == "AUTO")
  137. {
  138. //auto时候,默认是夹紧状态
  139. if (!_doClamp.Value && _previousAccessMode != accessMode.ToString())
  140. {
  141. Clamp(out _);
  142. }
  143. }
  144. if (accessMode.ToString().ToUpper() == "MANUAL")
  145. {
  146. ///1.manual模式,如果没有foup,不夹紧
  147. //2.manual模式,如果有foup,同时有load job,要夹紧,取走之后,不夹紧
  148. if (!IsFoupPresent && !_doRelease.Value && _previousAccessMode != accessMode.ToString())
  149. {
  150. Unclamp(out _);
  151. }
  152. }
  153. _previousAccessMode = accessMode.ToString();
  154. }
  155. }
  156. public void Reset()
  157. {
  158. }
  159. public void Terminate()
  160. {
  161. }
  162. //private bool SetExtend(out string reason, int time, object[] param)
  163. //{
  164. // reason = "";
  165. // if (param == null || param.Length == 0)
  166. // {
  167. // reason = "invalid parameter";
  168. // return false;
  169. // }
  170. // bool.TryParse(param[0].ToString(), out bool isExtend);
  171. // return SetExtend(isExtend, out reason);
  172. //}
  173. //public bool SetExtend(bool isExtend, out string reason)
  174. //{
  175. // return _doExtend.SetValue(isExtend, out reason) && _doRetract.SetValue(!isExtend, out reason);
  176. //}
  177. #region ILoadPort
  178. public IndicatorState IndicatiorLoad { get; set; }
  179. public IndicatorState IndicatiorUnload { get; set; }
  180. public IndicatorState IndicatiorPresence { get; set; }
  181. public IndicatorState IndicatorAlarm { get; set; }
  182. public IndicatorState IndicatiorPlacement { get; set; }
  183. public IndicatorState IndicatiorOpAccess { get; set; }
  184. public IndicatorState IndicatiorAccessAuto { get; set; }
  185. public IndicatorState IndicatiorAccessManual { get; set; }
  186. public IndicatorState IndicatiorStatus1 { get; set; }
  187. public IndicatorState IndicatiorStatus2 { get; set; }
  188. public IndicatorState IndicatiorManualMode { get; set; }
  189. public IndicatorState IndicatiorClampUnclamp { get; set; }
  190. public IndicatorState IndicatiorDockUndock { get; set; }
  191. public static Dictionary<IndicatorType, Indicator> LoadPortIndicatorLightMap =
  192. new Dictionary<IndicatorType, Indicator>()
  193. {
  194. {IndicatorType.Load, Indicator.LOAD},
  195. {IndicatorType.Unload, Indicator.UNLOAD},
  196. {IndicatorType.AccessAuto, Indicator.ACCESSAUTO },
  197. {IndicatorType.AccessManual, Indicator.ACCESSMANUL},
  198. {IndicatorType.Alarm, Indicator.ALARM},
  199. {IndicatorType.Presence, Indicator.PRESENCE},
  200. {IndicatorType.Placement, Indicator.PLACEMENT},
  201. {IndicatorType.Status1, Indicator.RESERVE1},
  202. {IndicatorType.Status2, Indicator.RESERVE2},
  203. };
  204. public virtual DeviceState State
  205. {
  206. get
  207. {
  208. if (MapError || ReadCarrierIDError)
  209. {
  210. return DeviceState.Error;
  211. }
  212. return DeviceState.Unknown;
  213. }
  214. }
  215. public bool IsPresent
  216. {
  217. get { return _isPresent; }
  218. }
  219. public bool IsPlacement
  220. {
  221. get { return _isPlaced; }
  222. }
  223. public bool IsMapped
  224. {
  225. get { return _isMapped; }
  226. }
  227. public virtual bool IsError { get; set; }
  228. public virtual string ErrorCode { get; set; } = "";
  229. public bool MapError { get; protected set; }
  230. public bool ReadCarrierIDError { get; set; }
  231. public IndicatorState[] IndicatorStateFeedback { get; set; }
  232. public virtual FoupClampState ClampState { get; set; }
  233. public virtual FoupDockState DockState { get; set; }
  234. public virtual FoupDoorState DoorState { get; set; }
  235. public virtual FoupDoorPostionEnum DoorPosition { get; set; }
  236. public virtual bool IsVacuumON { get; set; }
  237. public virtual CasstleType CasstleType { get; set; }
  238. public string SlotMap
  239. {
  240. get { return GetSlotMap(); }
  241. }
  242. public string CarrierId
  243. {
  244. get { return _carrierId; }
  245. }
  246. public string LPLotID
  247. {
  248. get { return _lplotID; }
  249. }
  250. public RD_TRIG PresentTrig
  251. {
  252. get { return _presentTrig; }
  253. }
  254. public RD_TRIG PlacedtTrig
  255. {
  256. get { return _placetTrig; }
  257. }
  258. public RD_TRIG AccessSwPressedTrig
  259. {
  260. get { return _accessSwPressedTrig; }
  261. }
  262. public RD_TRIG ClampedTrig
  263. {
  264. get { return _clampTrig; }
  265. }
  266. public RD_TRIG DockTrig
  267. {
  268. get { return _dockTrig; }
  269. }
  270. public RD_TRIG DoorTrig
  271. {
  272. get { return _doorTrig; }
  273. }
  274. protected virtual bool _isPresent { get; set; }
  275. protected virtual bool _isPlaced { get; set; }
  276. protected bool _isDocked { get => DockState == FoupDockState.Docked; }
  277. public string InfoPadCarrierType { get; set; }
  278. protected bool _isAccessSwPressed;
  279. protected string _carrierId = string.Empty;
  280. protected string _rfid;
  281. protected string _lplotID;
  282. protected bool _isMapped;
  283. private readonly RD_TRIG _presentTrig = new RD_TRIG();
  284. private readonly RD_TRIG _placetTrig = new RD_TRIG();
  285. private readonly RD_TRIG _accessSwPressedTrig = new RD_TRIG();
  286. private readonly RD_TRIG _clampTrig = new RD_TRIG();
  287. private readonly RD_TRIG _dockTrig = new RD_TRIG();
  288. private readonly RD_TRIG _doorTrig = new RD_TRIG();
  289. public R_TRIG TrigWaferProtrude = new R_TRIG();
  290. public int PortID
  291. {
  292. get => (int)LPModuleName;
  293. }
  294. protected string EventCarrierArrived = "CARRIER_ARRIVED";
  295. protected string EventCarrierIdRead = "CARRIER_ID_READ";
  296. protected string EventCarrierIdReadFailed = "CARRIER_ID_READ_FAILED";
  297. protected string EventCarrierIdWrite = "CARRIER_ID_WRITE";
  298. protected string EventCarrierIdWriteFailed = "CARRIER_ID_WRITE_FAILED";
  299. protected string EventSlotMapAvailable = "SLOT_MAP_AVAILABLE";
  300. protected string EventCarrierRemoved = "CARRIER_REMOVED";
  301. protected string EventCarrierUnloaded = "CARRIER_UNLOADED";
  302. protected string EventCarrierLoaded = "CARRIER_LOADED";
  303. protected string EventLPHomed = "LP_HOMED";
  304. //protected string PORT_ID = "PORT_ID";
  305. //protected string CAR_ID = "CAR_ID";
  306. //protected string SLOT_MAP = "SLOT_MAP";
  307. //protected string PORT_CTGRY = "PORT_CTGRY";
  308. //protected string RF_ID = "RF_ID";
  309. //protected string PORT_CARRIER_TYPE = "PORT_CARRIER_TYPE";
  310. private string EventRfIdRead = "RF_ID_READ";
  311. private string EventRfIdReadFailed = "RF_ID_READ_FAILED";
  312. private string EventRfIdWrite = "RF_ID_WRITE";
  313. private string EventRfIdWriteFailed = "RF_ID_WRITE_FAILED";
  314. public string AlarmLoadPortError { get => LPModuleName.ToString() + "Error"; }
  315. public string AlarmLoadPortCommunicationError { get => LPModuleName.ToString() + "CommunicationError"; }
  316. public string AlarmLoadPortWaferProtrusion { get => LPModuleName.ToString() + "WaferProtrusion"; }
  317. public string AlarmLoadPortLoadTimeOut { get => LPModuleName.ToString() + "LoadTimeOut"; }
  318. public string AlarmLoadPortLoadFailed { get => LPModuleName.ToString() + "LoadFailed"; }
  319. public string AlarmLoadPortUnloadTimeOut { get => LPModuleName.ToString() + "UnloadTimeOut"; }
  320. public string AlarmLoadPortUnloadFailed { get => LPModuleName.ToString() + "UnloadFailed"; }
  321. public string AlarmLoadPortMappingError { get => LPModuleName.ToString() + "MappingError"; }
  322. public string AlarmLoadPortMappingTimeout { get => LPModuleName.ToString() + "MappingTimeout"; }
  323. public string AlarmCarrierIDReadError { get => LPModuleName.ToString() + "CarrierIDReadFail"; }
  324. public string AlarmCarrierIDWriteError { get => LPModuleName.ToString() + "CarrierIDWriteFail"; }
  325. public string AlarmLoadPortHomeFailed { get => LPModuleName.ToString() + "HomeFailed"; }
  326. public string AlarmLoadPortHomeTimeout { get => LPModuleName.ToString() + "HomeTimeout"; }
  327. public string AlarmLoadE84TP1Timeout { get => LPModuleName.ToString() + "E84LoadTP1TimeOut"; }
  328. public string AlarmLoadE84TP2Timeout { get => LPModuleName.ToString() + "E84LoadTP2TimeOut"; }
  329. public string AlarmLoadE84TP3Timeout { get => LPModuleName.ToString() + "E84LoadTP3TimeOut"; }
  330. public string AlarmLoadE84TP4Timeout { get => LPModuleName.ToString() + "E84LoadTP4TimeOut"; }
  331. public string AlarmLoadE84TP5Timeout { get => LPModuleName.ToString() + "E84LoadTP5TimeOut"; }
  332. public string AlarmLoadE84TP6Timeout { get => LPModuleName.ToString() + "E84LoadTP6TimeOut"; }
  333. public string AlarmUnloadE84TP1Timeout { get => LPModuleName.ToString() + "E84UnloadTP1TimeOut"; }
  334. public string AlarmUnloadE84TP2Timeout { get => LPModuleName.ToString() + "E84UnloadTP2TimeOut"; }
  335. public string AlarmUnloadE84TP3Timeout { get => LPModuleName.ToString() + "E84UnloadTP3TimeOut"; }
  336. public string AlarmUnloadE84TP4Timeout { get => LPModuleName.ToString() + "E84UnloadTP4TimeOut"; }
  337. public string AlarmUnloadE84TP5Timeout { get => LPModuleName.ToString() + "E84UnloadTP5TimeOut"; }
  338. public string AlarmUnloadE84TP6Timeout { get => LPModuleName.ToString() + "E84UnloadTP6TimeOut"; }
  339. public string AlarmLoadPortMapCrossedWafer => LPModuleName.ToString() + "MapCrossedWafer";
  340. public string AlarmLoadPortMapDoubleWafer => LPModuleName.ToString() + "MapDoubleWafer";
  341. public string AlarmLoadPortMapUnknownWafer => LPModuleName.ToString() + "MapUnknownWafer";
  342. public string AlarmLoadPortCarrierIDIndexConfigError => LPModuleName.ToString() + "LoadPortCarrierIDIndexConfigError";
  343. private IE87CallBack _lpcallback = null;
  344. public IE87CallBack LPCallBack
  345. {
  346. get { return _lpcallback; }
  347. set { _lpcallback = value; }
  348. }
  349. private IE84CallBack _lpE84Callback = null;
  350. public IE84CallBack LPE84Callback
  351. {
  352. get { return _lpE84Callback; }
  353. set
  354. {
  355. _lpE84Callback = value;
  356. _lpE84Callback.OnE84ActiveSignalChange += _lpE84Callback_OnE84ActiveSignalChange;
  357. _lpE84Callback.OnE84PassiveSignalChange += _lpE84Callback_OnE84PassiveSignalChange;
  358. _lpE84Callback.OnE84HandOffComplete += _lpE84Callback_OnE84HandOffComplete;
  359. _lpE84Callback.OnE84HandOffStart += _lpE84Callback_OnE84HandOffStart;
  360. _lpE84Callback.OnE84HandOffTimeout += _lpE84Callback_OnE84HandOffTimeout;
  361. }
  362. }
  363. private ICarrierIDReader _carrierIDReadercallback = null;
  364. public ICarrierIDReader CarrierIDReaderCallBack
  365. {
  366. get { return _carrierIDReadercallback; }
  367. set { _carrierIDReadercallback = value; }
  368. }
  369. public virtual CIDReaderBaseDevice CurrentReader
  370. {
  371. get;
  372. set;
  373. }
  374. public virtual CIDReaderBaseDevice[] CIDReaders
  375. {
  376. get;
  377. set;
  378. }
  379. public virtual bool IsBypassCarrierIDReader
  380. {
  381. get
  382. {
  383. return SC.ContainsItem($"LoadPort.{LPModuleName}.BypassCarrierIDReader") ?
  384. SC.GetValue<bool>($"LoadPort.{LPModuleName}.BypassCarrierIDReader") : false;
  385. }
  386. }
  387. public virtual bool IsAutoDetectCarrierType
  388. {
  389. get
  390. {
  391. return SC.ContainsItem($"LoadPort.{LPModuleName}.AutoDetectCarrierType") ?
  392. SC.GetValue<bool>($"LoadPort.{LPModuleName}.AutoDetectCarrierType") : true;
  393. }
  394. }
  395. public virtual bool IsAutoReadCarrierID
  396. {
  397. get
  398. {
  399. return SC.ContainsItem($"LoadPort.{LPModuleName}.EnableAutoCarrierIdRead") ?
  400. SC.GetValue<bool>($"LoadPort.{LPModuleName}.EnableAutoCarrierIdRead") : true;
  401. }
  402. }
  403. public virtual LoadportCassetteState CassetteState
  404. {
  405. get;
  406. set;
  407. }
  408. public virtual int ValidSlotsNumber
  409. {
  410. get => 25;
  411. }
  412. public ModuleName LPModuleName { get; protected set; }
  413. public WaferSize Size
  414. {
  415. get; set;
  416. } = WaferSize.WS12;
  417. public virtual WaferSize GetCurrentWaferSize()
  418. {
  419. return Size;
  420. }
  421. public virtual bool IsVerifyPreDefineWaferCount
  422. {
  423. get => false;
  424. }
  425. public virtual int PreDefineWaferCount
  426. {
  427. get; set;
  428. }
  429. public virtual int InfoPadCarrierIndex { get; set; }
  430. public string SpecPortName { get; set; } = string.Empty;
  431. public virtual string SpecCarrierType
  432. {
  433. get; set;
  434. } = "";
  435. public virtual string SpecCarrierInformation
  436. {
  437. get
  438. {
  439. if (_isPresent)
  440. return "Index:" + InfoPadCarrierIndex.ToString() + "\r\n"
  441. + "Type:" + SpecCarrierType + "\r\n"
  442. + "Size:" + GetCurrentWaferSize().ToString() +
  443. (IsVerifyPreDefineWaferCount ? ("\r\n" + "Pre-Count:" + PreDefineWaferCount.ToString()) : "");
  444. return "";
  445. }
  446. }
  447. public bool IsAccessSwPressed
  448. {
  449. get { return _isAccessSwPressed; }
  450. }
  451. private void SubscribeDataVariable()
  452. {
  453. DoorState = FoupDoorState.Unknown;
  454. WaferManager.Instance.SubscribeLocation(LPModuleName, 25);
  455. CarrierManager.Instance.SubscribeLocation(LPModuleName.ToString());
  456. DATA.Subscribe(Name, "IsPresent", () => IsFoupPresent);
  457. DATA.Subscribe(Name, "IsPlaced", () => _isPlaced);
  458. DATA.Subscribe(Name, "IsClamped", () => ClampState == FoupClampState.Close);
  459. DATA.Subscribe(Name, "IsDocked", () => DockState == FoupDockState.Docked);
  460. DATA.Subscribe(Name, "IsDoorOpen", () => DoorState == FoupDoorState.Open);
  461. DATA.Subscribe(Name, "IsAccessSwPressed", () => IsAccessSwPressed);
  462. //DATA.Subscribe(Name, "CarrierId", () => _carrierId);
  463. DATA.Subscribe(Name, "LPLotID", () => _lplotID);
  464. DATA.Subscribe(Name, "IsMapped", () => _isMapped);
  465. DATA.Subscribe(Name, "IsAutoDetectCarrierType", () => IsAutoDetectCarrierType);
  466. //DATA.Subscribe($"{Name}.LoadportState", () => Status.ToString());
  467. //DATA.Subscribe($"{Name}.Status", () => "");
  468. //DATA.Subscribe($"{Name}.LoadportBusy", () => );
  469. DATA.Subscribe($"{Name}.LoadportError", () => ErrorCode);
  470. DATA.Subscribe($"{Name}.CassetteState", () => CassetteState);
  471. DATA.Subscribe($"{Name}.FoupClampState", () => ClampState);
  472. DATA.Subscribe($"{Name}.FoupDockState", () => DockState);
  473. DATA.Subscribe($"{Name}.FoupDoorState", () => DoorState);
  474. DATA.Subscribe($"{Name}.FoupDoorPosition", () => DoorPosition);
  475. DATA.Subscribe($"{Name}.SlotMap", () => SlotMap);
  476. DATA.Subscribe($"{Name}.IndicatiorLoad", () => IndicatiorLoad);
  477. DATA.Subscribe($"{Name}.IndicatiorUnload", () => IndicatiorUnload);
  478. DATA.Subscribe($"{Name}.IndicatiorPresence", () => IndicatiorPresence);
  479. DATA.Subscribe($"{Name}.IndicatiorPlacement", () => IndicatiorPlacement);
  480. DATA.Subscribe($"{Name}.IndicatiorAlarm", () => IndicatorAlarm);
  481. DATA.Subscribe($"{Name}.IndicatiorAccessAuto", () => IndicatiorAccessAuto);
  482. DATA.Subscribe($"{Name}.IndicatiorAccessManual", () => IndicatiorAccessManual);
  483. DATA.Subscribe($"{Name}.IndicatiorOpAccess", () => IndicatiorOpAccess);
  484. DATA.Subscribe($"{Name}.IndicatiorStatus1", () => IndicatiorStatus1);
  485. DATA.Subscribe($"{Name}.IndicatiorStatus2", () => IndicatiorStatus2);
  486. DATA.Subscribe($"{Name}.CasstleType", () => (int)CasstleType);
  487. DATA.Subscribe($"{Name}.InfoPadCarrierType", () => SpecCarrierType);
  488. DATA.Subscribe($"{Name}.InfoPadCarrierTypeInformation", () => SpecCarrierInformation);
  489. DATA.Subscribe($"{Name}.InfoPadCarrierIndex", () => InfoPadCarrierIndex);
  490. DATA.Subscribe($"{Name}.CarrierWaferSize", () => GetCurrentWaferSize().ToString());
  491. DATA.Subscribe($"{Name}.PreDefineWaferCount", () => PreDefineWaferCount);
  492. DATA.Subscribe($"{Name}.IsVerifyPreDefineWaferCount", () => IsVerifyPreDefineWaferCount);
  493. EV.Subscribe(new EventItem("Event", EventCarrierArrived, "Carrier arrived"));
  494. EV.Subscribe(new EventItem("Event", EventCarrierRemoved, "Carrier removed"));
  495. EV.Subscribe(new EventItem("Event", EventCarrierIdRead, "Carrier ID read"));
  496. EV.Subscribe(new EventItem("Event", EventCarrierIdReadFailed, "Carrier ID read failed"));
  497. EV.Subscribe(new EventItem("Event", EventCarrierIdWrite, "Carrier ID write"));
  498. EV.Subscribe(new EventItem("Event", EventCarrierIdWriteFailed, "Carrier ID write failed"));
  499. EV.Subscribe(new EventItem("Event", EventSlotMapAvailable, "Slot map available"));
  500. EV.Subscribe(new EventItem("Event", EventCarrierUnloaded, "Carrier unloaded"));
  501. EV.Subscribe(new EventItem("Event", EventCarrierLoaded, "Carrier loaded"));
  502. EV.Subscribe(new EventItem("Event", EventRfIdRead, "Carrier RFID read"));
  503. EV.Subscribe(new EventItem("Event", EventRfIdReadFailed, "Carrier RFID read failed"));
  504. EV.Subscribe(new EventItem("Event", EventRfIdWrite, "Carrier RFID write"));
  505. EV.Subscribe(new EventItem("Event", EventRfIdWriteFailed, "Carrier RFID write failed"));
  506. SubscribeAlarm();
  507. IndicatorStateFeedback = new IndicatorState[20];
  508. if (_lpE84Callback != null)
  509. {
  510. _lpE84Callback.OnE84ActiveSignalChange += _lpE84Callback_OnE84ActiveSignalChange;
  511. _lpE84Callback.OnE84PassiveSignalChange += _lpE84Callback_OnE84PassiveSignalChange;
  512. _lpE84Callback.OnE84HandOffComplete += _lpE84Callback_OnE84HandOffComplete;
  513. _lpE84Callback.OnE84HandOffStart += _lpE84Callback_OnE84HandOffStart;
  514. _lpE84Callback.OnE84HandOffTimeout += _lpE84Callback_OnE84HandOffTimeout;
  515. }
  516. }
  517. private void SubscribeAlarm()
  518. {
  519. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortError, $"Load Port {Name} occurred error.", EventLevel.Alarm, EventType.EventUI_Notify));
  520. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortCommunicationError, $"Load Port {Name}error.", EventLevel.Alarm, EventType.EventUI_Notify));
  521. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortWaferProtrusion, $"Load Port {Name} wafer protrusion error.", EventLevel.Alarm, EventType.EventUI_Notify));
  522. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortLoadTimeOut, $"Load Port {Name} load timeout.", EventLevel.Alarm, EventType.EventUI_Notify));
  523. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortLoadFailed, $"Load Port {Name} load failed.", EventLevel.Alarm, EventType.EventUI_Notify));
  524. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortUnloadTimeOut, $"Load Port {Name} unload timeout.", EventLevel.Alarm, EventType.EventUI_Notify));
  525. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortUnloadFailed, $"Load Port {Name} unload failed.", EventLevel.Alarm, EventType.EventUI_Notify));
  526. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortMappingError, $"Load Port {Name} mapping error.", EventLevel.Alarm, EventType.EventUI_Notify));
  527. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortMappingTimeout, $"Load Port {Name} mapping Timeout.", EventLevel.Alarm, EventType.EventUI_Notify));
  528. EV.Subscribe(new EventItem("Alarm", AlarmCarrierIDReadError, $"Load Port {Name} occurred error when read carrier ID.", EventLevel.Alarm, EventType.EventUI_Notify));
  529. EV.Subscribe(new EventItem("Alarm", AlarmCarrierIDWriteError, $"Load Port {Name} occurred error when write carrierID.", EventLevel.Alarm, EventType.EventUI_Notify));
  530. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortMapCrossedWafer, $"Load Port {Name} mapped crossed wafer.", EventLevel.Alarm, EventType.EventUI_Notify));
  531. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortMapDoubleWafer, $"Load Port {Name} mapped double wafer.", EventLevel.Alarm, EventType.EventUI_Notify));
  532. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortMapUnknownWafer, $"Load Port {Name} mapped unknown wafer.", EventLevel.Alarm, EventType.EventUI_Notify));
  533. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortCarrierIDIndexConfigError, $"Load Port {Name} carrierID reader configuration is invalid.", EventLevel.Alarm, EventType.EventUI_Notify));
  534. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortHomeFailed, $"Load Port {Name} occurred error when home.", EventLevel.Alarm, EventType.EventUI_Notify));
  535. EV.Subscribe(new EventItem("Alarm", AlarmLoadPortHomeTimeout, $"Load Port {Name} home timeout.", EventLevel.Alarm, EventType.EventUI_Notify));
  536. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP1Timeout, $"Load Port {Name} occurred TP1 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  537. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP2Timeout, $"Load Port {Name} occurred TP2 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  538. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP3Timeout, $"Load Port {Name} occurred TP3 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  539. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP4Timeout, $"Load Port {Name} occurred TP4 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  540. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP5Timeout, $"Load Port {Name} occurred TP5 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  541. EV.Subscribe(new EventItem("Alarm", AlarmLoadE84TP6Timeout, $"Load Port {Name} occurred TP6 timeout during loading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  542. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP1Timeout, $"Load Port {Name} occurred TP1 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  543. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP2Timeout, $"Load Port {Name} occurred TP2 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  544. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP3Timeout, $"Load Port {Name} occurred TP3 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  545. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP4Timeout, $"Load Port {Name} occurred TP4 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  546. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP5Timeout, $"Load Port {Name} occurred TP5 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  547. EV.Subscribe(new EventItem("Alarm", AlarmUnloadE84TP6Timeout, $"Load Port {Name} occurred TP6 timeout during unloading foup.", EventLevel.Alarm, EventType.EventUI_Notify));
  548. }
  549. private void _lpE84Callback_OnE84PassiveSignalChange(E84SignalID arg2, bool arg3)
  550. {
  551. }
  552. private void _lpE84Callback_OnE84HandOffTimeout(IOE84Passive.E84Timeout _timeout, string LoadorUnload)
  553. {
  554. if (LoadorUnload == "Load")
  555. {
  556. switch (_timeout)
  557. {
  558. case IOE84Passive.E84Timeout.TP1:
  559. EV.Notify(AlarmLoadE84TP1Timeout);
  560. //OnError(AlarmLoadE84TP1Timeout);
  561. break;
  562. case IOE84Passive.E84Timeout.TP2:
  563. EV.Notify(AlarmLoadE84TP2Timeout);
  564. //OnError(AlarmLoadE84TP2Timeout);
  565. break;
  566. case IOE84Passive.E84Timeout.TP3:
  567. EV.Notify(AlarmLoadE84TP3Timeout);
  568. //OnError(AlarmLoadE84TP3Timeout);
  569. break;
  570. case IOE84Passive.E84Timeout.TP4:
  571. EV.Notify(AlarmLoadE84TP4Timeout);
  572. //OnError(AlarmLoadE84TP4Timeout);
  573. break;
  574. case IOE84Passive.E84Timeout.TP5:
  575. EV.Notify(AlarmLoadE84TP5Timeout);
  576. //OnError(AlarmLoadE84TP5Timeout);
  577. break;
  578. default:
  579. break;
  580. }
  581. }
  582. if (LoadorUnload == "Unload")
  583. {
  584. switch (_timeout)
  585. {
  586. case IOE84Passive.E84Timeout.TP1:
  587. EV.Notify(AlarmUnloadE84TP1Timeout);
  588. //OnError(AlarmUnloadE84TP1Timeout);
  589. break;
  590. case IOE84Passive.E84Timeout.TP2:
  591. EV.Notify(AlarmUnloadE84TP2Timeout);
  592. //OnError(AlarmUnloadE84TP2Timeout);
  593. break;
  594. case IOE84Passive.E84Timeout.TP3:
  595. EV.Notify(AlarmUnloadE84TP3Timeout);
  596. //OnError(AlarmUnloadE84TP3Timeout);
  597. break;
  598. case IOE84Passive.E84Timeout.TP4:
  599. EV.Notify(AlarmUnloadE84TP4Timeout);
  600. //OnError(AlarmUnloadE84TP4Timeout);
  601. break;
  602. case IOE84Passive.E84Timeout.TP5:
  603. EV.Notify(AlarmUnloadE84TP5Timeout);
  604. //OnError(AlarmUnloadE84TP5Timeout);
  605. break;
  606. default:
  607. break;
  608. }
  609. }
  610. }
  611. public void OnE84HandOffStart(bool isload)
  612. {
  613. if (_lpcallback != null) _lpcallback.OnE84HandoffStart(isload);
  614. }
  615. public void OnE84HandOffComplete(bool isload)
  616. {
  617. if (_lpcallback != null) _lpcallback.OnE84HandoffComplete(isload);
  618. }
  619. private void _lpE84Callback_OnE84HandOffStart(string arg2)
  620. {
  621. OnE84HandOffStart(arg2 == "Load");
  622. }
  623. private void _lpE84Callback_OnE84HandOffComplete(string arg2)
  624. {
  625. OnE84HandOffComplete(arg2 == "Load");
  626. }
  627. private void _lpE84Callback_OnE84ActiveSignalChange(E84SignalID arg2, bool arg3)
  628. {
  629. ;
  630. }
  631. public virtual void OnSlotMapRead(string _slotMap)
  632. {
  633. if (_slotMap.Length != ValidSlotsNumber)
  634. {
  635. EV.PostAlarmLog("LoadPort", "Mapping Data Error.");
  636. }
  637. for (int i = 0; i < _slotMap.Length; i++)
  638. {
  639. // No wafer: "0", Wafer: "1", Crossed:"2", Undefined: "?", Overlapping wafers: "W"
  640. WaferInfo wafer = null;
  641. switch (_slotMap[i])
  642. {
  643. case '0':
  644. WaferManager.Instance.DeleteWafer(LPModuleName, i);
  645. CarrierManager.Instance.UnregisterCarrierWafer(Name, i);
  646. break;
  647. case '1':
  648. wafer = WaferManager.Instance.CreateWafer(LPModuleName, i, WaferStatus.Normal);
  649. WaferManager.Instance.UpdateWaferSize(LPModuleName, i, GetCurrentWaferSize());
  650. CarrierManager.Instance.RegisterCarrierWafer(Name, i, wafer);
  651. break;
  652. case '2':
  653. wafer = WaferManager.Instance.CreateWafer(LPModuleName, i, WaferStatus.Crossed);
  654. WaferManager.Instance.UpdateWaferSize(LPModuleName, i, GetCurrentWaferSize());
  655. CarrierManager.Instance.RegisterCarrierWafer(Name, i, wafer);
  656. EV.Notify(AlarmLoadPortMapCrossedWafer);
  657. EV.PostInfoLog("LoadPort", $"{LPModuleName} map crossed wafer on carrier:{_carrierId},slot:{i + 1}.");
  658. break;
  659. case 'W':
  660. wafer = WaferManager.Instance.CreateWafer(LPModuleName, i, WaferStatus.Double);
  661. WaferManager.Instance.UpdateWaferSize(LPModuleName, i, GetCurrentWaferSize());
  662. CarrierManager.Instance.RegisterCarrierWafer(Name, i, wafer);
  663. EV.Notify(AlarmLoadPortMapDoubleWafer);
  664. EV.PostInfoLog("LoadPort", $"{LPModuleName} map double wafer on carrier:{_carrierId},slot:{i + 1}.");
  665. break;
  666. case '?':
  667. wafer = WaferManager.Instance.CreateWafer(LPModuleName, i, WaferStatus.Unknown);
  668. WaferManager.Instance.UpdateWaferSize(LPModuleName, i, GetCurrentWaferSize());
  669. CarrierManager.Instance.RegisterCarrierWafer(Name, i, wafer);
  670. EV.PostInfoLog("LoadPort", $"{LPModuleName} map unknown wafer on carrier:{_carrierId},slot:{i + 1}.");
  671. break;
  672. }
  673. }
  674. SerializableDictionary<string, object> dvid = new SerializableDictionary<string, object>();
  675. dvid["SlotMap"] = _slotMap;
  676. dvid["PortID"] = PortID;
  677. dvid["PORT_CTGRY"] = SpecPortName;
  678. dvid["CarrierType"] = SpecCarrierType;
  679. dvid["CarrierID"] = CarrierId;
  680. EV.Notify(EventSlotMapAvailable, dvid);
  681. if (_slotMap.Contains("2"))
  682. {
  683. MapError = true;
  684. EV.Notify(AlarmLoadPortMappingError);
  685. }
  686. if (_slotMap.Contains("W"))
  687. {
  688. MapError = true;
  689. EV.Notify(AlarmLoadPortMappingError);
  690. }
  691. if (_slotMap.Contains("?"))
  692. {
  693. MapError = true;
  694. EV.Notify(AlarmLoadPortMappingError);
  695. }
  696. if (LPCallBack != null)
  697. LPCallBack.MappingComplete(_carrierId, _slotMap);
  698. _isMapped = true;
  699. }
  700. private string GetSlotMap()
  701. {
  702. WaferInfo[] wafers = WaferManager.Instance.GetWafers(ModuleHelper.Converter(Name));
  703. string slot = "";
  704. for (int i = 0; i < 25; i++)
  705. {
  706. slot += wafers[i].IsEmpty ? "0" : "1";
  707. }
  708. return slot;
  709. }
  710. public void ProceedSetCarrierID(string cid)
  711. {
  712. _carrierId = cid;
  713. CarrierManager.Instance.UpdateCarrierId(Name, cid);
  714. }
  715. public virtual bool SetE84Available(out string reason)
  716. {
  717. if (_lpE84Callback != null)
  718. {
  719. _lpE84Callback.SetHoAutoControl(false);
  720. _lpE84Callback.SetHoAvailable(true);
  721. }
  722. reason = "";
  723. return true;
  724. }
  725. public virtual bool SetE84Unavailable(out string reason)
  726. {
  727. if (_lpE84Callback != null)
  728. {
  729. _lpE84Callback.SetHoAutoControl(false);
  730. _lpE84Callback.SetHoAvailable(false);
  731. }
  732. reason = "";
  733. return true;
  734. }
  735. public virtual bool SetIndicator(IndicatorType light, IndicatorState state)
  736. {
  737. return true;
  738. }
  739. public virtual bool Unload(out string reason)
  740. {
  741. reason = "";
  742. //_doUnloadFoup.SetValue(true, out reason);
  743. //_doLoadFoup.SetValue(false, out reason);
  744. //_doInit.SetValue(false, out reason);
  745. return true;
  746. }
  747. public bool Load(out string reason)
  748. {
  749. reason = "";
  750. //_doUnloadFoup.SetValue(false, out reason);
  751. //_doLoadFoup.SetValue(true, out reason);
  752. //_doInit.SetValue(false, out reason);
  753. return true;
  754. }
  755. public bool Init(out string reason)
  756. {
  757. reason = "";
  758. //_doUnloadFoup.SetValue(false, out reason);
  759. //_doLoadFoup.SetValue(false, out reason);
  760. //_doInit.SetValue(true, out reason);
  761. return true;
  762. }
  763. public bool Stop()
  764. {
  765. var reason = "";
  766. //_doLoadFoup.SetValue(false, out reason);
  767. //_doUnloadFoup.SetValue(false, out reason);
  768. //_doInit.SetValue(false, out reason);
  769. return true;
  770. }
  771. public virtual bool FALoad(out string reason)
  772. {
  773. reason = "";
  774. //_doLoadFoup.SetValue(true, out reason);
  775. return true;
  776. }
  777. public virtual bool WriteRfid(string cid, int startpage, int length, out string reason)
  778. {
  779. reason = "";
  780. return true;
  781. }
  782. public virtual bool ReadRfId(out string reason)
  783. {
  784. reason = "";
  785. return true;
  786. }
  787. public virtual bool FAUnload(out string reason)
  788. {
  789. reason = "";
  790. //_doUnloadFoup.SetValue(true, out reason);
  791. return true;
  792. }
  793. public virtual bool Unclamp(out string reason)
  794. {
  795. reason = "";
  796. _doClamp?.SetValue(false, out reason);
  797. _doRelease?.SetValue(true, out reason);
  798. return true;
  799. }
  800. public virtual bool Clamp(out string reason)
  801. {
  802. reason = "";
  803. _doClamp?.SetValue(true, out reason);
  804. _doRelease?.SetValue(false, out reason);
  805. return true;
  806. }
  807. public virtual bool ReadCarrierID()
  808. {
  809. int offset = SC.ContainsItem($"LoadPort.{LPModuleName}.StartPage") ?
  810. SC.GetValue<int>($"LoadPort.{LPModuleName}.StartPage") : 0;
  811. int length = SC.ContainsItem($"LoadPort.{LPModuleName}.DataReadSize") ?
  812. SC.GetValue<int>($"LoadPort.{LPModuleName}.DataReadSize") : 16;
  813. if (SC.ContainsItem($"CarrierInfo.{LPModuleName}CIDReaderIndex{InfoPadCarrierIndex}"))
  814. {
  815. int cidindex = SC.GetValue<int>($"CarrierInfo.{LPModuleName}CIDReaderIndex{InfoPadCarrierIndex}");
  816. if (CIDReaders != null && CIDReaders.Length > cidindex)
  817. _carrierIDReadercallback = CIDReaders[cidindex];
  818. else
  819. {
  820. return true;
  821. }
  822. }
  823. if (_carrierIDReadercallback != null)
  824. {
  825. if (SC.ContainsItem("CarrierID.CarrierIdReaderProtocolType") && SC.GetStringValue("CarrierID.CarrierIdReaderProtocolType") == "1:N")
  826. return _carrierIDReadercallback.ReadCarrierID(offset, length, int.Parse(Name.ToString().Replace("LP", "")));
  827. return _carrierIDReadercallback.ReadCarrierID(offset, length);
  828. }
  829. return false;
  830. }
  831. #endregion
  832. }
  833. }