public override void HandleToolStopped(object stateSwchLock) { try { //NMC.Scheduling.Scheduler.GetInstance().StopSchedule(); // <><> stop scheduler for continuous calls, ALN 20150928 MissRun if (this.mRescheduleEventFired) { this.mRescheduleEventFired = false; // <> reset //<><><>yangy 20160617<><><>Coordinator.GetIns().RecalculateProcessTime(); string err = ""; Coordinator.GetIns().RecalculateProcessTime(ref err); if (!string.IsNullOrEmpty(err)) { Coordinator.GetIns().GetLogger().ErrorFormat("TaskManagerRunning::HandleToolStopped(): {0}", err); } TaskManager.GetIns().UpdateAllTasks(); // <><> yangy: update task for removed modules
List<ArrayList> routelist = new List<ArrayList>();
List<Material> wfs = new List<Material>();
using (StreamReader sr = new StreamReader("txt.txt"))
{
List<string> strlist = new List<string>();
string str = null;
List<string> tasklist = new List<string>();
Dictionary<string, double> modTimes = ModuleManager.GetIns().GetModuleAvailableTimes();
while ((str = sr.ReadLine()) != null)
{
if (str.Contains("DefineRoutes"))
{
str = str.Substring(str.IndexOf(':') + 1);
string[] steplist = str.Split('|');
ArrayList routedefine = new ArrayList();
for (int i = 1; i <= 25; ++i)
{
Route route = new Route("route");
for (int stepidx = 0; stepidx < steplist.Length; ++stepidx)
{
RouteStep step = new RouteStep();
if (stepidx == 0 || stepidx == steplist.Length - 1)
{
Visit visit = new Visit(steplist[stepidx], i, "", "", "");
step.AddVisit(visit);
}
else
{
//
string[] visitlist = steplist[stepidx].Split(',');
for (int vstidx = 0; vstidx < visitlist.Length; ++vstidx)
{
string[] rcpstr = visitlist[vstidx].Split('#');
string chamber = rcpstr[0];
string rcp = rcpstr.Length == 1 ? "" : rcpstr[1];
Visit visit = new Visit(chamber, 0, "", "", rcp);
step.AddVisit(visit);
}
}
route.AddStep(step);
}
routedefine.Add(route);
}
routelist.Add(routedefine);
}
if (str.Contains("@@ MovableMaterial:"))
{
int pos = str.IndexOf("ID(");
int matid = int.Parse(str.Substring(pos + 3, str.IndexOf(')', pos) - pos - 3));
strlist.Add(str.Substring(pos + 3, str.IndexOf(')', pos) - pos - 3)); // matid
pos = str.IndexOf("Name(");
string[] matName = str.Substring(pos + 5, str.IndexOf(')', pos) - pos - 5).Split('.');
if (!tasklist.Contains(matName[0]))
{
tasklist.Add(matName[0]);
}
int taskid = tasklist.Count;
int matsrcslot = int.Parse(matName[1]);
strlist.Add(tasklist.Count.ToString()); // taskid
strlist.Add(matName[1]); // matsrcslot
pos = str.IndexOf("CurStep(");
int stepid = int.Parse(str.Substring(pos + 8, str.IndexOf(')', pos) - pos - 8));
strlist.Add(str.Substring(pos + 8, str.IndexOf(')', pos) - pos - 8)); // curstep
pos = str.IndexOf("CurPos(");
string curPos = str.Substring(pos + 7, str.IndexOf(')', pos) - pos - 7);
strlist.Add(str.Substring(pos + 7, str.IndexOf(')', pos) - pos - 7)); // curpos
Material matNew = new Material(matid, taskid, (Route)routelist[taskid - 1][matsrcslot - 1], stepid, curPos.Substring(0, curPos.LastIndexOf('_')), int.Parse(curPos.Substring(curPos.LastIndexOf('_') + 1)), true, "nocare", matName[0] + "." + matName[1], "nocare", 0);
matNew.IsFromPureJob = true;
wfs.Add(matNew);
if (!curPos.Contains("ATR") && !curPos.Contains("VTR"))
{
matNew.Route.GetStep(stepid).GetVisit(curPos.Substring(0, curPos.IndexOf('_'))).ProcessRecipe = string.Empty;
}
}
if (str.Contains("UnleftMats"))
{
int taskid = int.Parse(str.Substring(str.IndexOf(':') + 1, 1));
string[] startend = str.Substring(str.IndexOf(',') + 1).Split('~');
int start = int.Parse(startend[0]);
int end = int.Parse(startend[1]);
for (; start <= end; ++start)
{
Route route = (Route)routelist[taskid - 1][start - 1];
string station = route.GetStep(0).GetVisit(0).StationName;
Material matlp = new Material(10000 + start, taskid, route, 0, station, start, true, "nocare", station + "." + start.ToString(), "nocare", 0);
matlp.IsFromPureJob = true;
wfs.Add(matlp);
}
}
if (str.Contains("UpdateStationAvailableTime:"))
{
double availabletime = double.Parse(str.Substring(str.IndexOf("= ") + 2));
if (availabletime != 0)
{
string chamber = str.Substring(str.IndexOf("UpdateStationAvailableTime: ") + 28, str.IndexOf(" =") - str.IndexOf("UpdateStationAvailableTime: ") - 28);
modTimes[chamber] = availabletime;
}
}
}
NMC.Scheduling.Scheduler.GetInstance().AddMaterials(wfs); // deep copy all materials <>
Coordinator.GetIns().SetMDxRecvMatIntvlMin(); // <> yangy 20170320: for MDx
//Dictionary<string, double> modTimes = ModuleManager.GetIns().GetModuleAvailableTimes();
NMC.Scheduling.Scheduler.GetInstance().UpdateStationAvailableTime(modTimes);
}
#endif
NMC.Scheduling.Scheduler.GetInstance().AddMaterials(MoveManager.GetIns().GetSortedMats()); // deep copy all materials <>
Coordinator.GetIns().SetMDxRecvMatIntvlMin(); // <> yangy 20170320: for MDx
NMC.Scheduling.Scheduler.GetInstance().UpdateStationAvailableTime(ModuleManager.GetIns().GetModuleAvailableTimes());
#endif
NMC.Scheduling.Scheduler.GetInstance().StartSchedule(); // will trigger new move event <>
}
}
catch (Exception ex) // <> yangy 20181016: avoid deadlock from Polaris 300mm zentao_bug_6354
{
Coordinator.GetIns().GetLogger().FatalFormat("TaskManagerRunning::HandleToolStopped(): {0}", ex.Message);
}
finally // <> yangy 20181016: avoid deadlock from Polaris 300mm zentao_bug_6354
{
Monitor.Exit(stateSwchLock); // <><> avoid racing-condition with 'PauseTool()' method
}
}
}这个C#程序可以实现对log文件的读取,比如log内容是这样的:DefineRoutes:LP2|LA|Ch1#/Ch1/3601;1|Ch3#/Ch3/175;1|Ch4#/Ch4/23.3;1|Ch5#/Ch5/65.3;1|LB|LP2
DefineRoutes:LP1|LA|Ch1#/Ch1/601;1|Ch3#/Ch3/110;1|Ch5#/Ch5/65.3;1|LB|LP1
2021-07-31 13:07:59.236 WARN [17420] Scheduler - @@ MovableMaterial: ID(378), Name(LP2.3), CurPos(Ch5_1), CurStep(5)
2021-07-31 13:07:59.236 WARN [17420] Scheduler - @@ MovableMaterial: ID(379), Name(LP2.4), CurPos(Ch4_1), CurStep(4)
2021-07-31 13:07:59.236 WARN [17420] Scheduler - @@ MovableMaterial: ID(380), Name(LP2.5), CurPos(Ch3_1), CurStep(3)
2021-07-31 13:07:59.236 WARN [17420] Scheduler - @@ MovableMaterial: ID(381), Name(LP2.6), CurPos(Ch1_7_1), CurStep(2)
2021-07-31 13:07:59.236 WARN [17420] Scheduler - @@ MovableMaterial: ID(382), Name(LP2.7), CurPos(Ch1_18_1), CurStep(2)。 现在需要对程序添加新功能,可以实现读取log自动生成路径的代码。比如log日志文件中的路径表示为:2025-08-28 13:36:47.429 WARN [11692] Coordinator - Slot{0}: Route(a) Group:Default2025-08-28 13:36:47.429 WARN [11692] Coordinator - Step(0)2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).StationName: LB2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).SlotID: 22025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).ProcessRecipe: 2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(1).StationName: LA2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(1).SlotID: 22025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(1).ProcessRecipe: 2025-08-28 13:36:47.429 WARN [11692] Coordinator - Step(1)2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).StationName: ChD2025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).SlotID: 02025-08-28 13:36:47.429 WARN [11692] Coordinator - Visit(0).ProcessRecipe: /ChD/test;12025-08-28 13:36:47.430 WARN [11692] Coordinator - Visit(1).StationName: ChC2025-08-28 13:36:47.430 WARN [11692] Coordinator - Visit(1).SlotID: 02025-08-28 13:36:47.430 WARN [11692] Coordinator - Visit(1).ProcessRecipe: /ChC/test;12025-08-28 13:36:47.431 WARN [11692] Coordinator - Step(2)2025-08-28 13:36:47.431 WARN [11692] Coordinator - Visit(0).StationName: ChE2025-08-28 13:36:47.431 WARN [11692] Coordinator - Visit(0).SlotID: 02025-08-28 13:36:47.431 WARN [11692] Coordinator - Visit(0).ProcessRecipe: /ChE/test_100s;12025-08-28 13:36:47.432 WARN [11692] Coordinator - Visit(1).StationName: ChF2025-08-28 13:36:47.432 WARN [11692] Coordinator - Visit(1).SlotID: 02025-08-28 13:36:47.432 WARN [11692] Coordinator - Visit(1).ProcessRecipe: /ChF/test_100s;1 2025-08-28 13:36:47.434 WARN [11692] Coordinator - Step(3)
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).StationName: ChA
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).SlotID: 0
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).ProcessRecipe:
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Step(4)
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).StationName: Ch1
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).SlotID: 0
2025-08-28 13:36:47.434 WARN [11692] Coordinator - Visit(0).ProcessRecipe: /Ch1/test100s;1
2025-08-28 13:36:47.438 WARN [11692] Coordinator - Step(5)
2025-08-28 13:36:47.438 WARN [11692] Coordinator - Visit(0).StationName: Ch6
2025-08-28 13:36:47.438 WARN [11692] Coordinator - Visit(0).SlotID: 0
2025-08-28 13:36:47.438 WARN [11692] Coordinator - Visit(0).ProcessRecipe: /Ch6/test100s;1
2025-08-28 13:36:47.439 WARN [11692] Coordinator - Visit(1).StationName: Ch4
2025-08-28 13:36:47.439 WARN [11692] Coordinator - Visit(1).SlotID: 0
2025-08-28 13:36:47.439 WARN [11692] Coordinator - Visit(1).ProcessRecipe: /Ch4/test100s;1
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Step(6)
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Visit(0).StationName: ChB
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Visit(0).SlotID: 0
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Visit(0).ProcessRecipe: /ChB/cool;1
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Step(7)
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Visit(0).StationName: LB
2025-08-28 13:36:47.440 WARN [11692] Coordinator - Visit(0).SlotID: 1
2025-08-28 13:36:47.441 WARN [11692] Coordinator - Visit(0).ProcessRecipe:
2025-08-28 13:36:47.441 WARN [11692] Coordinator - Visit(1).StationName: LA
2025-08-28 13:36:47.441 WARN [11692] Coordinator - Visit(1).SlotID: 1
2025-08-28 13:36:47.441 WARN [11692] Coordinator - Visit(1).ProcessRecipe: 在写入程序需要为:ArrayList routes = new ArrayList();
for (int i = 1; i <= 1; ++i)
{
Visit fromCassA = new Visit("LP1", i, "", "", "", "");
RouteStep step1 = new RouteStep();
step1.AddVisit(fromCassA);
Visit inLLB = new Visit("LB", 2, "", "", "", "");
Visit inLLA = new Visit("LA", 2, "", "", "", "");
RouteStep step2 = new RouteStep();
step2.AddVisit(inLLB);
step2.AddVisit(inLLA);
Visit todegas1 = new Visit("ChD", 0, "", "", "/ChD/test;1", "");
Visit todegas2 = new Visit("ChC", 0, "", "", "/ChC/test;1", "");
RouteStep step3 = new RouteStep();
step3.AddVisit(todegas1);
step3.AddVisit(todegas2);
Visit toche = new Visit("ChE", 0, "", "", "/ChE/test_100s;1", "");
Visit tochf = new Visit("ChF", 0, "", "", "/ChF/test_100s;1", "");
RouteStep step4 = new RouteStep();
step4.AddVisit(toche);
step4.AddVisit(tochf);
Visit tobypass1 = new Visit("ChA", 0, "", "", "", "");
RouteStep step5 = new RouteStep();
step5.AddVisit(tobypass1);Visit toch1 = new Visit("Ch1", 0, "", "", "/Ch1/test100s;1", "");
RouteStep step6 = new RouteStep();
step6.AddVisit(toch1);
Visit toch6 = new Visit("Ch6", 0, "", "", "/Ch6/test100s;1", "");
Visit toch4 = new Visit("Ch4", 0, "", "", "/Ch4/test100s;1", "");
RouteStep step7 = new RouteStep();
step7.AddVisit(toch6);
step7.AddVisit(toch4);
Visit tocu1 = new Visit("ChB", 0, "", "", "/ChB/cool;1", "");
RouteStep step8 = new RouteStep();
step8.AddVisit(tocu1);
Visit tobypass11 = new Visit("LB", 1, "", "", "", "");
Visit tobypass21 = new Visit("LA", 1, "", "", "", "");
RouteStep step9 = new RouteStep();
step9.AddVisit(tobypass11);
step9.AddVisit(tobypass21);
Visit toCassA = new Visit("LP1", i, "", "", "", "");
RouteStep step10 = new RouteStep();
step10.AddVisit(toCassA);
Route route = new Route("route");
route.AddStep(step1);
route.AddStep(step2);
route.AddStep(step3);
route.AddStep(step4);
route.AddStep(step5);
route.AddStep(step6);
route.AddStep(step7);
route.AddStep(step8);
route.AddStep(step9);
route.AddStep(step10);
routes.Add(route);
}。请你对上面的HandleToolStopped函数进行完善,添加读取路径的功能,能够通过日志中给出的路径,自动生成路径代码,而不是手动编写路径代码。