PMProcessRoutine.cs 8.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284
  1. using System;
  2. using System.Collections.Generic;
  3. using Aitex.Core.RT.Routine;
  4. using Aitex.Core.RT.SCCore;
  5. using Venus_RT.Devices;
  6. using MECF.Framework.Common.SubstrateTrackings;
  7. using System.Text.Json;
  8. using Venus_Core;
  9. namespace Venus_RT.Modules.PMs
  10. {
  11. class PMProcessRoutine : PMRoutineBase, IRoutine
  12. {
  13. private enum ProcessStep
  14. {
  15. kPreparePressure,
  16. kPrepareTemperature,
  17. kRunRecipes,
  18. kEnd,
  19. }
  20. public string CurrentRunningRecipe { get; set; }
  21. public string ProcessRecipeName { get; set; }
  22. public string ChuckRecipeName { get; set; }
  23. public string DechuckRecipeNamae { get; set; }
  24. public string CleanRecipeName { get; set; }
  25. public RecipeHead ProcessRecipeHead { get; set; }
  26. public DateTime RecipeStartTime { get; private set; }
  27. private readonly PumpDownRoutine _pumpDownRoutine;
  28. private bool _withWafer = true;
  29. private bool _needPumpDown = false;
  30. private Recipe _currentRecipe = null;
  31. private int _currentStep = 0;
  32. private Queue<Recipe> _qeRecipes = new Queue<Recipe>();
  33. private double _tolerance;
  34. private double _OffsetTemp = 0.0f;
  35. private bool _bLoopMode = false;
  36. private int _loopStartStep = 0;
  37. private int _loopCounter = 0;
  38. private double ChillerTemp
  39. {
  40. get
  41. {
  42. if (ProcessRecipeHead != null)
  43. {
  44. if (!string.IsNullOrEmpty(ProcessRecipeHead.ChillerTemp))
  45. {
  46. double setpoint = Convert.ToDouble(ProcessRecipeHead.ChillerTemp);
  47. if (setpoint > 0 && setpoint < 600)
  48. return setpoint;
  49. }
  50. }
  51. return 0;
  52. }
  53. }
  54. private double BasePressure
  55. {
  56. get
  57. {
  58. if (ProcessRecipeHead != null)
  59. {
  60. if (!string.IsNullOrEmpty(ProcessRecipeHead.BasePressure))
  61. {
  62. double setpoint = Convert.ToDouble(ProcessRecipeHead.BasePressure);
  63. if (setpoint > 0 && setpoint < 750000)
  64. return setpoint;
  65. }
  66. }
  67. return SC.GetValue<int>($"{Module}.Pump.PumpBasePressure");
  68. }
  69. }
  70. public double EstimatedTotalLeftTime
  71. {
  72. get;
  73. private set;
  74. }
  75. public PMProcessRoutine(JetPM chamber, PumpDownRoutine pdRoutine) : base(chamber)
  76. {
  77. Name = "Process";
  78. _pumpDownRoutine = pdRoutine;
  79. }
  80. public RState Start(params object[] objs)
  81. {
  82. if (_withWafer && WaferManager.Instance.CheckNoWafer(Module.ToString(), 0))
  83. {
  84. Stop($"can not run process, no wafer at {Module}");
  85. return RState.Failed;
  86. }
  87. if (!CheckSlitDoor() || !CheckDryPump() || !CheckTurboPump())
  88. {
  89. return RState.Failed;
  90. }
  91. // Load/Validate Recipe
  92. _qeRecipes.Clear();
  93. string recipeName = (string)objs[0];
  94. Recipe recipe = Recipe.Load(recipeName);
  95. if(recipe == null)
  96. {
  97. return RState.Failed;
  98. }
  99. switch(recipe.Header.Type)
  100. {
  101. case RecipeType.Process:
  102. var chuckRecipe = Recipe.Load(recipe.Header.ChuckRecipe);
  103. var dechuckRecipe = Recipe.Load(recipe.Header.DechuckRecipe);
  104. if(chuckRecipe == null || dechuckRecipe == null)
  105. {
  106. return RState.Failed;
  107. }
  108. ProcessRecipeName = recipeName;
  109. ChuckRecipeName = recipe.Header.ChuckRecipe;
  110. DechuckRecipeNamae = recipe.Header.DechuckRecipe;
  111. _qeRecipes.Enqueue(chuckRecipe);
  112. _qeRecipes.Enqueue(recipe);
  113. _qeRecipes.Enqueue(dechuckRecipe);
  114. break;
  115. case RecipeType.Chuck:
  116. ChuckRecipeName = recipeName;
  117. _qeRecipes.Enqueue(recipe);
  118. break;
  119. case RecipeType.DeChuck:
  120. DechuckRecipeNamae = recipeName;
  121. _qeRecipes.Enqueue(recipe);
  122. break;
  123. case RecipeType.Clean:
  124. CleanRecipeName = recipeName;
  125. _qeRecipes.Enqueue(recipe);
  126. break;
  127. }
  128. _bLoopMode = false;
  129. _loopStartStep = 0;
  130. _loopCounter = 0;
  131. _tolerance = SC.GetValue<double>($"System.MaxTemperatureToleranceToTarget");
  132. _OffsetTemp = SC.GetValue<double>($"{Module}.Chiller.ChillerTemperatureOffset");
  133. return Runner.Start(Module, Name);
  134. }
  135. public RState Monitor()
  136. {
  137. Runner.Run((int)ProcessStep.kPreparePressure, PreparePressure, IsPressureReady)
  138. .Run((int)ProcessStep.kPrepareTemperature, PrepareTemp, IsTempReady)
  139. .Run((int)ProcessStep.kRunRecipes, StartNewRecipe, RunRecipes)
  140. .End((int)ProcessStep.kEnd, ProcessDone, _delay_1s);
  141. return Runner.Status;
  142. }
  143. private bool PreparePressure()
  144. {
  145. if(_chamber.ChamberPressure < BasePressure)
  146. {
  147. _needPumpDown = false;
  148. return true;
  149. }
  150. _needPumpDown = true;
  151. return _pumpDownRoutine.Start(BasePressure) == RState.Running;
  152. }
  153. private bool IsPressureReady()
  154. {
  155. if (_needPumpDown == false)
  156. return true;
  157. var status = _pumpDownRoutine.Monitor();
  158. if(status == RState.End)
  159. {
  160. return true;
  161. }
  162. else if (status == RState.Failed || status == RState.Timeout)
  163. {
  164. Runner.Stop($"Pump down to {BasePressure} failed.");
  165. return true;
  166. }
  167. return false;
  168. }
  169. private bool PrepareTemp()
  170. {
  171. return SetCoolantTemp(ChillerTemp, _OffsetTemp);
  172. }
  173. private bool IsTempReady()
  174. {
  175. return CheckCoolantTemp(ChillerTemp, _tolerance);
  176. }
  177. private RState StartNewStep()
  178. {
  179. var state = _currentRecipe.Steps[_currentStep].Start();
  180. if (state != RState.Running)
  181. return state;
  182. if (_currentRecipe.Steps[_currentStep].CycleStart)
  183. {
  184. if (!_bLoopMode)
  185. {
  186. _bLoopMode = true;
  187. _loopStartStep = _currentStep;
  188. _loopCounter = _currentRecipe.Steps[_currentStep].CycleNumber;
  189. }
  190. }
  191. return RState.Running;
  192. }
  193. private bool StartNewRecipe()
  194. {
  195. if(_qeRecipes.Count > 0)
  196. {
  197. _currentStep = 0;
  198. _currentRecipe = _qeRecipes.Dequeue();
  199. CurrentRunningRecipe = _currentRecipe.Header.Name;
  200. Notify($"Recipe:{CurrentRunningRecipe} start");
  201. return StartNewStep() == RState.Running;
  202. }
  203. return false;
  204. }
  205. private bool RunRecipes()
  206. {
  207. var step = _currentRecipe.Steps[_currentStep];
  208. var result = step.Run();
  209. if(result == RState.Failed)
  210. {
  211. Runner.Stop($"Recipe:{CurrentRunningRecipe}, Step:{_currentStep + 1} Failed");
  212. return true;
  213. }
  214. else if(result == RState.End)
  215. {
  216. _currentRecipe.Steps[_currentStep].End();
  217. if(_currentRecipe.Steps[_currentStep].CycleEnd)
  218. {
  219. if(_loopCounter > 0)
  220. {
  221. _loopCounter--;
  222. _currentStep = _loopStartStep;
  223. return StartNewStep() != RState.Running;
  224. }
  225. else
  226. {
  227. _bLoopMode = false;
  228. _loopStartStep = 0;
  229. }
  230. }
  231. if (_currentStep < _currentRecipe.Steps.Count - 1)
  232. {
  233. _currentStep++;
  234. return StartNewStep() != RState.Running;
  235. }
  236. else
  237. {
  238. Notify($"Recipe:{CurrentRunningRecipe} finished");
  239. return !StartNewRecipe();
  240. }
  241. }
  242. return false;
  243. }
  244. private bool ProcessDone()
  245. {
  246. return true;
  247. }
  248. public void Abort()
  249. {
  250. CloseAllValves();
  251. }
  252. }
  253. }