ディスパッチャを使用するマルチスレッド コードがいくつかあります。gtk スレッドでディスパッチャーを作成/破棄する際には注意が必要でした。しかし、そこからでも破壊できないらしい。このコードを参照してください (これはシングル スレッドでもあります)。何か不足していますか?
#include <gtkmm.h>
#include <iostream>
using namespace std;
class HelloWorld:public Gtk::Window {
public:
Glib::Dispatcher* disp;
Glib::Dispatcher disp2;
sigc::connection conn;
void onDisp(){
cout << "Hello by disp" << endl;
}
HelloWorld():m_button("Hello"),m_destr("Destr") {
disp=new Glib::Dispatcher();
conn=disp->connect(sigc::mem_fun(*this,&HelloWorld::onDisp));
disp2.connect(sigc::mem_fun(*this,&HelloWorld::on_work));
m_button.signal_clicked().connect(sigc::mem_fun(*this,&HelloWorld::on_button_clicked));
m_destr.signal_clicked().connect(sigc::mem_fun(*this,&HelloWorld::on_destr_clicked));
v.add(m_button);
v.add(m_destr);
add(v);
show_all_children();
}
protected:
void on_work(){
usleep(1*1E5);
}
void on_button_clicked(){
for (size_t i=0;i<100;i++){
if (disp!=NULL){
(*disp)();
}
disp2();
}
}
void on_destr_clicked() {
conn.disconnect();
delete disp;
disp=NULL;
}
Gtk::Button m_button;
Gtk::Button m_destr;
Gtk::VBox v;
};
int main (int argc, char *argv[]) {
Gtk::Main kit(argc, argv);
HelloWorld helloworld;
//Shows the window and returns when it is closed.
Gtk::Main::run(helloworld);
return 0;
}
===環境=== Ubuntu 11.10、gtkmm 2.24.2-1、libglib 2.30.0
===GDB====
Program received signal SIGSEGV, Segmentation fault.
0x00007ffff70f6ee9 in Glib::DispatchNotifier::pipe_io_handler(Glib::IOCondition) () from /usr/lib/libglibmm-2.4.so.1
(gdb) bt
#0 0x00007ffff70f6ee9 in Glib::DispatchNotifier::pipe_io_handler(Glib::IOCondition) () from /usr/lib/libglibmm-2.4.so.1
#1 0x00007ffff70f8dcc in Glib::IOSource::dispatch(sigc::slot_base*) () from /usr/lib/libglibmm-2.4.so.1
#2 0x00007ffff70f89df in Glib::Source::dispatch_vfunc(_GSource*, int (*)(void*), void*) () from /usr/lib/libglibmm-2.4.so.1
#3 0x00007ffff4e68a5d in g_main_context_dispatch () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
#4 0x00007ffff4e69258 in ?? () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
#5 0x00007ffff4e69792 in g_main_loop_run () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
#6 0x00007ffff5751db7 in gtk_main () from /usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0
#7 0x00007ffff7824326 in Gtk::Main::run(Gtk::Window&) () from /usr/lib/libgtkmm-2.4.so.1
#8 0x0000000000442f9a in main (argc=1, argv=0x7fffffffe368) at gtkmmWindow.cpp:66
====VALGRIND====
Invalid read of size 8
==5254== at 0x5931E81:
Glib::DispatchNotifier::pipe_io_handler(Glib::IOCondition) (in
/usr/lib/libglibmm-2.4.so.1.3.0)
==5254== by 0x5933DCB: Glib::IOSource::dispatch(sigc::slot_base*) (in
/usr/lib/libglibmm-2.4.so.1.3.0)
==5254== by 0x59339DE: Glib::Source::dispatch_vfunc(_GSource*, int
(*)(void*), void*) (in /usr/lib/libglibmm-2.4.so.1.3.0)
==5254== by 0x7B35A5C: g_main_context_dispatch (in
/lib/x86_64-linux-gnu/libglib-2.0.so.0.3000.0)
==5254== by 0x7B36257: ??? (in
/lib/x86_64-linux-gnu/libglib-2.0.so.0.3000.0)
==5254== by 0x7B36791: g_main_loop_run (in
/lib/x86_64-linux-gnu/libglib-2.0.so.0.3000.0)
==5254== by 0x70E6DB6: gtk_main (in
/usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0.2400.6)
==5254== by 0x530B325: Gtk::Main::run(Gtk::Window&) (in
/usr/lib/libgtkmm-2.4.so.1.1.0)
==5254== by 0x442F99: main (gtkmmWindow.cpp:66)
==5254== Address 0xd1ad9e8 is 8 bytes inside a block of size 24 free'd
==5254== at 0x4C27FF2: operator delete(void*) (vg_replace_malloc.c:387)
==5254== by 0x5B584E8: sigc::signal_base::~signal_base() (in
/usr/lib/libsigc-2.0.so.0.0.0)
==5254== by 0x443A45: HelloWorld::on_destr_clicked() (gtkmmWindow.cpp:50)
==5254== by 0x4442B4: sigc::bound_mem_functor0<void,
HelloWorld>::operator()() const (in
/home/fabio/research/software/bin/gui/gtkmmWindow.greenplanet)
==5254== by 0x4441DF: sigc::adaptor_functor<sigc::bound_mem_functor0<void,
HelloWorld> >::operator()() const (adaptor_trait.h:251)
==5254== by 0x444096:
sigc::internal::slot_call0<sigc::bound_mem_functor0<void, HelloWorld>,
void>::call_it(sigc::internal::slot_rep*) (slot.h:103)
==5254== by 0x5938B07:
Glib::SignalProxyNormal::slot0_void_callback(_GObject*, void*) (in
/usr/lib/libglibmm-2.4.so.1.3.0)
==5254== by 0x78AF0A3: g_closure_invoke (in
/usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0.3000.0)
==5254== by 0x78C11F4: ??? (in
/usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0.3000.0)
==5254== by 0x78CA6B0: g_signal_emit_valist (in
/usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0.3000.0)
==5254== by 0x78CA851: g_signal_emit (in
/usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0.3000.0)
==5254== by 0x7040904: ??? (in
/usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0.2400.6)