Пример #1
0
  /**
   * 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);
    }
  }
Пример #2
0
  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);
  }
Пример #3
0
  /**
   * 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);
    }
  }
Пример #4
0
  /**
   * 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;
  }
Пример #5
0
 /**
  * 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);
   }
 }
Пример #6
0
  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;
 }
Пример #9
0
  /**
   * 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;
  }
Пример #10
0
  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;
  }
Пример #11
0
    /**
     * 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;
    }
Пример #12
0
 /**
  * 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);
 }
Пример #13
0
 /**
  * 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);
 }