字体:  

《ACE程序员指南》7.6.2范例的问题

Youth 发表于: 2008-6-21 23:52 来源: ACE 开发者

基本照着书上的代码,ACE 5.6.1+VS2005SP1,碰到的问题是在handle_timeout中putq进去的mb在handle_output中却getq不出来,试着跟踪了一下,putq应该是没问题的,调用之后可以看到msg_queue_里已经有内容,但在getq时,返回的mb没有内容。

相关代码如下:

int Client::handle_timeout(const ACE_Time_Value &, const void *)
{
  if (this->iterations_ >= ITERATIONS)
  {
    this->peer().close_writer();
    return 0;
  }

  ACE_Message_Block *mb;
  char msg[128];
  ACE_OS::sprintf(msg, "Iteration %d\n", this->iterations_);

  ACE_NEW_RETURN(mb, ACE_Message_Block(msg), -1);
  this->msg_queue()->enqueue_tail(mb);// this->putq(mb);
  ++ iterations_;

  return 0;
}

int Client::handle_output(ACE_HANDLE fd /* = ACE_INVALID_HANDLE */)
{
  ACE_Message_Block *mb;
  ACE_Time_Value nowait(ACE_OS::gettimeofday());

  while (-1 != this->getq(mb, &nowait))
  {
    size_t size = mb->length();
    ssize_t send_cnt = this->peer().send(mb->rd_ptr(), mb->length());

    if (send_cnt == -1)
       ACE_ERROR((LM_ERROR, "(%P|%t) %p\n", "send"));
    else
       mb->rd_ptr(ACE_static_cast(size_t, send_cnt));

    if (mb->length() > 0)
    {
       this->ungetq(mb);
       break;
    }

    mb->release();
  }

  if (this->msg_queue()->is_empty())
     this->reactor()->cancel_wakeup(this, ACE_Event_Handler::WRITE_MASK);
  else
    this->reactor()->schedule_wakeup(this, ACE_Event_Handler::WRITE_MASK);

  return 0;
}

最新回复

winston at 2008-6-22 09:53:59

CODE:

  ACE_Message_Block *mb;
  char msg[128];
  ACE_OS::sprintf(msg, "Iteration %d\n", this->iterations_);

  ACE_NEW_RETURN(mb, ACE_Message_Block(msg), -1);
这几行有错,ACE_NEW_RETURN(mb, ACE_Message_Block(msg), -1); 这样用法有问题,msg不能是栈上面的东西,你最好直接把内容复制到mb。
参考ACE_Message_Block的类说明文档。上面有注释。
Youth at 2008-6-22 12:42:32
好的,谢谢了,我昨天看了论坛里另外几个帖子后,也怀疑是这方面的问题,但捣鼓了一会还是没搞定,今天再试试~~
Youth at 2008-6-22 15:09:51
ACE_NEW_RETURN(mb, ACE_Message_Block(32), -1);
ACE_OS::sprintf(mb->wr_ptr(), "Iteration %d\n", this->iterations_);
mb->wr_ptr(12);

this->putq(mb);