{boost 1.54}
所有asio操作都发生在同一个io_service上,它从几个std :: threads调用run()(因此是一个线程池)
struct Async : std::enable_shared_from_this<Async>
{
boost::signals2::signal<void()> m_sig;
void read()
{
auto self = shared_from_this();
boost::asio::async_read_until(
/*socket*/,
/*bufferToCollectData*/,
/*delimiter*/,
[self]{self->onRead(..);}
);
}
void onRead(..)
{
m_sig();
}
};
struct Process : std::enable_shared_from_this<Process>
{
std::shared_ptr<Async> m_shrPtrAsync;
boost::signals2::connection m_connection;
void start()
{
m_shrPtrAsync = std::make_shared<Async>();
//m_shrPtrAsync->startUpThings();
auto self = shared_from_this();
m_connection = m_shrPtrAsync->m_sig.connect(
[self]{self->slot();}
);
}
void stop()
{
//this will not delete the slot and have to wait indefinitely until some operation happens on m_sig.
//------------------------------- <2>
m_connection.disconnect();
//this should force the original slot deletion.
m_connection = m_shrPtrAsync->m_sig.connect([this]{dummy();});
m_connection.disconnect();
}
void dummy() {}
void slot()
{
auto self = shared_from_this(); //-------------------- <1>
//to not block the calling thread (Async's m_sig())
m_strand.post(
[self]{self->slotPrivateImpl();}
);
}
void slotPrivateImpl() { /*Processing*/ }
};
//This is from the main thread outside the thread-pool
{//local scope begins
auto shrPtrProcess = std::make_shared<Process>();
shrPtrProcess->start();
//after sometime
shrPtrProcess->stop();
}//local scope ends. I want shrPtrProcess to delete the contained pointer here
//which should in turn delete the Async's pointer in shrPtrProcess->m_shrPtrAsync
这样安全吗?当主线程执行shrPtrProcess->stop();
从而从Async的m_sig
删除插槽然后从本地范围出来时,对shared_ptr到Process
的最后一个剩余引用将会死亡,从而销毁它,但是到那时其他线程触发m_sig
可能已经输入Process::slot(
)并且即将执行标记为&lt; 1&gt;的行。以上。 signal2是否保证在完全执行插槽之前不会删除插槽?
如果这不安全,那么我如何实现shrPtrProcess
破坏Process
ptr的这种行为,一旦本地范围结束,它会在Async
中销毁shrPtrAsync
原始ptr ?如果我没有在标记为&lt; 2&gt;的地方进行黑客攻击。如果m_sig()不再触发,我将永远无法释放资源,因为signals2::connection::disconnect()
不会导致立即删除插槽。