Esempio n. 1
0
ACE_Data_Block *
ACE_Data_Block::clone_nocopy (ACE_Message_Block::Message_Flags mask,
                              size_t max_size) const
{
  ACE_FUNCTION_TIMEPROBE(ACE_DATA_BLOCK_CLONE_ENTER);

  ACE_TRACE ("ACE_Data_Block::clone_nocopy");

  // You always want to clear this one to prevent memory leaks but you
  // might add some others later.
  const ACE_Message_Block::Message_Flags always_clear =
    ACE_Message_Block::DONT_DELETE;

  const size_t newsize =
    max_size == 0 ? this->max_size_ : max_size;

  ACE_Data_Block *nb = 0;

  ACE_NEW_MALLOC_RETURN (nb,
                         static_cast<ACE_Data_Block*> (
                           this->data_block_allocator_->malloc (sizeof (ACE_Data_Block))),
                         ACE_Data_Block (newsize, // size
                                         this->type_,     // type
                                         0,               // data
                                         this->allocator_strategy_, // allocator
                                         this->locking_strategy_, // locking strategy
                                         this->flags_,  // flags
                                         this->data_block_allocator_),
                         0);

  // Message block initialization may fail while the construction
  // succeds.  Since as a matter of policy, ACE may throw no
  // exceptions, we have to do a separate check like this.
  if (nb != 0 && nb->size () < newsize)
    {
      nb->ACE_Data_Block::~ACE_Data_Block();  // placement destructor ...
      this->data_block_allocator_->free (nb); // free ...
      errno = ENOMEM;
      return 0;
    }


  // Set new flags minus the mask...
  nb->clr_flags (mask | always_clear);
  return nb;
}
Esempio n. 2
0
TAO_Queued_Data *
TAO_Queued_Data::duplicate (TAO_Queued_Data &sqd)
{
  // Check to see if the underlying block is on the stack. If not it
  // is fine. If the datablock is on stack, try to make a copy of that
  // before doing a duplicate.
  // @@ todo: Theoretically this should be within the Message Block,
  // but we dont have much scope to do this in that mess. Probably in
  // the next stage of MB rewrite we should be okay
  ACE_Message_Block::Message_Flags fl =
    sqd.msg_block_->self_flags ();

  if (ACE_BIT_ENABLED (fl,
                       ACE_Message_Block::DONT_DELETE))
    (void) TAO_Queued_Data::replace_data_block (*sqd.msg_block_);


  TAO_Queued_Data *qd = 0;

  if (sqd.allocator_)
    {
      ACE_NEW_MALLOC_RETURN (qd,
                             static_cast<TAO_Queued_Data *> (
                               sqd.allocator_->malloc (sizeof (TAO_Queued_Data))),
                             TAO_Queued_Data (sqd),
                             0);

      return qd;
    }

  // No allocator, so use the global pool!
  // @@ TODO: We should be removing this at some point of time!
  if (TAO_debug_level == 4)
    {
      // This debug is for testing purposes!
      TAOLIB_DEBUG ((LM_DEBUG,
                  "TAO (%P|%t) - Queued_Data[%d]::duplicate\n",
                  "Using global pool for allocation\n"));
    }

  ACE_NEW_RETURN (qd,
                  TAO_Queued_Data (sqd),
                  0);

  return qd;
}
Esempio n. 3
0
// Note: The FooDataWriter gives ownership of the marshalled data
//       to the WriteDataContainer.
ACE_Message_Block*
 FooDataWriterImpl::marshal(
                const Foo& instance_data,
                int  for_write)
{
  ACE_Message_Block* mb;
  if (for_write)
  {
    ACE_NEW_MALLOC_RETURN (mb,
                           static_cast<ACE_Message_Block*> (
                             mb_allocator_->malloc (
                             sizeof (ACE_Message_Block))),
                           ACE_Message_Block( sizeof (Foo),
                                              ACE_Message_Block::MB_DATA,
                                              0, //cont
                                              0, //data
                                              foo_allocator_, //allocator_strategy
                                              0, //locking_strategy
                                              ACE_DEFAULT_MESSAGE_BLOCK_PRIORITY,
                                              ACE_Time_Value::zero,
                                              ACE_Time_Value::max_time,
                                              db_allocator_,
                                              mb_allocator_),
                            0);
    mb->copy ((const char *)&instance_data, sizeof (Foo));
  }
  else
  { // Don't use the cached allocator for the registered sample message
    // block.
    Foo* register_sample = new Foo();
    *register_sample = instance_data;

    ACE_NEW_RETURN (mb,
                    ACE_Message_Block ((const char*)register_sample,
                                        sizeof (Foo)),
                    0);
    // Let the PublicationInstance destructor release the Message Block
    // and delete this register_sample.
    mb->clr_flags(ACE_Message_Block::DONT_DELETE);
  }

  return mb;
}
Esempio n. 4
0
template <class T, class C> int
ACE_Unbounded_Set_Ex<T, C>::insert_tail (const T &item)
{
  // ACE_TRACE ("ACE_Unbounded_Set_Ex<T, C>::insert_tail");
  NODE *temp = 0;

  // Insert <item> into the old dummy node location.
  this->head_->item_ = item;

  // Create a new dummy node.
  ACE_NEW_MALLOC_RETURN (temp,
                         static_cast<NODE*> (this->allocator_->malloc (sizeof (NODE))),
                         NODE (this->head_->next_),
                         -1);
  // Link this pointer into the list.
  this->head_->next_ = temp;

  // Point the head to the new dummy node.
  this->head_ = temp;

  ++this->cur_size_;
  return 0;
}
Esempio n. 5
0
int
DDS_TEST::run(int num_messages, int msg_size)
{
  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "Build the DataSampleElementList\n"));

  this->num_messages_delivered_ = 0;
  this->num_messages_sent_      = num_messages;

  // Set up the SendStateDataSampleList
  OpenDDS::DCPS::SendStateDataSampleList samples;

  samples.size_ = num_messages;

  // Now we can create the DataSampleHeader struct and set its fields.
  OpenDDS::DCPS::DataSampleHeader header;

  // The +1 makes the null terminator ('\0') get placed into the block.
  header.message_id_ = 1;
  header.publication_id_ = this->pub_id_;

  OpenDDS::DCPS::DataSampleElement* prev_element = 0;

  OpenDDS::DCPS::DataSampleElementAllocator allocator(num_messages);
  Cleanup cleanup(allocator, samples);
  OpenDDS::DCPS::TransportSendElementAllocator trans_allocator(num_messages, sizeof (OpenDDS::DCPS::TransportSendElement));

  std::string data = "Hello World!";

  if (msg_size) {
    data.clear();
    for (int j = 1; j <= msg_size; ++j) {
      data += char(1 + (j % 255));
    }
  }

  for (int i = 1; i <= num_messages; ++i) {
    // This is what goes in the "Data Block".
    std::ostringstream ostr;
    ostr << data << " [" << i << "]";

    std::string data_str = msg_size ? data : ostr.str();

    ssize_t num_data_bytes = data_str.length() + 1;

    header.message_length_ = static_cast<ACE_UINT32>(num_data_bytes);
    header.sequence_ = i;

    // The DataSampleHeader is what goes in the "Header Block".
    ACE_Message_Block* header_block =
      new ACE_Message_Block(header.max_marshaled_size());
    *header_block << header;

    ACE_Message_Block* data_block = new ACE_Message_Block(num_data_bytes);
    data_block->copy(data_str.c_str());

    // Chain the "Data Block" to the "Header Block"
    header_block->cont(data_block);

    // Create the DataSampleElement now.
    OpenDDS::DCPS::DataSampleElement* element;

    ACE_NEW_MALLOC_RETURN(element,
      static_cast<OpenDDS::DCPS::DataSampleElement*>(allocator.malloc(sizeof (OpenDDS::DCPS::DataSampleElement))),
      OpenDDS::DCPS::DataSampleElement(this->pub_id_, this, 0, &trans_allocator, 0), 1);

    // The Sample Element will hold on to the chain of blocks (header + data).
    element->sample_ = header_block;
    if (prev_element == 0) {
      samples.head_ = element;
    } else {
      prev_element->set_next_send_sample(element);
    }

    prev_element = element;
    samples.tail_ = element;
  }

  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "Send the SendStateDataSampleList (samples).\n"));

  ACE_Time_Value start = ACE_OS::gettimeofday();
  this->send(samples);
  ACE_Time_Value finished = ACE_OS::gettimeofday();

  ACE_Time_Value total = finished - start;
  ACE_DEBUG((LM_INFO,
    "(%P|%t) Publisher total time required was %d.%d seconds.\n",
             total.sec(),
             total.usec() % 1000000));

  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "The Publisher has finished sending the samples.\n"));

  if (msg_size) {
    ACE_OS::sleep(15);
  }

  return 0;
}
Esempio n. 6
0
int
ACE_Message_Block::init_i (size_t size,
                           ACE_Message_Type msg_type,
                           ACE_Message_Block *msg_cont,
                           const char *msg_data,
                           ACE_Allocator *allocator_strategy,
                           ACE_Lock *locking_strategy,
                           Message_Flags flags,
                           unsigned long priority,
                           const ACE_Time_Value &execution_time,
                           const ACE_Time_Value &deadline_time,
                           ACE_Data_Block *db,
                           ACE_Allocator *data_block_allocator,
                           ACE_Allocator *message_block_allocator)
{
  ACE_TRACE ("ACE_Message_Block::init_i");
  ACE_FUNCTION_TIMEPROBE (ACE_MESSAGE_BLOCK_INIT_I_ENTER);

  this->rd_ptr_ = 0;
  this->wr_ptr_ = 0;
  this->priority_ = priority;
#if defined (ACE_HAS_TIMED_MESSAGE_BLOCKS)
  this->execution_time_ = execution_time;
  this->deadline_time_ = deadline_time;
#else
  ACE_UNUSED_ARG (execution_time);
  ACE_UNUSED_ARG (deadline_time);
#endif /* ACE_HAS_TIMED_MESSAGE_BLOCKS */
  this->cont_ = msg_cont;
  this->next_ = 0;
  this->prev_ = 0;

  this->message_block_allocator_ = message_block_allocator;

  if (this->data_block_ != 0)
    {
      this->data_block_->release ();
      this->data_block_ = 0;
    }

  if (db == 0)
    {
      if (data_block_allocator == 0)
        ACE_ALLOCATOR_RETURN (data_block_allocator,
                              ACE_Allocator::instance (),
                              -1);

      ACE_TIMEPROBE (ACE_MESSAGE_BLOCK_INIT_I_DB_ALLOC);

      // Allocate the <ACE_Data_Block> portion, which is reference
      // counted.
      ACE_NEW_MALLOC_RETURN (db,
                             static_cast<ACE_Data_Block *> (
                               data_block_allocator->malloc (sizeof (ACE_Data_Block))),
                             ACE_Data_Block (size,
                                             msg_type,
                                             msg_data,
                                             allocator_strategy,
                                             locking_strategy,
                                             flags,
                                             data_block_allocator),
                             -1);
      ACE_TIMEPROBE (ACE_MESSAGE_BLOCK_INIT_I_DB_CTOR);

      // Message block initialization may fail, while the construction
      // succeds.  Since ACE may throw no exceptions, we have to do a
      // separate check and clean up, like this:
      if (db != 0 && db->size () < size)
        {
          db->ACE_Data_Block::~ACE_Data_Block();  // placement destructor ...
          data_block_allocator->free (db); // free ...
          errno = ENOMEM;
          return -1;
        }
    }

  // Reset the data_block_ pointer.
  this->data_block (db);

  return 0;
}
Esempio n. 7
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;
}
Esempio n. 8
0
template <class EXT_ID, class INT_ID, class COMPARE_KEYS, class ACE_LOCK> int
ACE_RB_Tree<EXT_ID, INT_ID, COMPARE_KEYS, ACE_LOCK>::insert_i (const EXT_ID &k,
        const INT_ID &t,
        ACE_RB_Tree_Node<EXT_ID, INT_ID> *&entry)
{
    ACE_TRACE ("ACE_RB_Tree<EXT_ID, INT_ID, COMPARE_KEYS, ACE_LOCK>::insert_i");

    // Find the closest matching node, if there is one.
    RB_SearchResult result = LEFT;
    ACE_RB_Tree_Node<EXT_ID, INT_ID> *current = find_node (k, result);
    if (current)
    {
        // If the keys match, just return a pointer to the node's item.
        if (result == EXACT)
        {
            entry = current;
            return 1;
        }
        // Otherwise if we're to the left of the insertion
        // point, insert into the right subtree.
        else if (result == LEFT)
        {
            if (current->right ())
            {
                // If there is already a right subtree, complain.
                ACE_ERROR_RETURN ((LM_ERROR,
                                   ACE_TEXT ("%p\n"),
                                   ACE_TEXT ("\nright subtree already present in ")
                                   ACE_TEXT ("ACE_RB_Tree<EXT_ID, INT_ID>::insert_i\n")),
                                  -1);
            }
            else
            {
                // The right subtree is empty: insert new node there.
                ACE_RB_Tree_Node<EXT_ID, INT_ID> *tmp = 0;
                ACE_NEW_MALLOC_RETURN
                (tmp,
                 (reinterpret_cast<ACE_RB_Tree_Node<EXT_ID, INT_ID>*>
                  (this->allocator_->malloc (sizeof (*tmp)))),
                 (ACE_RB_Tree_Node<EXT_ID, INT_ID>) (k, t),
                 -1);
                current->right (tmp);

                // If the node was successfully inserted, set its parent, rebalance
                // the tree, color the root black, and return a pointer to the
                // inserted item.
                entry = current->right ();
                current->right ()->parent (current);
                RB_rebalance (current->right ());
                this->root_->color (ACE_RB_Tree_Node_Base::BLACK);
                ++this->current_size_;
                return 0;
            }
        }
        // Otherwise, we're to the right of the insertion point, so
        // insert into the left subtree.
        else // (result == RIGHT)
        {
            if (current->left ())
                // If there is already a left subtree, complain.
                ACE_ERROR_RETURN ((LM_ERROR,
                                   ACE_TEXT ("%p\n"),
                                   ACE_TEXT ("\nleft subtree already present in ")
                                   ACE_TEXT ("ACE_RB_Tree<EXT_ID, INT_ID>::insert_i\n")),
                                  -1);
            else
            {
                // The left subtree is empty: insert new node there.
                ACE_RB_Tree_Node<EXT_ID, INT_ID> *tmp = 0;
                ACE_NEW_MALLOC_RETURN
                (tmp,
                 (reinterpret_cast<ACE_RB_Tree_Node<EXT_ID, INT_ID>*>
                  (this->allocator_->malloc (sizeof (*tmp)))),
                 (ACE_RB_Tree_Node<EXT_ID, INT_ID>) (k, t),
                 -1);
                current->left (tmp);
                // If the node was successfully inserted, set its
                // parent, rebalance the tree, color the root black, and
                // return a pointer to the inserted item.
                entry = current->left ();
                current->left ()->parent (current);
                RB_rebalance (current->left ());
                this->root_->color (ACE_RB_Tree_Node_Base::BLACK);
                ++this->current_size_;
                return 0;
            }
        }
    }
    else
    {
        // The tree is empty: insert at the root and color the root black.
        ACE_NEW_MALLOC_RETURN
        (this->root_,
         (reinterpret_cast<ACE_RB_Tree_Node<EXT_ID, INT_ID>*>
          (this->allocator_->malloc (sizeof (ACE_RB_Tree_Node<EXT_ID, INT_ID>)))),
         (ACE_RB_Tree_Node<EXT_ID, INT_ID>) (k, t),
         -1);
        this->root_->color (ACE_RB_Tree_Node_Base::BLACK);
        ++this->current_size_;
        entry = this->root_;
        return 0;
    }
}
Esempio n. 9
0
int
SimpleDataWriter::run(SimplePublisher* publisher, unsigned num_messages)
{
  this->num_messages_delivered_ = 0;
  this->num_messages_sent_      = num_messages;

  // Set up the DataSampleList
  TAO::DCPS::DataSampleList samples;

  samples.head_ = 0;
  samples.tail_ = 0;
  samples.size_ = num_messages;

  // This is what goes in the "Data Block".
  std::string data = "Hello World!";

  // Now we can create the DataSampleHeader struct and set its fields.
  TAO::DCPS::DataSampleHeader header;
  header.message_id_ = 1;
  header.publication_id_ = this->pub_id_;

  TAO::DCPS::DataSampleListElement* prev_element = 0;

  TAO::DCPS::DataSampleListElementAllocator allocator(num_messages);
  TAO::DCPS::TransportSendElementAllocator trans_allocator(num_messages, sizeof (TAO::DCPS::TransportSendElement));

  for (unsigned i = 1; i <= num_messages; ++i)
    {
      // This is what goes in the "Data Block".
      std::ostringstream ostr;
      ostr << data << " [" << i << "]";

      std::string data_str = ostr.str();

      ssize_t num_data_bytes = data_str.length() + 1;

      header.message_length_ = num_data_bytes;
      header.sequence_ = i;

      // The DataSampleHeader is what goes in the "Header Block".
      ACE_Message_Block* header_block =
                          new ACE_Message_Block(header.max_marshaled_size());
      header_block << header;

      ACE_Message_Block* data_block = new ACE_Message_Block(num_data_bytes);
      data_block->copy(data_str.c_str());

      // Chain the "Data Block" to the "Header Block"
      header_block->cont(data_block);

      // Create the DataSampleListElement now.
      TAO::DCPS::DataSampleListElement* element;

      ACE_NEW_MALLOC_RETURN(element,
              static_cast<TAO::DCPS::DataSampleListElement*> (allocator.malloc(sizeof (TAO::DCPS::DataSampleListElement))),
              TAO::DCPS::DataSampleListElement(this->pub_id_, this, 0, &trans_allocator),
              1);

      // The Sample Element will hold the chain of blocks (header + data).
      element->sample_ = header_block;

      if (prev_element == 0)
        {
          samples.head_ = element;
        }
      else
        {
          prev_element->next_send_sample_ = element;
        }

      prev_element = element;
      samples.tail_ = element;
    }

  publisher->send_samples(samples);

  return 0;
}
Esempio n. 10
0
int
SimpleDataWriter::run(SimplePublisher* publisher)
{
  DBG_ENTRY("SimpleDataWriter","run");

  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "Build the DataSampleElementList to contain one element - "
             "our 'Hello World' string.\n"));

  // We just send one message.

  // This is what goes in the "Data Block".
  ACE_TString data = "Hello World!";

  // Now we can create the DataSampleHeader struct and set its fields.
  TAO::DCPS::DataSampleHeader header;

  // The +1 makes the null terminator ('/0') get placed into the block.
  header.message_length_ = data.length() + 1;
  header.message_id_ = 1;
  header.sequence_ = 0;
  // TMB - Compiler no longer likes the next line...  source_timestamp_ is gone.
  //header.source_timestamp_ = ACE_OS::gettimeofday().msec();
  header.publication_id_ = this->pub_id_;

  // The DataSampleHeader is what goes in the "Header Block".
  ACE_Message_Block* header_block = new ACE_Message_Block
                                                (header.max_marshaled_size());
  header_block << header;

  // The +1 makes the null terminator ('/0') get placed into the block.
  ACE_Message_Block* data_block = new ACE_Message_Block(data.length() + 1);
  data_block->copy(data.c_str());

  // Chain the "Data Block" to the "Header Block"
  header_block->cont(data_block);

  // Create the DataSampleListElement now.
  TAO::DCPS::DataSampleListElementAllocator allocator(3);
  TAO::DCPS::TransportSendElementAllocator trans_allocator(3, sizeof (TAO::DCPS::TransportSendElement));
  TAO::DCPS::DataSampleListElement* element;

  ACE_NEW_MALLOC_RETURN(element,
           static_cast<TAO::DCPS::DataSampleListElement*> (allocator.malloc(sizeof (TAO::DCPS::DataSampleListElement))),
           TAO::DCPS::DataSampleListElement(this->pub_id_, this, 0, &trans_allocator),
           1);

  // The Sample Element will hold on to the chain of blocks (header + data).
  element->sample_ = header_block;

  // Set up the DataSampleList
  TAO::DCPS::DataSampleList samples;

  samples.head_ = element;
  samples.tail_ = element;
  samples.size_ = 1;

  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "Ask the publisher to send the DataSampleList (samples).\n"));

  publisher->send_samples(samples);

  VDBG((LM_DEBUG, "(%P|%t) DBG:   "
             "The Publisher has finished sending the samples.\n"));

  return 0;
}