private void transmitComposition(BinaryWriter bw) { Dictionary <string, string> properties; foreach (CompositionModelData cmData in TaskAssign.CompositionData.Models) { string mainLibrary = WorkspaceManager.GetCompositionModelMainLibrary(cmData.CompositionModel); properties = new Dictionary <string, string>(); properties["modelId"] = cmData.CompositionModel.guid; properties["linkableComponent"] = cmData.Model.className; properties["assemblyPath"] = mainLibrary; properties["workingDirectory"] = WorkspaceManager.GetCompositionModelDirectory(cmData.CompositionModel); PipeUtil.WriteCommand(bw, new PipeCommand("AddModel", properties)); properties = new Dictionary <string, string>(); properties["modelId"] = cmData.CompositionModel.guid; if (cmData.PropertyValues != null) { Dictionary <string, string> propertyValues = cmData.PropertyValues.Kvs; foreach (ModelProperty property in cmData.ModelProperties) { switch (property.type) { case 4: properties[property.key] = WorkspaceManager.GetLocalPath(propertyValues[property.key]); break; case 5: properties[property.key] = WorkspaceManager.HomeDirectory + @"\" + propertyValues[property.key]; break; default: properties[property.key] = propertyValues[property.key]; break; } } } PipeUtil.WriteCommand(bw, new PipeCommand("SetModelProperties", properties)); } foreach (CompositionLinkData link in TaskAssign.CompositionData.Links) { properties = new Dictionary <string, string>(); properties["linkId"] = link.CompositionLink.guid; properties["sourceModelId"] = link.CompositionLink.sourceCmGuid; properties["targetModelId"] = link.CompositionLink.targetCmGuid; properties["sourceQuantity"] = link.CompositionLink.sourceQuantity; properties["targetQuantity"] = link.CompositionLink.targetQuantity; properties["sourceElementSet"] = link.CompositionLink.sourceElementSet; properties["targetElementSet"] = link.CompositionLink.targetElementSet; PipeUtil.WriteCommand(bw, new PipeCommand("AddLink", properties)); } properties = new Dictionary <string, string>(); properties["triggerInvokeTime"] = TaskAssign.TriggerInvokeTime; properties["progressReportInterval"] = progressReportInterval.ToString(); /* TODO: make some attribute for it */ properties["parallelized"] = "false"; PipeUtil.WriteCommand(bw, new PipeCommand("SetSimulationProperties", properties)); }
private bool runnerLifetime() { bool succeed = false; using (BinaryReader br = new BinaryReader(pipeServer)) using (BinaryWriter bw = new BinaryWriter(pipeServer)) { /* handshake */ PipeCommand helloCommand = PipeUtil.ReadCommand(br); if (helloCommand.Command != "Hello") { throw new Exception("Handshake failed."); } logger.Info("Pipe: Handshake signal received."); PipeUtil.WriteCommand(bw, new PipeCommand("Hello")); logger.Info("Pipe: Handshake signal sent."); /* transmit composition */ transmitComposition(bw); PipeUtil.WriteCommand(bw, new PipeCommand("RunSimulation")); /* waiting for simulation finish */ do { PipeCommand command = PipeUtil.ReadCommand(br); logger.Info("Pipe: Received command: " + command.Command); switch (command.Command) { case "Progress": TaskProgressChangedHandler(this, command.Parameters); break; case "Completed": case "Failed": PipeUtil.WriteCommand(bw, new PipeCommand("Halt")); succeed = (command.Command == "Completed"); isReleased = true; break; } } while (!isReleased); } runnerProcess.WaitForExit(); return(succeed); }
public void Run() { DateTime lastReport; logger.Info("TaskRunner is initializing..."); pipeClient = new NamedPipeClientStream(".", PipeName, PipeDirection.InOut, PipeOptions.WriteThrough, TokenImpersonationLevel.Impersonation); pipeClient.Connect(); logger.Info("Pipe connected."); bool isReleased = false; try { using (BinaryReader br = new BinaryReader(pipeClient)) using (BinaryWriter bw = new BinaryWriter(pipeClient)) { /* handshake */ PipeUtil.WriteCommand(bw, new PipeCommand("Hello")); logger.Info("Pipe: Handshake signal sent."); PipeCommand helloCommand = PipeUtil.ReadCommand(br); if (helloCommand.Command != "Hello") { throw new Exception("Handshake failed."); } logger.Info("Pipe: Handshake signal received."); composition = new CompositionManager(); do { string modelId; PipeCommand command = PipeUtil.ReadCommand(br); logger.Info("Pipe: Received command: " + command.Command); switch (command.Command) { case "AddModel": modelId = command.Parameters["modelId"]; string workingDirectory = command.Parameters["workingDirectory"]; string assemblyPath = command.Parameters["assemblyPath"]; string linkableComponent = command.Parameters["linkableComponent"]; Model model = new Model(); model.Create(modelId, workingDirectory, assemblyPath, linkableComponent); composition.AddModel(model); logger.Info("Created model " + modelId + ": " + linkableComponent); break; case "SetModelProperties": modelId = command.Parameters["modelId"]; foreach (KeyValuePair <string, string> entry in command.Parameters) { logger.Info("Model " + modelId + " Property: [Key=" + entry.Key + ", Value=" + entry.Value + "]"); } composition.GetModel(modelId).Init(command.Parameters); break; case "AddLink": string linkId = command.Parameters["linkId"]; string sourceModelId = command.Parameters["sourceModelId"]; string targetModelId = command.Parameters["targetModelId"]; string sourceQuantity = command.Parameters["sourceQuantity"]; string targetQuantity = command.Parameters["targetQuantity"]; string sourceElementSet = command.Parameters["sourceElementSet"]; string targetElementSet = command.Parameters["targetElementSet"]; logger.Info("Link " + linkId + " Property: [sourceModelId=" + sourceModelId + ", targetModelId=" + targetModelId + ", sourceQuantity=" + sourceQuantity + ", targetQuantity=" + targetQuantity + ", sourceElementSet=" + sourceElementSet + ", targetElementSet=" + targetElementSet + "]"); composition.AddLink(linkId, sourceModelId, targetModelId, sourceQuantity, targetQuantity, sourceElementSet, targetElementSet); break; case "SetSimulationProperties": DateTime triggerInvokeTime = DateTime.Parse(command.Parameters["triggerInvokeTime"]); bool parallelized = Boolean.Parse(command.Parameters["parallelized"]); progressReportInterval = Int32.Parse(command.Parameters["progressReportInterval"]); composition.TriggerInvokeTime = triggerInvokeTime; composition.Parallelized = parallelized; break; case "RunSimulation": lastReport = DateTime.Now; modelProgress = new Dictionary <string, string>(); composition.CompositionModelProgressChangedHandler += new CompositionModelProgressChangedDelegate(delegate(object sender, string cmGuid, string progress) { lock (this) { modelProgress[cmGuid] = progress; if ((DateTime.Now - lastReport).TotalSeconds > progressReportInterval) { lastReport = DateTime.Now; PipeUtil.WriteCommand(bw, new PipeCommand("Progress", modelProgress)); } } }); RunSimulation(delegate(object sender, bool succeed) { logger.Info("Simulation finished, succeed=" + succeed); PipeUtil.WriteCommand(bw, new PipeCommand("Progress", modelProgress)); PipeUtil.WriteCommand(bw, new PipeCommand(succeed ? "Completed" : "Failed")); }); break; case "Halt": isReleased = true; return; } } while (true); } } catch (Exception e) { if (!isReleased) { logger.Crit("Exception occured during task lifetime: " + e.ToString()); } } finally { pipeClient.Close(); pipeClient.Dispose(); } }