CarrierRobotPick.cs 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708
  1. using Aitex.Core.RT.Routine;
  2. using Aitex.Core.RT.SCCore;
  3. using Aitex.Core.Util;
  4. using Aitex.Sorter.Common;
  5. using DocumentFormat.OpenXml.Wordprocessing;
  6. using MECF.Framework.Common.Equipment;
  7. using MECF.Framework.Common.Schedulers;
  8. using MECF.Framework.Common.SubstrateTrackings;
  9. using MECF.Framework.RT.EquipmentLibrary.LogicUnits;
  10. using System;
  11. using System.Collections.Generic;
  12. using FurnaceRT.Equipments.FIMSs;
  13. using FurnaceRT.Equipments.LPs;
  14. using FurnaceRT.Equipments.Stockers;
  15. using FurnaceRT.Equipments.Systems;
  16. using FurnaceRT.Equipments.WaferRobots;
  17. using static FurnaceRT.Equipments.FIMSs.FIMSModule;
  18. namespace FurnaceRT.Equipments.CarrierRobots
  19. {
  20. public class CarrierRobotPick : ModuleRoutine, IRoutine
  21. {
  22. enum RoutineStep
  23. {
  24. SetBufferTargetPosition,
  25. SetBufferMoveTo,
  26. Delay,
  27. Goto,
  28. Pick,
  29. DoorOpen,
  30. DoorClose,
  31. RobotRequestCassettePresent,
  32. CheckCassetteInfoByRobotSensor,
  33. SetStageUnlock,
  34. CheckBeforePick,
  35. CheckGotoFinish,
  36. }
  37. private CarrierRobotModule _cassetteRobotModule;
  38. private ModuleName _source;
  39. private int _sourceSlot;
  40. private Hand _blade;
  41. private int _timeout = 0;
  42. private RD_TRIG _holdTrig = new RD_TRIG();
  43. private R_TRIG _emergencyStopTrig = new R_TRIG();
  44. private R_TRIG _pauseTrig = new R_TRIG();
  45. private R_TRIG _resumeTrig = new R_TRIG();
  46. private RoutineStep _routineStep;
  47. private double _durationTime = 0;
  48. private bool _isHasAlarm = false;
  49. private bool _needStartCheck = true;
  50. public CarrierRobotPick(CarrierRobotModule cassetteModule)
  51. {
  52. _cassetteRobotModule = cassetteModule;
  53. Module = cassetteModule.Module;
  54. Name = "Pick";
  55. }
  56. public void Init(ModuleName source, int sourceSlot, Hand blade, bool isHasAlarm)
  57. {
  58. _source = source;
  59. _sourceSlot = sourceSlot;
  60. _blade = blade;
  61. var para = new List<object> { _source, _sourceSlot, _blade, true };
  62. _cassetteRobotModule.PickCassetteTimeoutAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  63. _cassetteRobotModule.PickCassetteTimeoutAlarm.RetryMessageParas = para.ToArray();
  64. _cassetteRobotModule.PickCassetteFailAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  65. _cassetteRobotModule.PickCassetteFailAlarm.RetryMessageParas = para.ToArray();
  66. _cassetteRobotModule.RequestCassettePresentFailAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  67. _cassetteRobotModule.RequestCassettePresentFailAlarm.RetryMessageParas = para.ToArray();
  68. _cassetteRobotModule.RequestCassettePresentTimeoutAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  69. _cassetteRobotModule.RequestCassettePresentTimeoutAlarm.RetryMessageParas = para.ToArray();
  70. _cassetteRobotModule.SetStageValveFailAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  71. _cassetteRobotModule.SetStageValveFailAlarm.RetryMessageParas = para.ToArray();
  72. _cassetteRobotModule.SetStageValveTimeout.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  73. _cassetteRobotModule.SetStageValveTimeout.RetryMessageParas = para.ToArray();
  74. _cassetteRobotModule.RobotHasError.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  75. _cassetteRobotModule.RobotHasError.RetryMessageParas = para.ToArray();
  76. _cassetteRobotModule.ShutterOpenTimeoutAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  77. _cassetteRobotModule.ShutterOpenTimeoutAlarm.RetryMessageParas = para.ToArray();
  78. _cassetteRobotModule.ShutterCloseTimeoutAlarm.RetryMessage = (int)CarrierRobotModule.MSG.PickRetry;
  79. _cassetteRobotModule.ShutterCloseTimeoutAlarm.RetryMessageParas = para.ToArray();
  80. _isHasAlarm = isHasAlarm;
  81. if (!_isHasAlarm)
  82. _needStartCheck = true;
  83. }
  84. public Result Start(params object[] objs)
  85. {
  86. // 抛出过alarm就不reset
  87. if (!_isHasAlarm)
  88. {
  89. Reset();
  90. }
  91. else
  92. {
  93. _historySteps.Remove((int)_routineStep);
  94. _isHasAlarm = false;
  95. ResetState();
  96. }
  97. _holdTrig.RST = true;
  98. _emergencyStopTrig.RST = true;
  99. _pauseTrig.RST = true;
  100. _resumeTrig.RST = true;
  101. _timeout = SC.GetValue<int>($"{Module}.MotionTimeout");
  102. if (_needStartCheck)
  103. {
  104. if (!Singleton<EquipmentManager>.Instance.Modules.ContainsKey(_source))
  105. {
  106. _cassetteRobotModule.PlaceCassetteFailAlarm.Set($"pick from {_source} failed for not install");
  107. return Result.FAIL;
  108. }
  109. if (ModuleHelper.IsLoadPort(_source))
  110. {
  111. var lpModule = Singleton<EquipmentManager>.Instance.Modules[_source] as LoadPortModule;
  112. if(lpModule == null)
  113. {
  114. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for not install");
  115. return Result.FAIL;
  116. }
  117. if (lpModule != null && !lpModule.CheckReadyForTransfer(ModuleHelper.Converter(Module), _blade, _sourceSlot, EnumTransferType.Pick, out string reason))
  118. {
  119. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for {reason}");
  120. return Result.FAIL;
  121. }
  122. }
  123. else if (_source == ModuleName.FIMS1 || _source == ModuleName.FIMS2)
  124. {
  125. var fims = Singleton<EquipmentManager>.Instance.Modules[_source] as FIMSModule;
  126. if (fims == null)
  127. {
  128. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for not install");
  129. return Result.FAIL;
  130. }
  131. if (fims != null && !fims.CheckReadyForTransfer(ModuleHelper.Converter(Module), _blade, _sourceSlot, EnumTransferType.Pick, out string reason))
  132. {
  133. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for {reason}");
  134. return Result.FAIL;
  135. }
  136. if (!SC.GetValue<bool>("System.IsSimulatorMode"))
  137. {
  138. if (fims != null && !fims.IsFoupExist)
  139. {
  140. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for cassette is not present");
  141. return Result.FAIL;
  142. }
  143. }
  144. }
  145. else
  146. {
  147. var stockerModule = Singleton<EquipmentManager>.Instance.Modules[_source] as StockerModule;
  148. if (stockerModule == null)
  149. {
  150. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for not install");
  151. return Result.FAIL;
  152. }
  153. if (!SC.GetValue<bool>("System.IsSimulatorMode"))
  154. {
  155. if (stockerModule != null && !stockerModule.IsFoupPresent)
  156. {
  157. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for cassette is not present");
  158. return Result.FAIL;
  159. }
  160. }
  161. }
  162. if (SC.GetValue<bool>("System.IsSimulatorMode"))
  163. {
  164. if (!CarrierManager.Instance.CheckNoCarrier(ModuleName.CarrierRobot, 0))
  165. {
  166. _cassetteRobotModule.BladeCassettePresentWarning.Set($"{ModuleName.CarrierRobot} cassette present");
  167. return Result.FAIL;
  168. }
  169. }
  170. else
  171. {
  172. if (_cassetteRobotModule.CarrierRobotDevice.IsWaferPresenceOnBlade1 || !CarrierManager.Instance.CheckNoCarrier(ModuleName.CarrierRobot, 0))
  173. {
  174. _cassetteRobotModule.BladeCassettePresentWarning.Set($"{ModuleName.CarrierRobot} cassette present");
  175. return Result.FAIL;
  176. }
  177. }
  178. if (!CarrierManager.Instance.CheckHasCarrier(_source, 0))
  179. {
  180. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for cassette is not present");
  181. return Result.FAIL;
  182. }
  183. }
  184. Notify($"Start");
  185. return Result.RUN;
  186. }
  187. public void Abort()
  188. {
  189. _cassetteRobotModule.Stop();
  190. (Singleton<EquipmentManager>.Instance.Modules[_source] as ITransferTarget)?.NoteTransferStop(ModuleHelper.Converter(_cassetteRobotModule.Module), _blade, _sourceSlot, EnumTransferType.Pick);
  191. }
  192. public override Result Monitor()
  193. {
  194. try
  195. {
  196. PauseRountine(_cassetteRobotModule.CarrierRobotDevice.IsPause);
  197. if (_cassetteRobotModule.CarrierRobotDevice.IsPause)
  198. return Result.RUN;
  199. CheckBeforePick((int)RoutineStep.CheckBeforePick, _source, _sourceSlot, _blade);
  200. if (ModuleHelper.IsBufferStocker(_source))
  201. {
  202. Goto((int)RoutineStep.Goto, _source, _sourceSlot, _blade, true, _timeout);
  203. SetBufferTargetPosition((int)RoutineStep.SetBufferTargetPosition, _source, _timeout);
  204. SetBufferMoveTo((int)RoutineStep.SetBufferMoveTo, _source, _timeout);
  205. CheckGotoFinish((int)RoutineStep.CheckGotoFinish, _source, _timeout);
  206. }
  207. if (_source == ModuleName.LP1 || _source == ModuleName.LP2)
  208. {
  209. Goto((int)RoutineStep.Goto, _source, _sourceSlot, _blade, true, _timeout);
  210. SaferDoorOpen((int)RoutineStep.DoorOpen, true, _timeout);
  211. CheckGotoFinish((int)RoutineStep.CheckGotoFinish, _source, _timeout);
  212. }
  213. Pick((int)RoutineStep.Pick, _source, _sourceSlot, _blade, _timeout);
  214. if (_source == ModuleName.LP1 || _source == ModuleName.LP2)
  215. SaferDoorOpen((int)RoutineStep.DoorClose, false, _timeout);
  216. //RobotRequestCassettePresent((int)RoutineStep.RobotRequestCassettePresent, _blade, _timeout);
  217. CheckCassetteInfoByRobotSensor((int)RoutineStep.CheckCassetteInfoByRobotSensor, _blade, true);
  218. }
  219. catch (RoutineBreakException)
  220. {
  221. return Result.RUN;
  222. }
  223. catch (RoutineFaildException ex)
  224. {
  225. (Singleton<EquipmentManager>.Instance.Modules[_source] as ITransferTarget)?.NoteTransferStop(ModuleHelper.Converter(_cassetteRobotModule.Module), _blade, _sourceSlot, EnumTransferType.Pick);
  226. return Result.FAIL;
  227. }
  228. (Singleton<EquipmentManager>.Instance.Modules[_source] as ITransferTarget)?.NoteTransferStop(ModuleHelper.Converter(_cassetteRobotModule.Module), _blade, _sourceSlot, EnumTransferType.Pick);
  229. Notify("Finished");
  230. return Result.DONE;
  231. }
  232. private void SetBufferTargetPosition(int id, ModuleName source, int timeout)
  233. {
  234. _routineStep = (RoutineStep)Enum.Parse(typeof(RoutineStep), id.ToString());
  235. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  236. {
  237. Notify($"Set buffer target position {source}");
  238. _cassetteRobotModule.SetBufferTargetPosition(source.ToString());
  239. return true;
  240. }, () =>
  241. {
  242. return _cassetteRobotModule.CheckBufferTargetPosition(source.ToString());
  243. }, timeout * 1000);
  244. if (ret.Item1)
  245. {
  246. if (ret.Item2 == Result.FAIL)
  247. {
  248. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for set buffer target position");
  249. throw (new RoutineFaildException());
  250. }
  251. else if (ret.Item2 == Result.TIMEOUT) //timeout
  252. {
  253. _cassetteRobotModule.PickCassetteTimeoutAlarm.Set($"timeout over {timeout} seconds");
  254. throw (new RoutineFaildException());
  255. }
  256. else
  257. throw (new RoutineBreakException());
  258. }
  259. }
  260. private void SetBufferMoveTo(int id, ModuleName source, int timeout)
  261. {
  262. _routineStep = (RoutineStep)Enum.Parse(typeof(RoutineStep), id.ToString());
  263. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  264. {
  265. Notify($"Set buffer move to {source}");
  266. _cassetteRobotModule.SetBufferMoveTo();
  267. return true;
  268. }, () =>
  269. {
  270. return _cassetteRobotModule.BufferDevice.IsReady && _cassetteRobotModule.BufferDevice.IsInPosition;
  271. }, timeout * 1000);
  272. if (ret.Item1)
  273. {
  274. if (ret.Item2 == Result.FAIL)
  275. {
  276. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for robot error, error code={_cassetteRobotModule.CarrierRobotDevice.ErrorCode}");
  277. throw (new RoutineFaildException());
  278. }
  279. else if (ret.Item2 == Result.TIMEOUT) //timeout
  280. {
  281. _cassetteRobotModule.PickCassetteTimeoutAlarm.Set($"timeout over {timeout} seconds");
  282. throw (new RoutineFaildException());
  283. }
  284. else
  285. throw (new RoutineBreakException());
  286. }
  287. }
  288. private void Pick(int id, ModuleName source, int slot, Hand hand, int timeout)
  289. {
  290. _routineStep = (RoutineStep)Enum.Parse(typeof(RoutineStep), id.ToString());
  291. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  292. {
  293. Notify($"Send pick from {source} command to robot device");
  294. string reason;
  295. (Singleton<EquipmentManager>.Instance.Modules[source] as ITransferTarget)?.NoteTransferStart(ModuleHelper.Converter(_cassetteRobotModule.Module), hand, slot, EnumTransferType.Pick);
  296. if (!_cassetteRobotModule.RobotPick(source, slot, hand, out reason))
  297. {
  298. //_cassetteRobotModule.PickCassetteFailAlarm.Description = reason;
  299. _cassetteRobotModule.PickCassetteFailAlarm.Set(reason);
  300. return false;
  301. }
  302. return true;
  303. }, () =>
  304. {
  305. if (_cassetteRobotModule.CarrierRobotDevice.IsReady() && !_cassetteRobotModule.CarrierRobotDevice.IsError)
  306. {
  307. return true;
  308. }
  309. return false;
  310. }, timeout * 1000);
  311. if (ret.Item1)
  312. {
  313. if (ret.Item2 == Result.FAIL)
  314. {
  315. //_cassetteRobotModule.PickCassetteFailAlarm.Description = $"{_cassetteRobotModule.CassetteRobotDevice.ErrorCode}";
  316. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for robot error, error code={_cassetteRobotModule.CarrierRobotDevice.ErrorCode}");
  317. throw (new RoutineFaildException());
  318. }
  319. else if (ret.Item2 == Result.TIMEOUT) //timeout
  320. {
  321. //_cassetteRobotModule.PickCassetteTimeoutAlarm.Description = $"timeout over {timeout} seconds";
  322. _cassetteRobotModule.PickCassetteTimeoutAlarm.Set($"timeout over {timeout} seconds");
  323. throw (new RoutineFaildException());
  324. }
  325. else
  326. throw (new RoutineBreakException());
  327. }
  328. }
  329. private void RobotRequestCassettePresent(int id, Hand hand, int timeout)
  330. {
  331. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  332. {
  333. Notify("Request cassette present");
  334. if (!_cassetteRobotModule.RequestCassettePresent(hand, out string reason))
  335. {
  336. //_cassetteRobotModule.RequestCassettePresentFailAlarm.Description = reason;
  337. _cassetteRobotModule.RequestCassettePresentFailAlarm.Set(reason);
  338. return false;
  339. }
  340. return true;
  341. }, () =>
  342. {
  343. if (_cassetteRobotModule.CarrierRobotDevice.IsReady() && !_cassetteRobotModule.CarrierRobotDevice.IsError)
  344. {
  345. return true;
  346. }
  347. return false;
  348. }, timeout * 1000);
  349. if (ret.Item1)
  350. {
  351. if (ret.Item2 == Result.FAIL)
  352. {
  353. throw (new RoutineFaildException());
  354. }
  355. else if (ret.Item2 == Result.TIMEOUT) //timeout
  356. {
  357. //_cassetteRobotModule.RequestCassettePresentTimeoutAlarm.Description = $"timeout over {timeout} seconds";
  358. _cassetteRobotModule.RequestCassettePresentTimeoutAlarm.Set($"timeout over {timeout} seconds");
  359. throw (new RoutineFaildException());
  360. }
  361. else
  362. throw (new RoutineBreakException());
  363. }
  364. }
  365. private void CheckCassetteInfoByRobotSensor(int id, Hand hand, bool isAfterPick)
  366. {
  367. Tuple<bool, Result> ret = Execute(id, () =>
  368. {
  369. Notify($"Check cassette info by robot RQ present");
  370. if (SC.GetValue<bool>("System.IsSimulatorMode"))
  371. return true;
  372. if (hand == Hand.Blade1 || hand == Hand.Both)
  373. {
  374. if (!isAfterPick && _cassetteRobotModule.CarrierRobotDevice.IsWaferPresenceOnBlade1)
  375. {
  376. //_cassetteRobotModule.RobotSensorFoundCassetteOnBladeAfterPlaceAlarm.Description = "Cassette Robot sensor found cassette on blade 1";
  377. _cassetteRobotModule.RobotSensorFoundCassetteOnBladeAfterPlaceAlarm.Set("Cassette Robot sensor found cassette on blade 1");
  378. return false;
  379. }
  380. if (isAfterPick && !_cassetteRobotModule.CarrierRobotDevice.IsWaferPresenceOnBlade1)
  381. {
  382. //_cassetteRobotModule.RobotSensorNotFoundCassetteOnBladeAfterPickAlarm.Description = "Cassette Robot sensor no cassette on blade 1";
  383. _cassetteRobotModule.RobotSensorNotFoundCassetteOnBladeAfterPickAlarm.Set("Cassette Robot sensor no cassette on blade 1");
  384. return false;
  385. }
  386. }
  387. if (hand == Hand.Blade2 || hand == Hand.Both)
  388. {
  389. if (!isAfterPick && _cassetteRobotModule.CarrierRobotDevice.IsWaferPresenceOnBlade2)
  390. {
  391. //_cassetteRobotModule.RobotSensorFoundCassetteOnBladeAfterPlaceAlarm.Description = "Cassette Robot sensor found cassette on blade 2";
  392. _cassetteRobotModule.RobotSensorFoundCassetteOnBladeAfterPlaceAlarm.Set("Cassette Robot sensor found cassette on blade 2");
  393. return false;
  394. }
  395. if (isAfterPick && !_cassetteRobotModule.CarrierRobotDevice.IsWaferPresenceOnBlade2)
  396. {
  397. //_cassetteRobotModule.RobotSensorNotFoundCassetteOnBladeAfterPickAlarm.Description = "Cassette Robot sensor no cassette on blade 2";
  398. _cassetteRobotModule.RobotSensorNotFoundCassetteOnBladeAfterPickAlarm.Set("Cassette Robot sensor no cassette on blade 2");
  399. return false;
  400. }
  401. }
  402. return true;
  403. });
  404. if (ret.Item1)
  405. {
  406. if (ret.Item2 == Result.FAIL)
  407. {
  408. //_cassetteRobotModule.CheckCassetteInformationFailAlarm.Description = $"check cassette info failed.";
  409. _cassetteRobotModule.CheckCassetteInformationFailAlarm.Set($"check cassette info failed.");
  410. throw (new RoutineFaildException());
  411. }
  412. else
  413. throw (new RoutineBreakException());
  414. }
  415. }
  416. private void CheckBeforePick(int id, ModuleName source, int slot, Hand blade)
  417. {
  418. Tuple<bool, Result> ret = Execute(id, () =>
  419. {
  420. Notify($"Check pick from {source} condition");
  421. string reason = string.Empty;
  422. if (_cassetteRobotModule.CarrierRobotDevice.IsError)
  423. {
  424. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for robot error, error code={_cassetteRobotModule.CarrierRobotDevice.ErrorCode}");
  425. return false;
  426. }
  427. if (!_cassetteRobotModule.CarrierRobotDevice.IsReady())
  428. {
  429. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for robot isn't Ready");
  430. return false;
  431. }
  432. if (!CarrierManager.Instance.CheckHasCarrier(_source, 0))
  433. {
  434. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for pod is not present");
  435. return false;
  436. }
  437. if (source == ModuleName.LP1 || source == ModuleName.LP2)
  438. {
  439. var lpModule = Singleton<EquipmentManager>.Instance.Modules[_source] as LoadPortModule;
  440. if (lpModule != null && !lpModule.CheckReadyForTransfer(ModuleHelper.Converter(Module), blade, slot, EnumTransferType.Pick, out reason))
  441. {
  442. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for {reason}");
  443. return false;
  444. }
  445. }
  446. else if (source == ModuleName.FIMS1 || source == ModuleName.FIMS2)
  447. {
  448. var fims = Singleton<EquipmentManager>.Instance.Modules[source] as FIMSModule;
  449. if (fims != null && !fims.CheckReadyForTransfer(ModuleHelper.Converter(Module), blade, slot, EnumTransferType.Pick, out reason))
  450. {
  451. _cassetteRobotModule.PickCassetteFailAlarm.Set(reason);
  452. return false;
  453. }
  454. if (!SC.GetValue<bool>("System.IsSimulatorMode"))
  455. {
  456. if (fims != null && !fims.IsFoupExist)
  457. {
  458. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {_source} failed for carrier is not present");
  459. return false;
  460. }
  461. }
  462. }
  463. else
  464. {
  465. if (!SC.GetValue<bool>("System.IsSimulatorMode"))
  466. {
  467. var stockerModule = Singleton<EquipmentManager>.Instance.Modules[source] as StockerModule;
  468. if (stockerModule != null && !stockerModule.IsFoupPresent)
  469. {
  470. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for cassette is not present");
  471. return false;
  472. }
  473. }
  474. }
  475. if (blade == Hand.Blade1)
  476. {
  477. if (!CarrierManager.Instance.CheckHasCarrier(source, 0))
  478. {
  479. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for {source} no carrrier");
  480. return false;
  481. }
  482. if (!CarrierManager.Instance.CheckNoCarrier(Module, 0))
  483. {
  484. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for blade has carrier");
  485. return false;
  486. }
  487. }
  488. else if (blade == Hand.Blade2)
  489. {
  490. if (!CarrierManager.Instance.CheckHasCarrier(source, 0))
  491. {
  492. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for {source} no carrier");
  493. return false;
  494. }
  495. if (!CarrierManager.Instance.CheckNoCarrier(Module, 0))
  496. {
  497. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for blade has carrier");
  498. return false;
  499. }
  500. }
  501. else
  502. {
  503. if (!CarrierManager.Instance.CheckHasCarrier(source, 0))
  504. {
  505. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for {source} no carrier");
  506. return false;
  507. }
  508. if (!CarrierManager.Instance.CheckNoCarrier(Module, 0))
  509. {
  510. _cassetteRobotModule.PickCassetteFailAlarm.Set($"pick from {source} failed for blade has carrier");
  511. return false;
  512. }
  513. }
  514. return true;
  515. });
  516. if (ret.Item1)
  517. {
  518. if (ret.Item2 == Result.FAIL)
  519. {
  520. throw (new RoutineFaildException());
  521. }
  522. }
  523. _needStartCheck = false;
  524. }
  525. private void Goto(int id, ModuleName target, int slot, Hand hand, bool isPickReady, int timeout)
  526. {
  527. _routineStep = (RoutineStep)Enum.Parse(typeof(RoutineStep), id.ToString());
  528. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  529. {
  530. Notify($"Send goto to {target} command to robot device");
  531. string reason;
  532. _cassetteRobotModule.RobotGoto(target, slot, hand, isPickReady, out reason);
  533. return true;
  534. }, () =>
  535. {
  536. return true;
  537. }, timeout * 1000);
  538. if (ret.Item1)
  539. {
  540. if (ret.Item2 == Result.FAIL)
  541. {
  542. _cassetteRobotModule.GotoFailAlarm.Set($"goto to {target} failed for robot error, error code={_cassetteRobotModule.CarrierRobotDevice.ErrorCode}");
  543. throw (new RoutineFaildException());
  544. }
  545. else if (ret.Item2 == Result.TIMEOUT) //timeout
  546. {
  547. _cassetteRobotModule.GotoTimeoutAlarm.Set($"timeout over {timeout} seconds");
  548. throw (new RoutineFaildException());
  549. }
  550. else
  551. throw (new RoutineBreakException());
  552. }
  553. }
  554. private void CheckGotoFinish(int id, ModuleName target, int timeout)
  555. {
  556. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  557. {
  558. Notify($"Check goto to {target} command finish");
  559. return true;
  560. }, () =>
  561. {
  562. if (_cassetteRobotModule.CarrierRobotDevice.IsError)
  563. return null;
  564. if (_cassetteRobotModule.CarrierRobotDevice.IsReady() && !_cassetteRobotModule.CarrierRobotDevice.IsError)
  565. {
  566. return true;
  567. }
  568. return false;
  569. }, timeout * 1000);
  570. if (ret.Item1)
  571. {
  572. if (ret.Item2 == Result.FAIL)
  573. {
  574. _cassetteRobotModule.GotoFailAlarm.Set($"goto to {target} failed for robot error, error code={_cassetteRobotModule.CarrierRobotDevice.ErrorCode}");
  575. throw (new RoutineFaildException());
  576. }
  577. else if (ret.Item2 == Result.TIMEOUT) //timeout
  578. {
  579. _cassetteRobotModule.GotoTimeoutAlarm.Set($"timeout over {timeout} seconds");
  580. throw (new RoutineFaildException());
  581. }
  582. else
  583. throw (new RoutineBreakException());
  584. }
  585. }
  586. private void SaferDoorOpen(int id, bool isOpen, int timeout)
  587. {
  588. Tuple<bool, Result> ret = ExecuteAndWait(id, () =>
  589. {
  590. Notify($"Shutter Door {(isOpen ? "Open" : "Close")}");
  591. if (isOpen)
  592. _cassetteRobotModule.DoorDevice.Open();
  593. else
  594. _cassetteRobotModule.DoorDevice.Close();
  595. return true;
  596. }, () =>
  597. {
  598. return isOpen ? _cassetteRobotModule.DoorDevice.OpenCloseStatus == Devices.DeviceStatus.Open : _cassetteRobotModule.DoorDevice.OpenCloseStatus == Devices.DeviceStatus.Close;
  599. }, timeout * 1000);
  600. if (ret.Item1)
  601. {
  602. if (ret.Item2 == Result.FAIL)
  603. {
  604. throw new RoutineFaildException();
  605. }
  606. else if (ret.Item2 == Result.TIMEOUT) //timeout
  607. {
  608. if (isOpen)
  609. _cassetteRobotModule.ShutterOpenTimeoutAlarm.Set($"timeout over {timeout} seconds");
  610. else
  611. _cassetteRobotModule.ShutterCloseTimeoutAlarm.Set($"timeout over {timeout} seconds");
  612. throw (new RoutineFaildException());
  613. }
  614. else
  615. throw new RoutineBreakException();
  616. }
  617. }
  618. }
  619. }