12

I want to remove all handlers from an IO_service right before I reuse it. Is this possible?

I'm writing unit tests that involve an asio::io_service. In between each test case I want to clear the handlers from the global io_service. I thought that io_service::reset would to that but it doesn't. reset() only allows the io_service to be resumed. All of the handlers from the last test case are still queued up.

I only need to do this for unit testing so any crazy hack would work.


More info:

The io_service is from a deadline_timer member variable. The deadline_timer is part of the code I'm testing so I can't change how it's constructed. I get a hold of its io_service via the deadline_timer's get_io_service method.

deft_code
  • 57,255
  • 29
  • 141
  • 224

1 Answers1

4

Well, I racked my brain on this for a few days and came up with a workable solution. It's the mother of all hacks.

void clear( boost::asio::io_service& service )
{
    service.stop();
    service.~io_service();
    new( &service ) boost::asio::io_service;
}

I'm not sure how safe this would be for productions code. But so far it seems to work (no segfaults, no weird behavior).

deft_code
  • 57,255
  • 29
  • 141
  • 224
  • You could allocate the io_service dynamically and store it in an std::auto_ptr or boost::scoped_ptr. Then you can reset it when you need to "clear" the handlers. That way you avoid using placement new (in which case you need to explicitly call the destructor - see http://www.parashift.com/c++-faq-lite/dtors.html#faq-11.10). – Yukiko Mar 06 '10 at 11:03
  • @Yukiko: I don't control the code that creates the io_service. Further I don't contol the code that sets the deadline_timer's io_service. In short I don't allocate the io_service so I can't store it in smart_ptr. – deft_code Dec 22 '10 at 19:54
  • I am using boost 1.49. That trick is not working (some assertion failed) – Martin Meeser Mar 14 '13 at 16:18