public void DivideProblemMessageSerializationTest() { byte[] byteArray = Encoding.UTF8.GetBytes("Test Byte Array"); var divideProblemMessageMessage = new DivideProblemMessage("Problem Type", 123L, byteArray, 321L); var result = divideProblemMessageMessage.SerializeToXml(); Assert.IsNotNull(result); Assert.AreNotEqual(0, result.Length); var xmlValidator = new XmlValidator(); var xsdSchemaFile = "DivideProblemMessage.xsd"; var xsdSchemaPath = Path.Combine(_xsdSchemasPath, xsdSchemaFile); var validationResult = xmlValidator.Validate(result, xsdSchemaPath, true); var errorsCount = validationResult.Errors.Count + validationResult.Warnings.Count; Assert.AreEqual(0, errorsCount); #region ExampleResult //<?xml version="1.0" encoding="utf-16"?> //<DivideProblem xmlns="http://www.mini.pw.edu.pl/ucc/"> // <ProblemType>Problem Type</ProblemType> // <Id>123</Id> // <Data>VGVzdCBCeXRlIEFycmF5</Data> // <ComputationalNodes>321</ComputationalNodes> //</DivideProblem> #endregion }
public void Parse_DivideProblemMessage_XMLString() { string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, @"xml_samples\DivideProblem.xml"); string problemType = "TSP"; ulong problemId = 12; byte[] data = { 1, 2, 4, 6, 5, 4, 32, 3 }; ulong nodesCount = 16; ulong nodeId = 8; DivideProblemMessage message = new DivideProblemMessage( problemType, problemId, data, nodesCount, nodeId); string actualXmlStr = message.ToXmlString(); XmlDocument xmlDoc = new XmlDocument(); xmlDoc.Load(path); string expectedXmlStr = xmlDoc.OuterXml; Assert.AreEqual(expectedXmlStr, actualXmlStr); }
public void Parse_XMLString_DivideProblemMessage() { /*********** Actual message ***********/ string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, @"xml_samples\DivideProblem.xml"); XmlDocument xmlDoc = new XmlDocument(); xmlDoc.Load(path); string xmlStr = xmlDoc.OuterXml; string name = Message.GetMessageName(xmlStr); DivideProblemMessage actualMessage = null; if (name == DivideProblemMessage.ELEMENT_NAME) { actualMessage = DivideProblemMessage.Construct(xmlStr); } /*********** Expected message ***********/ string problemType = "TSP"; ulong problemId = 12; byte[] data = { 1, 2, 4, 6, 5, 4, 32, 3 }; ulong nodesCount = 16; ulong nodeId = 8; DivideProblemMessage expectedMessage = new DivideProblemMessage( problemType, problemId, data, nodesCount, nodeId); Assert.AreEqual(expectedMessage, actualMessage); }
/// <summary> /// Handler for DivideProblemMessage. /// </summary> /// <param name="message">A DivideProblemMessage.</param> /// <exception cref="System.InvalidOperationException"> /// Thrown when: /// - message is designated for TaskManger with different ID, /// - problem type can't be divided with this TaskManager, /// - dividing the problem cannot be started bacause no threads are available in thread pool. /// </exception> private void DivideProblemMessageHandler(DivideProblemMessage message) { if (Id != message.TaskManagerId) { // shouldn't ever get here - received message for other TaskManager throw new InvalidOperationException( string.Format("TaskManager with ID={0} received message for TaskManager with ID={1}.", Id, message.TaskManagerId)); } Type taskSolverType; if (!TaskSolvers.TryGetValue(message.ProblemType, out taskSolverType)) { // shouldn't ever get here - received unsolvable problem throw new InvalidOperationException( string.Format("\"{0}\" problem type can't be divided with this TaskManager.", message.ProblemType)); } var actionDescription = string.Format("Dividing problem \"{0}\"(problem instance id={1})", message.ProblemType, message.ProblemInstanceId); // should be started properly cause server sends at most as many tasks to do as count of component's threads in idle state var started = StartActionInNewThread(() => { var taskSolver = (TaskSolver)Activator.CreateInstance(taskSolverType, message.ProblemData); taskSolver.ThrowIfError(); var partialProblemsData = taskSolver.DivideProblem((int)message.ComputationalNodes); taskSolver.ThrowIfError(); var partialProblems = new List <PartialProblemsMessage.PartialProblem>(partialProblemsData.GetLength(0)); for (var i = 0; i < partialProblemsData.GetLength(0); i++) { partialProblems.Add(new PartialProblemsMessage.PartialProblem { PartialProblemId = (ulong)i, Data = partialProblemsData[i], TaskManagerId = Id }); } var partialProblemsMessage = new PartialProblemsMessage { ProblemType = message.ProblemType, ProblemInstanceId = message.ProblemInstanceId, CommonData = message.ProblemData, PartialProblems = partialProblems }; EnqueueMessageToSend(partialProblemsMessage); }, actionDescription, message.ProblemType, message.ProblemInstanceId, null); if (!started) { throw new InvalidOperationException( "Couldn't divide problem because couldn't start new thread."); } }
private void ProcessDivideProblem() { DivideProblemMessage processedMessage = null; lock (divideProblemMessageQueue) { if (divideProblemMessageQueue.Count > 0) { processedMessage = divideProblemMessageQueue.Dequeue(); } } if (processedMessage == null) { return; } _logger.Debug("Processing divideMessage. " + processedMessage.Id); TaskSolverDVRP taskSolver = CreateTaskSolver(processedMessage.ProblemType, processedMessage.Data); var dividedProblem = taskSolver.DivideProblem((int)processedMessage.ComputationalNodes); _logger.Debug("Finished dividing problem"); var solutionsMessage = new PartialProblemsMessage() { CommonData = processedMessage.Data, Id = processedMessage.Id, ProblemType = processedMessage.ProblemType, SolvingTimeout = (ulong)Timeout.TotalMilliseconds, SolvingTimeoutSpecified = true, PartialProblems = new SolvePartialProblemsPartialProblem[(int)processedMessage.ComputationalNodes] }; solutionsMessage.PartialProblems = new SolvePartialProblemsPartialProblem[dividedProblem.Length]; for (int i = 0; i < dividedProblem.Length; i++) { solutionsMessage.PartialProblems[i] = new SolvePartialProblemsPartialProblem() { Data = dividedProblem[i], TaskId = (ulong)i }; } var socket = communicationModule.SetupClient(); communicationModule.Connect(socket); var message = SerializeMessage(solutionsMessage); communicationModule.SendData(message, socket); communicationModule.CloseSocket(socket); }
/// <summary> /// Constructs message by given xml string /// </summary> /// <param name="xmlString"> /// xml in string /// </param> /// <returns> /// Message constructed by the xml /// </returns> public static Message Construct(string xmlString) { xmlString = concCompabilityIssuesStringWojtekIsGay(xmlString); if (GetMessageName(xmlString) == RegisterMessage.ELEMENT_NAME) { return(RegisterMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == DivideProblemMessage.ELEMENT_NAME) { return(DivideProblemMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == NoOperationMessage.ELEMENT_NAME) { return(NoOperationMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == RegisterResponseMessage.ELEMENT_NAME) { return(RegisterResponseMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == SolutionRequestMessage.ELEMENT_NAME) { return(SolutionRequestMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == SolutionsMessage.ELEMENT_NAME) { return(SolutionsMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == SolvePartialProblemsMessage.ELEMENT_NAME) { try { //return SolvePartialProblemsMessage.Construct(xmlString); } catch (InvalidOperationException e) { return(null); } Console.WriteLine("******** SOLVE PARTIAL PROBLEM MESSAGE **************"); return(SolvePartialProblemsMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == SolveRequestMessage.ELEMENT_NAME) { return(SolveRequestMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == SolveRequestResponseMessage.ELEMENT_NAME) { return(SolveRequestResponseMessage.Construct(xmlString)); } if (GetMessageName(xmlString) == StatusMessage.ELEMENT_NAME) { return(StatusMessage.Construct(xmlString)); } return(null); }
/// <summary> /// Create divide problem message that can be send to a task manager. /// </summary> /// <returns>Divide problem message.</returns> public override Message CreateMessage() { var message = new DivideProblemMessage { ComputationalNodes = Problem.NumberOfParts.Value, ProblemData = Problem.Data, ProblemInstanceId = Problem.Id, ProblemType = Problem.Type, TaskManagerId = AssigneeId }; return(message); }
/// <summary> /// In this function divideProblem message is sent if there is a new task and node is has proper taskSolver. /// It returns true in case of completition of sending the message. /// </summary> /// <param name="numOfTask"></param> /// <param name="node"></param> /// <param name="messagePackage"></param> /// <returns></returns> private bool isMessageProblemDividedSent(int numOfTask, NetworkNode node, MessagePackage messagePackage) { if (taskTracker.Tasks[numOfTask].Status == Cluster.TaskStatus.New && taskTracker.Tasks[numOfTask].Type == node.SolvableProblems[0]) { DivideProblemMessage divideProblemMessage = new DivideProblemMessage(taskTracker.Tasks[numOfTask].Type, (ulong)taskTracker.Tasks[numOfTask].ID, taskTracker.Tasks[numOfTask].BaseData, (ulong)4, (ulong)node.Id); taskTracker.Tasks[numOfTask].Status = Cluster.TaskStatus.Dividing; server.Send(messagePackage.Socket, divideProblemMessage); SmartConsole.PrintLine("Divide problem message has been sent", SmartConsole.DebugLevel.Advanced); return(true); } return(false); }
public void DivideProblemMessageSerialization() { string testData = System.IO.File.ReadAllText(@"XMLTestData\DivideProblemMessage.xml"); var serializer = new ComputationSerializer <DivideProblemMessage>(); var divideProblemMessage = new DivideProblemMessage() { ProblemType = "TSP", Id = 1, Data = new byte[] { 0, 0, 25 }, ComputationalNodes = 5 }; var result = serializer.Serialize(divideProblemMessage); Assert.AreEqual(result, testData); }
public static DivideProblemMessage CreateDivideProblemMessage() { string problemType = "TSP"; ulong problemId = 12; byte[] data = { 1, 2, 4, 6, 5, 4, 32, 3 }; ulong nodesCount = 16; ulong nodeId = 8; DivideProblemMessage expectedMessage = new DivideProblemMessage( problemType, problemId, data, nodesCount, nodeId); return(expectedMessage); }
public void DivideProblemMessageXmlIsProperlySerializedAndDeserialized() { var message = new DivideProblemMessage { ComputationalNodes = 5, TaskManagerId = 10, ProblemData = new byte[] { 1, 2, 3, 4, 5 }, ProblemInstanceId = 15, ProblemType = "Dvrp" }; var serializedMessage = _serializer.Serialize(message); var deserializedMessage = _serializer.Deserialize(serializedMessage); Assert.IsInstanceOfType(deserializedMessage, typeof(DivideProblemMessage)); }
protected override void ProcessDivideProblemMessage(DivideProblemMessage message) { if (SolvableProblems.FirstOrDefault(x => x == message.ProblemType) == null) { EventLogger.GetLog().ErrorFormat("Nie obsługiwany problem: {0}", message.ProblemType); return; } TaskSolver taskSolver = null; switch (message.ProblemType) { case ("MultiplyProblem"): taskSolver = new MultiplyTaskSolver(message.Data); break; case ("DVRP"): taskSolver = new DllProject.DvrpTaskSolver(message.Data); break; } var problemSolvingHelper = new ProblemSolvingHelper() { ProblemId = message.Id, ProblemType = message.ProblemType, TaskSolver = taskSolver, }; _problems.Add(message.Id, problemSolvingHelper); taskSolver.ProblemDividingFinished += taskSolver_ProblemDividingFinished; taskSolver.SolutionsMergingFinished += taskSolver_SolutionsMergingFinished; var thread = new IOThread { ProblemType = message.ProblemType, State = EState.Busy, RealThread = new Thread(() => DivideProblem(message, taskSolver)), ProblemInstanceId = message.Id }; _runningThreads.Add(thread); thread.RealThread.Start(); }
private void handleDivideProblemMessage(DivideProblemMessage message) { for (int i = 0; i < systemTracker.Node.ParallelThreads; i++) { if (systemTracker.Node.TaskThreads[i].StatusThread.State == StatusThreadState.Idle) { DVRPSolver dvrpSolver = new DVRPSolver(message.Data); systemTracker.Node.TaskThreads[i].StatusThread.State = StatusThreadState.Busy; systemTracker.Node.TaskThreads[i].CurrentTask = new Cluster.Task((int)message.Id, message.ProblemType, message.Data) { Status = Cluster.TaskStatus.Dividing }; systemTracker.Node.TaskThreads[i].TaskSolver = dvrpSolver; systemTracker.Node.TaskThreads[i].Thread = new Thread(new ThreadStart(systemTracker.Node.TaskThreads[i].Start)); systemTracker.Node.TaskThreads[i].Thread.Start(); break; } } ///WE SHOULD CHECK HERE WHETHER THERE WAS IDLE THREAD AVALIABLE !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! // start computations }
private void DivideProblem(DivideProblemMessage msg, TaskSolver taskSolver) { var partialProblemsData = taskSolver.DivideProblem((int)msg.ComputationalNodes); var messagesList = new List <SolvePartialProblemsMessage>(); for (int i = partialProblemsData.Length - 1; i >= 0; i -= PartialProblemsPackageSize) { var packageSize = i + 1 < PartialProblemsPackageSize ? i + 1 : PartialProblemsPackageSize; var partialProblemsPackage = new byte[packageSize][]; for (int j = 0; j < packageSize; j++) { partialProblemsPackage[j] = partialProblemsData[i - j]; } var partialProblemsObjects = new List <PartialProblem>(); foreach (var partialData in partialProblemsPackage) { partialProblemsObjects.Add(new PartialProblem() { Data = partialData, TaskId = ++_maxTaskId }); } _problems[msg.Id].PartialProblems.AddRange(partialProblemsObjects); //TODO: NA PEWNO NIE MILIJON TAJMAŁTUW var partialProblemsMsg = new SolvePartialProblemsMessage(msg.ProblemType, msg.Id, new byte[0], 100000000, partialProblemsObjects); messagesList.Add(partialProblemsMsg); } foreach (var partialProblemsMessage in messagesList) { var serialized = partialProblemsMessage.Serialize(); SendMessage(serialized); } var thread = GetThreadByProblemInstanceId(msg.Id); thread.State = EState.Idle; }
/// <summary> /// Dequeues first solveReqest of given type and returns appropiate DivideProblemMessage for SolveRequest /// </summary> /// <param name="type"></param> /// <returns></returns> private DivideProblemMessage GetDivideProblemMessageForType(List <string> solvingTypes) { DivideProblemMessage divideProblemMessage = null; ulong solveRequestId = 0; SolveRequestMessage solveRequest = new SolveRequestMessage(); lock (solveRequests) { solveRequestId = solveRequests.FirstOrDefault(x => solvingTypes.Contains(x.Value.ProblemType)).Key; solveRequests.TryRemove(solveRequestId, out solveRequest); } if (solveRequest != null) { int activeNodeCount = 0; lock (activeNodes) { foreach (var activeNode in this.activeNodes) { if (activeNode.Value.Type == RegisterType.ComputationalNode) { activeNodeCount++; } } } divideProblemMessage = new DivideProblemMessage() { ComputationalNodes = (ulong)activeNodeCount, Data = solveRequest.Data, ProblemType = solveRequest.ProblemType, Id = solveRequestId }; } return(divideProblemMessage); }
private void ProcessSolveRequestMessage(SolveRequestMessage msg, TcpClient client) { var data = msg.Data; var problemType = msg.ProblemType; var timeout = msg.SolvingTimeout; var taskManagerInfo = GetTaskManagerByProblemType(problemType); if (taskManagerInfo == null) { EventLogger.GetLog().ErrorFormat("Brak task managera dla problemu {0}", msg.ProblemType); return; } var problemInstance = new ProblemInstanceInfo(++_maxProblemId, msg.ProblemType) { Data = data, TaskManager = taskManagerInfo, ComputationalClient = GetComponentsInfoByTcpClient(client), SolvingTimeout = timeout, ProblemType = msg.ProblemType }; _problemInstances.Add(problemInstance); //Wyslij odpowiedz var responseMsg = new SolveRequestResponseMessage(problemInstance.Id); SendMessage(responseMsg.Serialize(), client); EventLogger.GetLog().InfoFormat("Otrzymano żądanie rozwiązania problemu {0} o id {1}", problemInstance.ProblemType, problemInstance.Id); //Wyslij prosbe o podzielenie var availableComputationalNodes = _computationalNodes.Count(c => c.SolvableProblems.Contains(problemInstance.ProblemType)); var divideProblemMsg = new DivideProblemMessage(problemInstance.ProblemType, problemInstance.Id, problemInstance.Data, (ulong)availableComputationalNodes); SendMessage(divideProblemMsg.Serialize(), taskManagerInfo.Client); EventLogger.GetLog().InfoFormat("Wysłano żądanie podzielenia problemu {0} o id {1} do TM {2}", problemInstance.ProblemType, problemInstance.Id, taskManagerInfo.Id); }
static void Main(string[] args) { EventLogger.AddAppender(new Log4NetAppender()); var ipAddress = "127.0.0.1"; var port = 8123; IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse(ipAddress), port); Console.WriteLine("Choose component: \n" + "1 ComputationalClient\n" + "2 TaskManager\n" + "3 ComputationalNode\n"); Console.WriteLine("Select: "); int componentType; int.TryParse(Console.ReadLine(), out componentType); Component component = new ComputationalClient(); switch (componentType) { case 1: component = new ComputationalClient(); break; case 2: component = new TaskManager(); break; case 3: component = new ComputationalNode(); break; } component.SolvableProblems = new List <string>() { "MultiplyProblem", "DVRP" }; component.Register(endPoint); var filePath = @"DvrpData\okulD.vrp"; var problem = new DvrpProblem(new DvrpProblemData(filePath)); //var problem = new MultiplyProblem(10, 3, 1000000); while (true) { Common.Abstractions.Message msg = null; int result; Console.WriteLine("RegisterMessage was sent\n" + "Choose another message: \n" + "1 RegisterMessage\n" + "2 RegisterResponseMessage\n" + "3 StatusMessage\n" + "4 SolveRequestMessage\n" + "5 SolveRequestResponseMessage\n" + "6 DivideProblemMessage\n" + "7 SolutionRequestMessage\n" + "8 PartialProblemsMessage\n" + "9 Solutions message\n" + "10 Exit" ); Console.WriteLine("Choose message to send: "); if (int.TryParse(Console.ReadLine(), out result) == false || result < 1 || result > 10) { Console.WriteLine("\nWrong input\n\n"); continue; } switch (result) { case 1: msg = new RegisterMessage(component.Type, 0, component.SolvableProblems); break; case 2: msg = new RegisterResponseMessage(123L, DateTime.Now); break; case 3: msg = new StatusMessage(123L, null); break; case 4: msg = new SolveRequestMessage(problem.ProblemType, problem.SolvingTimeout, problem.Data); break; case 5: msg = new SolveRequestResponseMessage(123L); break; case 6: msg = new DivideProblemMessage("Problem type", 123L, Encoding.UTF8.GetBytes("test1"), 321L); break; case 7: msg = new SolutionRequestMessage(123L); break; case 8: msg = new SolvePartialProblemsMessage("problem type", 123L, Encoding.UTF8.GetBytes("test1"), 333L, null); break; case 9: msg = new SolutionsMessage("problemy type", 123L, Encoding.UTF8.GetBytes("test1"), null); break; case 10: Environment.Exit(0); break; } component.SendMessage(msg.Serialize()); } //component.SendMessage(Encoding.UTF8.GetBytes("dupa")); }
protected virtual void ProcessDivideProblemMessage(DivideProblemMessage message) { }
protected void ProcessMessage(byte[] msg) { var encoder = new UTF8Encoding(); string messagesString = encoder.GetString(msg); _messageParser.ParseMessage(messagesString); var messagesToProcess = _messageParser.GetMessagesToProcess(); foreach (var xmlMessage in messagesToProcess) { Type type = Message.GetMessageType(xmlMessage); switch (type.Name) { case ("RegisterResponseMessage"): { var regMsg = Message.Deserialize <RegisterResponseMessage>(xmlMessage); ProcessRegisterResponseMessage(regMsg); break; } case ("SolveRequestMessage"): { throw new NotImplementedException(); break; } case ("DivideProblemMessage"): { DivideProblemMessage divMsg = Message.Deserialize <DivideProblemMessage>(xmlMessage); ProcessDivideProblemMessage(divMsg); break; } case ("SolveRequestResponseMessage"): { var solveRequestResponseMsg = Message.Deserialize <SolveRequestResponseMessage>(xmlMessage); ProcessSolveRequestResponseMessage(solveRequestResponseMsg); break; } case ("SolutionRequestMessage"): { throw new NotImplementedException(); break; } case ("SolutionsMessage"): { var solutionsMsg = Message.Deserialize <SolutionsMessage>(xmlMessage); ProcessSolutionsMessage(solutionsMsg); break; } case ("SolvePartialProblemsMessage"): { SolvePartialProblemsMessage _msg = Message.Deserialize <SolvePartialProblemsMessage>(xmlMessage); ProcessSolvePartialProblemsMessage(_msg); break; } } } }