views:

199

answers:

2

These two functions are both infinite loops,

and the programe hangs once called in the same thread.

gtk_main(); 
...
pcap_loop(adhandle, 0, packet_handler, NULL);

When I click the "start" button,I want pcap to start working;And if I press the "stop" button,pcap stop.

How do I create a child thread and run pcap_loop(adhandle, 0, packet_handler, NULL); instead?

A: 

Take a look at the documentation for g_thread_create(). Also read this tutorial and this blog post for more information on multithreaded GTK programs.

Basically you'll want to call gtk_main() first when you've built your user interface and started your program. Then in the callback for the "start" button, create a new thread with g_thread_create() in which you call pcap_loop().

The "stop" button is a little more difficult since GLib doesn't allow you to interrupt a thread from a different thread. You'll have to create some signaling mechanism; for example, a boolean abort flag protected by a GMutex. In your stop button callback, lock the flag with g_mutex_lock(), set it, and unlock it with g_mutex_unlock(). In your packet_handler, also lock the flag, read it, and unlock it. If the flag was set, then call whatever it is you call to make pcap break out of the loop.

ptomato
How can I output something into `gtk_text_view`(main thread) from the thread(child thread) created by `g_thread_create()`?
httpinterpret
Read the documentation about threads in GTK. You can call GTK functions from the child thread, as long as you _protect_ them by surrounding the GTK calls with `gdk_threads_enter()` and `gdk_threads_leave()`.
ptomato
Thanks,let me read the tuto carefully:)
httpinterpret
+2  A: 

Unless I am missing something, your problem is that both GTK+ and libpcap are organized around events fired from a main loop. Without looking through the documentation, I don't know about GTK+, but there is another mode of operation for libpcap: You can use pcap_next() or pcap_next_ex() without giving up control over your program flow.

It should be possible to register a function that periodically calls one of these two functions using g_timeout_add() or g_idle_add(), removing the need to mess around with threads and mutex mechanisms altogether.

hillu