Пример #1
0
ACE_Message_Block *
ACE_Message_Block::clone (Message_Flags mask) const
{
  ACE_TRACE ("ACE_Message_Block::clone");

  // Get a pointer to a "cloned" <ACE_Data_Block> (will copy the
  // values rather than increment the reference count).
  ACE_Data_Block *db = this->data_block ()->clone (mask);

  if (db == 0)
    return 0;

  ACE_Message_Block *nb = 0;

  if (message_block_allocator_ == 0)
    {
      ACE_NEW_RETURN (nb,
                      ACE_Message_Block (0, // size
                                         ACE_Message_Type (0), // type
                                         0, // cont
                                         0, // data
                                         0, // allocator
                                         0, // locking strategy
                                         0, // flags
                                         this->priority_, // priority
                                         ACE_EXECUTION_TIME, // execution time
                                         ACE_DEADLINE_TIME, // absolute time to deadline
                                         // Get a pointer to a
                                         // "duplicated" <ACE_Data_Block>
                                         // (will simply increment the
                                         // reference count).
                                         db,
                                         db->data_block_allocator (),
                                         this->message_block_allocator_),
                      0);
    }
  else
    {
      // This is the ACE_NEW_MALLOC macro with the return check removed.
      // We need to do it this way because if it fails we need to release
      // the cloned data block that was created above.  If we used
      // ACE_NEW_MALLOC_RETURN, there would be a memory leak because the
      // above db pointer would be left dangling.
      nb = static_cast<ACE_Message_Block*> (message_block_allocator_->malloc (sizeof (ACE_Message_Block)));
      if (nb != 0)
        new (nb) ACE_Message_Block (0, // size
                                    ACE_Message_Type (0), // type
                                    0, // cont
                                    0, // data
                                    0, // allocator
                                    0, // locking strategy
                                    0, // flags
                                    this->priority_, // priority
                                    ACE_EXECUTION_TIME, // execution time
                                    ACE_DEADLINE_TIME, // absolute time to deadline
                                    db,
                                    db->data_block_allocator (),
                                    this->message_block_allocator_);
    }

  if (nb == 0)
    {
      db->release ();
      return 0;
    }

  // Set the read and write pointers in the new <Message_Block> to the
  // same relative offset as in the existing <Message_Block>.
  nb->rd_ptr (this->rd_ptr_);
  nb->wr_ptr (this->wr_ptr_);

  // Clone all the continuation messages if necessary.
  if (this->cont () != 0
      && (nb->cont_ = this->cont ()->clone (mask)) == 0)
    {
      nb->release ();
      return 0;
    }
  return nb;
}
Пример #2
0
ACE_Message_Block *
ACE_Message_Block::clone (Message_Flags mask) const
{
  ACE_TRACE ("ACE_Message_Block::clone");

  const ACE_Message_Block *old_message_block = this;
  ACE_Message_Block *new_message_block = 0;
  ACE_Message_Block *new_previous_message_block = 0;
  ACE_Message_Block *new_root_message_block = 0;

  do
    {
      // Get a pointer to a "cloned"<ACE_Data_Block> (will copy the
      // values rather than increment the reference count).
      ACE_Data_Block *db = old_message_block->data_block ()->clone (mask);

      if (db == 0)
        return 0;

      if(old_message_block->message_block_allocator_ == 0)
        {
          ACE_NEW_RETURN (new_message_block,
                          ACE_Message_Block (0, // size
                                             ACE_Message_Type (0), // type
                                             0, // cont
                                             0, // data
                                             0, // allocator
                                             0, // locking strategy
                                             0, // flags
                                             old_message_block->priority_, // priority
                                             ACE_EXECUTION_TIME, // execution time
                                             ACE_DEADLINE_TIME, // absolute time to deadline
                                             // Get a pointer to a
                                             // "duplicated"<ACE_Data_Block>
                                             // (will simply increment the
                                             // reference count).
                                             db,
                                             db->data_block_allocator (),
                                             old_message_block->message_block_allocator_),
                          0);
        }
      else
        {
          // This is the ACE_NEW_MALLOC macro with the return check removed.
          // We need to do it this way because if it fails we need to release
          // the cloned data block that was created above. If we used
          // ACE_NEW_MALLOC_RETURN, there would be a memory leak because the
          // above db pointer would be left dangling.
          new_message_block = static_cast<ACE_Message_Block*> (old_message_block->message_block_allocator_->malloc (sizeof (ACE_Message_Block)));
          if (new_message_block != 0)
            new (new_message_block) ACE_Message_Block (0, // size
                                                       ACE_Message_Type (0), // type
                                                       0, // cont
                                                       0, // data
                                                       0, // allocator
                                                       0, // locking strategy
                                                       0, // flags
                                                       old_message_block->priority_, // priority
                                                       ACE_EXECUTION_TIME, // execution time
                                                       ACE_DEADLINE_TIME, // absolute time to deadline
                                                       db,
                                                       db->data_block_allocator (),
                                                       old_message_block->message_block_allocator_);
        }

      if (new_message_block == 0)
        {
          db->release ();
          return 0;
        }

      // Set the read and write pointers in the new <Message_Block> to the
      // same relative offset as in the existing <Message_Block>.
      new_message_block->rd_ptr (old_message_block->rd_ptr_);
      new_message_block->wr_ptr (old_message_block->wr_ptr_);
      // save the root message block to return
      if (new_root_message_block == 0)
        new_root_message_block = new_message_block;
      if (new_previous_message_block != 0)
        // we're a continuation of the previous block, add ourself to its chain
        new_previous_message_block->cont_ = new_message_block;
      new_previous_message_block = new_message_block;
      old_message_block = old_message_block->cont ();
    }
  while (old_message_block != 0);

  return new_root_message_block;
}
Пример #3
0
ACE_Message_Block *
ACE_Message_Block::duplicate (void) const
{
  ACE_TRACE ("ACE_Message_Block::duplicate");

  ACE_Message_Block *nb = 0;

  // Create a new <ACE_Message_Block> that contains unique copies of
  // the message block fields, but a reference counted duplicate of
  // the <ACE_Data_Block>.

  // If there is no allocator, use the standard new and delete calls.
  if (this->message_block_allocator_ == 0)
    ACE_NEW_RETURN (nb,
                    ACE_Message_Block (0, // size
                                       ACE_Message_Type (0), // type
                                       0, // cont
                                       0, // data
                                       0, // allocator
                                       0, // locking strategy
                                       0, // flags
                                       this->priority_, // priority
                                       ACE_EXECUTION_TIME,
                                       ACE_DEADLINE_TIME,
                                       // Get a pointer to a
                                       // "duplicated" <ACE_Data_Block>
                                       // (will simply increment the
                                       // reference count).
                                       this->data_block ()->duplicate  (),
                                       this->data_block ()->data_block_allocator (),
                                       this->message_block_allocator_),
                  0);
  else // Otherwise, use the message_block_allocator passed in.
    ACE_NEW_MALLOC_RETURN (nb,
                           static_cast<ACE_Message_Block*> (
                             message_block_allocator_->malloc (sizeof (ACE_Message_Block))),
                           ACE_Message_Block (0, // size
                                              ACE_Message_Type (0), // type
                                              0, // cont
                                              0, // data
                                              0, // allocator
                                              0, // locking strategy
                                              0, // flags
                                              this->priority_, // priority
                                              ACE_EXECUTION_TIME,
                                              ACE_DEADLINE_TIME,
                                              // Get a pointer to a
                                              // "duplicated" <ACE_Data_Block>
                                              // (will simply increment the
                                              // reference count).
                                              this->data_block ()->duplicate  (),
                                              this->data_block ()->data_block_allocator (),
                                              this->message_block_allocator_),
                           0);

  // Set the read and write pointers in the new <Message_Block> to the
  // same relative offset as in the existing <Message_Block>.  Note
  // that we are assuming that the data_block()->base() pointer
  // doesn't change when it's duplicated.
  nb->rd_ptr (this->rd_ptr_);
  nb->wr_ptr (this->wr_ptr_);

  // Increment the reference counts of all the continuation messages.
  if (this->cont_)
    {
      nb->cont_ = this->cont_->duplicate ();

      // If things go wrong, release all of our resources and return
      // 0.
      if (nb->cont_ == 0)
        {
          nb->release ();
          nb = 0;
        }
    }

  return nb;
}
Пример #4
0
ACE_Message_Block *
ACE_Message_Block::duplicate (void) const
{
  ACE_TRACE ("ACE_Message_Block::duplicate");

  ACE_Message_Block *nb_top = 0;
  ACE_Message_Block *nb = 0;

  const ACE_Message_Block *current = this;

  // Increment the reference counts of all the continuation messages.
  while (current)
    {
      ACE_Message_Block* cur_dup = 0;

      // Create a new <ACE_Message_Block> that contains unique copies of
      // the message block fields, but a reference counted duplicate of
      // the <ACE_Data_Block>.

      // If there is no allocator, use the standard new and delete calls.
      if (current->message_block_allocator_ == 0)
        ACE_NEW_NORETURN (cur_dup,
                          ACE_Message_Block (0, // size
                                             ACE_Message_Type (0), // type
                                             0, // cont
                                             0, // data
                                             0, // allocator
                                             0, // locking strategy
                                             0, // flags
                                             current->priority_, // priority
                                             ACE_EXECUTION_TIME,
                                             ACE_DEADLINE_TIME,
                                             // Get a pointer to a
                                             // "duplicated" <ACE_Data_Block>
                                             // (will simply increment the
                                             // reference count).
                                             current->data_block ()->duplicate  (),
                                             current->data_block ()->data_block_allocator (),
                                             current->message_block_allocator_));
      else // Otherwise, use the message_block_allocator passed in.
        ACE_NEW_MALLOC_NORETURN (cur_dup,
                                 static_cast<ACE_Message_Block*> (
                                      current->message_block_allocator_->malloc (sizeof (ACE_Message_Block))),
                                 ACE_Message_Block (0, // size
                                                    ACE_Message_Type (0), // type
                                                    0, // cont
                                                    0, // data
                                                    0, // allocator
                                                    0, // locking strategy
                                                    0, // flags
                                                    current->priority_, // priority
                                                    ACE_EXECUTION_TIME,
                                                    ACE_DEADLINE_TIME,
                                                    // Get a pointer to a
                                                    // "duplicated" <ACE_Data_Block>
                                                    // (will simply increment the
                                                    // reference count).
                                                    current->data_block ()->duplicate  (),
                                                    current->data_block ()->data_block_allocator (),
                                                    current->message_block_allocator_));


      // If allocation failed above, release everything done so far and return NULL
      if (cur_dup == 0)
        {
          if (nb_top != 0)
            {
              nb_top->release ();
            }
          return 0;
        }

      // Set the read and write pointers in the new <Message_Block> to the
      // same relative offset as in the existing <Message_Block>.  Note
      // that we are assuming that the data_block()->base() pointer
      // doesn't change when it's duplicated.
      cur_dup->rd_ptr (current->rd_ptr_);
      cur_dup->wr_ptr (current->wr_ptr_);

      if (!nb)
        {
          /* First in the list: set leading pointers */
          nb_top = nb = cur_dup;
        }
      else
        {
          /* Continuing on: append to nb and walk down the list */
          nb->cont_ = cur_dup;
          nb = nb->cont_;
        }

      current = current->cont_;
    }

  return nb_top;
}