質問に適切なタイトルを付けることができなかった場合は申し訳ありません。非常に興味深いことに気付いたとき、私は自分のプログラムをデバッグしていました。コードは非常に簡単です。私のコメントをインラインでフォローしてください:
//my session class
class Session
{
public:
/// Constructor.
Session(boost::asio::io_service &io_service)
: socket_(io_service)
{
}
boost::asio::ip::tcp::socket& socket()
{
return socket_;
}
void async_read(/*...*/);
void async_write(/*...*/);
//blah blah
private:
std::vector<char> inbound_data_;//<---note this variable, but don't mind it until i tell you
std::string outbound_data_;
boost::asio::ip::tcp::socket socket_;
}
typedef boost::shared_ptr<Session> session_ptr; //just for easy reading
//and this is my connection server class
class ConnectionServer {
public:
void ConnectionServer::CreatSocketAndAccept() {
session_ptr new_sess(new Session(io_service_));//<--I created a scope limited shared_ptr
Print()<< "new_sess.use_count()= " << new_sess.use_count() << std::endl;//prints 1
acceptor_.async_accept(new_sess->socket(),//<-used it for async connection acceptance
boost::bind(&ConnectionServer::handle_accept, this,
boost::asio::placeholders::error, new_sess));
Print()<< "new_sess.use_count()= " << new_sess.use_count() << std::endl;//prints 2
}//<-- Scope is ending. what happens to my new_sess? who keeps a copy of my session?
//and now the strangest thing:
void ConnectionServer::handle_accept(const boost::system::error_code& e, session_ptr sess) {
if (!e) {
Print()<< "sess.use_count()= " << sess.use_count() << std::endl;//prints 4 !!!! while I have never copied the session anywhere else in between
Print() << "Connection Accepted" << std::endl;
handleNewClient(sess);
}
else
{
std::cout << "Connection Refused" << std::endl;
}
CreatSocketAndAccept();
}
誰が (で) 私の内部boost::asio
コピーを作成し、いつそれらすべてをリリースするのかわかりません。shared_ptr
実際、次のような場合にこの状況に気付きました: アプリケーションが完了するまで実行され、ネストされたオブジェクトでいっぱいのコンテナーが (私ではなく自動的に) クリーンアップされているときに、プログラムがしようとしている場所で が呼び出されたshared_ptr
後に、セグ フォールトが発生します。 ~Session()
a に対処しますstd::vector<char>
(これは、最初に覚えておくように言った場所です)。これは、Eclipseデバッガーで確認できました。
私はセグフォルトを読むのが苦手ですが、プログラムが存在しないものを試みてclear
いると思います。vector
長い質問で申し訳ありませんが、お時間を割いていただき、親切なコメントに感謝します。
EDIT-1:Session
アプリケーションを変更して、新しい(s) ではなく
生のポインターを使用するようにしましshared_ptr
た セッションを削除しないと、セグフォルトはなくなります。したがって、少なくとも、セグフォルトの原因は Session にあると確信しています。
編集-2: 前回の更新で述べたように、セッションを削除しようとすると問題が発生しますが、セグメント障害につながるトレースが毎回異なります。時々これ:
Basic Debug [C/C++ Application]
SimMobility_Short [10350] [cores: 0]
Thread [1] 10350 [core: 0] (Suspended : Signal : SIGSEGV:Segmentation fault)
malloc_consolidate() at malloc.c:4,246 0x7ffff5870e20
malloc_consolidate() at malloc.c:4,215 0x7ffff5871b19
_int_free() at malloc.c:4,146 0x7ffff5871b19
__gnu_cxx::new_allocator<char>::deallocate() at new_allocator.h:100 0xa4ab4a
std::_Vector_base<char, std::allocator<char> >::_M_deallocate() at stl_vector.h:175 0xab9508
std::_Vector_base<char, std::allocator<char> >::~_Vector_base() at stl_vector.h:161 0xabf8c7
std::vector<char, std::allocator<char> >::~vector() at stl_vector.h:404 0xabeca4
sim_mob::Session::~Session() at Session.hpp:35 0xabea8d
safe_delete_item<sim_mob::Session>() at LangHelpers.hpp:136 0xabef31
sim_mob::ConnectionHandler::~ConnectionHandler() at ConnectionHandler.cpp:40 0xabd7e6
<...more frames...>
gdb
そして時々これ:
Basic Debug [C/C++ Application]
SimMobility_Short [10498] [cores: 1]
Thread [1] 10498 [core: 1] (Suspended : Signal : SIGSEGV:Segmentation fault)
_int_free() at malloc.c:4,076 0x7ffff5871674
std::basic_string<char, std::char_traits<char>, std::allocator<char> >::~basic_string() at 0x7ffff639d540
sim_mob::ConnectionHandler::~ConnectionHandler() at ConnectionHandler.cpp:30 0xabd806
boost::checked_delete<sim_mob::ConnectionHandler>() at checked_delete.hpp:34 0xadd482
boost::detail::sp_counted_impl_p<sim_mob::ConnectionHandler>::dispose() at sp_counted_impl.hpp:78 0xadd6a2
boost::detail::sp_counted_base::release() at sp_counted_base_gcc_x86.hpp:145 0x849d5e
boost::detail::shared_count::~shared_count() at shared_count.hpp:305 0x849dd7
boost::shared_ptr<sim_mob::ConnectionHandler>::~shared_ptr() at shared_ptr.hpp:164 0x84a668
sim_mob::ClientHandler::~ClientHandler() at ClientHandler.cpp:42 0xac726d
sim_mob::ClientHandler::~ClientHandler() at ClientHandler.cpp:45 0xac72da
<...more frames...>
gdb
私の記憶はすでに壊れているということですか?さらにチェックするにはどうすればよいですか?ありがとうございました