/// <summary> Multicast a message request to all members in <code>dests</code> and receive responses via the RspCollector /// interface. When done receiving the required number of responses, the caller has to call done(req_id) on the /// underlyinh RequestCorrelator, so that the resources allocated to that request can be freed. /// /// </summary> /// <param name="dests"> The list of members from which to receive responses. Null means all members /// </param> /// <param name="req_id">The ID of the request. Used by the underlying RequestCorrelator to correlate responses with /// requests /// </param> /// <param name="msg"> The request to be sent /// </param> /// <param name="coll"> The sender needs to provide this interface to collect responses. Call will return immediately if /// this is null /// </param> public virtual void castMessage(ArrayList dests, long req_id, Message msg, RspCollector coll) { ArrayList real_dests; if (msg == null) { NCacheLog.Error("MsgDispatcher.castMessage()", "request is null"); return; } if (coll == null) { NCacheLog.Error("MessageDispatcher.castMessage()", "response collector is null (must be non-null)"); return; } // we need to clone because we don't want to modify the original // (we remove ourselves if LOCAL is false, see below) ! real_dests = dests != null?(ArrayList)dests.Clone():(ArrayList)channel.View.Members.Clone(); // if local delivery is off, then we should not wait for the message from the local member. // therefore remove it from the membership if (channel != null && channel.getOpt(Channel.LOCAL).Equals(false)) { real_dests.Remove(channel.LocalAddress); } // don't even send the message if the destination list is empty if (real_dests.Count == 0) { NCacheLog.Debug("MsgDispatcher.castMessage()", "destination list is empty, won't send message"); return; } corr.sendRequest(req_id, real_dests, msg, coll); }
public RequestEntry(RspCollector coll) { this.coll = coll; }
public virtual void sendNHopRequest(long id, System.Collections.ArrayList dest_mbrs, Message msg, RspCollector coll) { sendRequest(id, dest_mbrs, msg, coll, HDR.NHOP_REQ); }
/// <summary> Send a request to a group. If no response collector is given, no /// responses are expected (making the call asynchronous). /// /// </summary> /// <param name="id">The request ID. Must be unique for this JVM (e.g. current /// time in millisecs) /// </param> /// <param name="dest_mbrs">The list of members who should receive the call. Usually a group RPC /// is sent via multicast, but a receiver drops the request if its own address /// is not in this list. Will not be used if it is null. /// </param> /// <param name="msg">The request to be sent. The body of the message carries /// the request data /// /// </param> /// <param name="coll">A response collector (usually the object that invokes /// this method). Its methods <code>ReceiveResponse</code> and /// <code>Suspect</code> will be invoked when a message has been received /// or a member is suspected, respectively. /// </param> public virtual void sendRequest(long id, System.Collections.ArrayList dest_mbrs, Message msg, RspCollector coll, byte hdrType) { HDR hdr = null; if (transport == null) { NCacheLog.Warn("RequestCorrelator.sendRequest()", "transport is not available !"); return ; } // i. Create the request correlator header and add it to the // msg // ii. If a reply is expected (sync call / 'coll != null'), add a // coresponding entry in the pending requests table // iii. If deadlock detection is enabled, set/update the call stack // iv. Pass the msg down to the protocol layer below hdr = msg.getHeader(HeaderType.REQUEST_COORELATOR) as RequestCorrelator.HDR; if (hdr == null) { hdr = new HDR(); hdr.type = hdrType; hdr.id = id; hdr.rsp_expected = coll != null ? true : false; hdr.dest_mbrs = dest_mbrs; } if (coll != null) { if (deadlock_detection) { if (local_addr == null) { NCacheLog.Error("RequestCorrelator.sendRequest()", "local address is null !"); return ; } System.Collections.ArrayList new_call_stack = (call_stack != null?(System.Collections.ArrayList) call_stack.Clone():new System.Collections.ArrayList()); new_call_stack.Add(local_addr); hdr.call_stack = new_call_stack; } addEntry(hdr.id, new RequestEntry(coll), dest_mbrs); } msg.putHeader(HeaderType.REQUEST_COORELATOR, hdr); try { if (transport is Protocol) { Event evt = new Event(); evt.Type = Event.MSG; evt.Arg = msg; ((Protocol)transport).passDown(evt); } else if (transport is Transport) ((Transport)transport).send(msg); else NCacheLog.Error("RequestCorrelator.sendRequest()", "transport object has to be either a " + "Transport or a Protocol, however it is a " + transport.GetType()); } catch (System.Exception e) { NCacheLog.Error("RequestCorrelator.sendRequest()",e.ToString()); } }
/// <summary> Helper method for {@link #sendRequest(long,List,Message,RspCollector)}.</summary> public virtual void sendRequest(long id, Message msg, RspCollector coll) { sendRequest(id, null, msg, coll); }
/// <summary> Multicast a message request to all members in <code>dests</code> and receive responses via the RspCollector /// interface. When done receiving the required number of responses, the caller has to call done(req_id) on the /// underlyinh RequestCorrelator, so that the resources allocated to that request can be freed. /// /// </summary> /// <param name="dests"> The list of members from which to receive responses. Null means all members /// </param> /// <param name="req_id">The ID of the request. Used by the underlying RequestCorrelator to correlate responses with /// requests /// </param> /// <param name="msg"> The request to be sent /// </param> /// <param name="coll"> The sender needs to provide this interface to collect responses. Call will return immediately if /// this is null /// </param> public virtual void castMessage(ArrayList dests, long req_id, Message msg, RspCollector coll) { ArrayList real_dests; if (msg == null) { NCacheLog.Error("MsgDispatcher.castMessage()", "request is null"); return ; } if (coll == null) { NCacheLog.Error("MessageDispatcher.castMessage()", "response collector is null (must be non-null)"); return ; } // we need to clone because we don't want to modify the original // (we remove ourselves if LOCAL is false, see below) ! real_dests = dests != null?(ArrayList) dests.Clone():(ArrayList) channel.View.Members.Clone(); // if local delivery is off, then we should not wait for the message from the local member. // therefore remove it from the membership if (channel != null && channel.getOpt(Channel.LOCAL).Equals(false)) { real_dests.Remove(channel.LocalAddress); } // don't even send the message if the destination list is empty if (real_dests.Count == 0) { NCacheLog.Debug("MsgDispatcher.castMessage()", "destination list is empty, won't send message"); return ; } corr.sendRequest(req_id, real_dests, msg, coll); }