/** * Takes an object and uses Java serialization to generate the byte[] buffer which is set in the * message. Parameter 'obj' has to be serializable (e.g. implementing Serializable, Externalizable * or Streamable, or be a basic type (e.g. Integer, Short etc)). */ public final void setObject(Object obj) { if (obj == null) return; if (obj instanceof Buffer) { setBuffer((Buffer) obj); return; } try { byte[] tmp = Util.objectToByteBuffer(obj); setBuffer(tmp); } catch (Exception ex) { throw new IllegalArgumentException(ex); } }
public <T> NotifyingFuture<T> callRemoteMethodWithFuture( Address dest, MethodCall call, RequestOptions options) throws Throwable { if (log.isTraceEnabled()) log.trace("dest=" + dest + ", method_call=" + call + ", options=" + options); Object buf = req_marshaller != null ? req_marshaller.objectToBuffer(call) : Util.objectToByteBuffer(call); Message msg = new Message(dest, null, null); if (buf instanceof Buffer) msg.setBuffer((Buffer) buf); else msg.setBuffer((byte[]) buf); msg.setFlag(options.getFlags()); if (options.getScope() > 0) msg.setScope(options.getScope()); return super.sendMessageWithFuture(msg, options); }
/** * Send all fragments as separate messages (with same ID !). Example: * * <pre> * Given the generated ID is 2344, number of fragments=3, message {dst,src,buf} * would be fragmented into: * * [2344,3,0]{dst,src,buf1}, * [2344,3,1]{dst,src,buf2} and * [2344,3,2]{dst,src,buf3} * </pre> */ private void fragment(Message msg) { try { byte[] buffer = msg.getRawBuffer(); List<Range> fragments = Util.computeFragOffsets(msg.getOffset(), msg.getLength(), frag_size); int num_frags = fragments.size(); num_sent_frags.addAndGet(num_frags); if (log.isTraceEnabled()) { Address dest = msg.getDest(); StringBuilder sb = new StringBuilder("fragmenting packet to "); sb.append((dest != null ? dest.toString() : "<all members>")) .append(" (size=") .append(buffer.length); sb.append(") into ") .append(num_frags) .append(" fragment(s) [frag_size=") .append(frag_size) .append(']'); log.trace(sb.toString()); } long frag_id = getNextId(); // used as a seqno for (int i = 0; i < fragments.size(); i++) { Range r = fragments.get(i); // don't copy the buffer, only src, dest and headers. Only copy the headers one time ! Message frag_msg = msg.copy(false, i == 0); frag_msg.setBuffer(buffer, (int) r.low, (int) r.high); FragHeader hdr = new FragHeader(frag_id, i, num_frags); frag_msg.putHeader(this.id, hdr); down_prot.down(new Event(Event.MSG, frag_msg)); } } catch (Exception e) { if (log.isErrorEnabled()) log.error("fragmentation failure", e); } }
/** * Invokes a method in all members contained in dests (or all members if dests is null). * * @param dests A list of addresses. If null, the method will be invoked on all cluster members * @param method_call The method (plus args) to be invoked * @param options A collection of call options, e.g. sync versus async, timeout etc * @return RspList A list of return values and flags (suspected, not received) per member * @since 2.9 */ public RspList callRemoteMethods( Collection<Address> dests, MethodCall method_call, RequestOptions options) { if (dests != null && dests.isEmpty()) { // don't send if dest list is empty if (log.isTraceEnabled()) log.trace( new StringBuilder("destination list of ") .append(method_call.getName()) .append("() is empty: no need to send message")); return RspList.EMPTY_RSP_LIST; } if (log.isTraceEnabled()) log.trace( new StringBuilder("dests=") .append(dests) .append(", method_call=") .append(method_call) .append(", options=") .append(options)); Object buf; try { buf = req_marshaller != null ? req_marshaller.objectToBuffer(method_call) : Util.objectToByteBuffer(method_call); } catch (Exception e) { // if(log.isErrorEnabled()) log.error("exception", e); // we will change this in 3.0 to add the exception to the signature // (see http://jira.jboss.com/jira/browse/JGRP-193). The reason for a RTE is that we cannot // change the // signature in 2.3, otherwise 2.3 would be *not* API compatible to prev releases throw new RuntimeException("failure to marshal argument(s)", e); } Message msg = new Message(); if (buf instanceof Buffer) msg.setBuffer((Buffer) buf); else msg.setBuffer((byte[]) buf); msg.setFlag(options.getFlags()); if (options.getScope() > 0) msg.setScope(options.getScope()); RspList retval = super.castMessage(dests, msg, options); if (log.isTraceEnabled()) log.trace("responses: " + retval); return retval; }
/** * Takes an object and uses Java serialization to generate the byte[] buffer which is set in the * message. */ public final void setObject(Serializable obj) { if (obj == null) return; try { byte[] tmp = Util.objectToByteBuffer(obj); setBuffer(tmp); } catch (Exception ex) { throw new IllegalArgumentException(ex); } }
public Object callRemoteMethod(Address dest, MethodCall call, RequestOptions options) throws Throwable { if (log.isTraceEnabled()) log.trace("dest=" + dest + ", method_call=" + call + ", options=" + options); Object buf = req_marshaller != null ? req_marshaller.objectToBuffer(call) : Util.objectToByteBuffer(call); Message msg = new Message(dest, null, null); if (buf instanceof Buffer) msg.setBuffer((Buffer) buf); else msg.setBuffer((byte[]) buf); msg.setFlag(options.getFlags()); if (options.getScope() > 0) msg.setScope(options.getScope()); Object retval = super.sendMessage(msg, options); if (log.isTraceEnabled()) log.trace("retval: " + retval); if (retval instanceof Throwable) throw (Throwable) retval; return retval; }
protected static Message constructMessage( Buffer buf, Address recipient, ResponseMode mode, boolean rsvp, DeliverOrder deliverOrder) { Message msg = new Message(); msg.setBuffer(buf); encodeDeliverMode(msg, deliverOrder); // some issues with the new bundler. put back the DONT_BUNDLE flag. if (deliverOrder == DeliverOrder.NONE || mode != ResponseMode.GET_NONE) msg.setFlag(Message.Flag.DONT_BUNDLE); if (rsvp) msg.setFlag(Message.Flag.RSVP); if (recipient != null) msg.setDest(recipient); return msg; }
private static Message constructMessage( Buffer buf, Address recipient, boolean oob, ResponseMode mode, boolean rsvp) { Message msg = new Message(); msg.setBuffer(buf); if (oob) msg.setFlag(Message.OOB); if (oob || mode != ResponseMode.GET_NONE) { msg.setFlag(Message.DONT_BUNDLE); // This is removed since this optimisation is no longer valid. See ISPN-1878 // msg.setFlag(Message.NO_FC); } if (rsvp) msg.setFlag(Message.RSVP); if (recipient != null) msg.setDest(recipient); return msg; }
/** * Create a copy of the message. If offset and length are used (to refer to another buffer), the * copy will contain only the subset offset and length point to, copying the subset into the new * copy. * * @param copy_buffer * @param copy_headers Copy the headers * @return Message with specified data */ public Message copy(boolean copy_buffer, boolean copy_headers) { Message retval = new Message(false); retval.dest_addr = dest_addr; retval.src_addr = src_addr; retval.flags = flags; if (copy_buffer && buf != null) { // change bela Feb 26 2004: we don't resolve the reference retval.setBuffer(buf, offset, length); } retval.headers = copy_headers ? createHeaders(headers) : createHeaders(3); return retval; }
private Message _decrypt(final Cipher cipher, Message msg, boolean decrypt_entire_msg) throws Exception { byte[] decrypted_msg; if (cipher == null) decrypted_msg = code(msg.getRawBuffer(), msg.getOffset(), msg.getLength(), true); else decrypted_msg = cipher.doFinal(msg.getRawBuffer(), msg.getOffset(), msg.getLength()); if (!decrypt_entire_msg) { msg.setBuffer(decrypted_msg); return msg; } Message ret = Util.streamableFromBuffer(Message.class, decrypted_msg, 0, decrypted_msg.length); if (ret.getDest() == null) ret.setDest(msg.getDest()); if (ret.getSrc() == null) ret.setSrc(msg.getSrc()); return ret; }
/** * Assembles all the fragments into one buffer. Takes all Messages, and combines their buffers * into one buffer. This method does not check if the fragmentation is complete (use {@link * #isComplete()} to verify before calling this method) * * @return the complete message in one buffer */ private Message assembleMessage() { Message retval; byte[] combined_buffer, tmp; int combined_length = 0, length, offset; int index = 0; for (Message fragment : fragments) combined_length += fragment.getLength(); combined_buffer = new byte[combined_length]; retval = fragments[0].copy(false); // doesn't copy the payload, but copies the headers for (int i = 0; i < fragments.length; i++) { Message fragment = fragments[i]; fragments[i] = null; // help garbage collection a bit tmp = fragment.getRawBuffer(); length = fragment.getLength(); offset = fragment.getOffset(); System.arraycopy(tmp, offset, combined_buffer, index, length); index += length; } retval.setBuffer(combined_buffer); return retval; }
/** * Constructs a message. The index and length parameters allow to provide a <em>reference</em> to * a byte buffer, rather than a copy, and refer to a subset of the buffer. This is important when * we want to avoid copying. When the message is serialized, only the subset is serialized.<br> * <em> Note that the byte[] buffer passed as argument must not be modified. Reason: if we * retransmit the message, it would still have a ref to the original byte[] buffer passed in as * argument, and so we would retransmit a changed byte[] buffer ! </em> * * @param dest Address of receiver. If it is <em>null</em> then the message sent to the group. * Otherwise, it contains a single destination and is sent to that member. * <p> * @param src Address of sender * @param buf A reference to a byte buffer * @param offset The index into the byte buffer * @param length The number of bytes to be used from <tt>buf</tt>. Both index and length are * checked for array index violations and an ArrayIndexOutOfBoundsException will be thrown if * invalid */ public Message(Address dest, Address src, byte[] buf, int offset, int length) { this(dest); setSrc(src); setBuffer(buf, offset, length); }
/** * Constructs a Message given a destination Address, a source Address and the payload byte buffer * * @param dest Address of receiver. If it is <em>null</em> then the message sent to the group. * Otherwise, it contains a single destination and is sent to that member. * <p> * @param src Address of sender * @param buf Message to be sent. Note that this buffer must not be modified (e.g. buf[0]=0 is not * allowed), since we don't copy the contents on clopy() or clone(). */ public Message(Address dest, Address src, byte[] buf) { this(dest); setSrc(src); setBuffer(buf); }