I'm building a fairly simple C application using GTK, but have to perform some blocking IO which will trigger updates to the GUI. In order to do this, I start a new pthread right before gtk_main() as such:
/* global variables */
GMainContext *mainc;
/* local variables */
FILE *fifo;
pthread_t reader;
/* main() */
mainc = g_main_context_default();
pthread_create(&reader, NULL, watch_fifo, argv[argc-1]);
gtk_main();
When the pthread reads some data, it updates the GUI like so:
g_main_context_invoke(mainc, set_icon, param);
Where set_icon is
gboolean set_icon(gpointer data)
{
char *p = (char*)data;
gtk_status_icon_set_from_icon_name(icon, p);
return FALSE;
}
This all works most of the time, but every now and again I get this curious error message:
[xcb] Unknown sequence number while processing queue
[xcb] Most likely this is a multi-threaded client and XInitThreads has not been called
[xcb] Aborting, sorry about that.
mktrayicon: xcb_io.c:274: poll_for_event: Assertion `!xcb_xlib_threads_sequence_lost' failed.
I thought the whole point of using g_main_context_invoke was to avoid issues with threads? Doing a bit of Googling, I came across gdk_threads_init, gdk_threads_enter and friends, but they all seem to be deprecated? I know the GTK documentation says that all GUI updaes should be performed on the main thread, but this does not combine all that well with blocking IO, and I'd prefer not to have to construct some complex communication mechanism between the threads.
And so, my question is, how should I correctly deal with this?
EDIT: The full code can be seen here
EDIT2: As an update based on #ptomato's answer, I've moved to GThreads and using gdk_threads_add_idle() as seen in this commit, but the problem is still present.
Call XInitThreads(). This should be done before gtk_init, that will stop the messages!
Something like this:
#include <X11/Xlib.h>
...
XInitThreads();
...
gtk_init(&argc, &argv);
I don't remember seeing these messages before GLIB 2.32, when
g_thread_init()/gdk_threads_init() were used.
You might want to check out g_thread_pool_new and g_thread_pool_push.
From thread, use g_main_context_invoke to execute in main loop or
just wrap thread between gdk_threads_enter()/gdk_threads_leave()
I do not use a tray so I can not easily check this. I think you are
correct about gdk_threads_add_idle using locks to protect GTK/GDK API.
There is nothing obvious to me that would cause these messages to
appear. The function description for gtk_status_icon_new_from_icon_name
states that "If the current icon theme is changed, the icon will be
updated appropriately. Which to me, implies your code is not the only
code that will access the X display, which could potentially be the
problem.
There is also some related info regarding XInitThreads() at
What is the downside of XInitThreads()?
Note that while GDK uses locks for the display, GTK/GDK do not ever
call XInitThreads.
On a side note: What's protecting the global variable "onclick", which
is passed to execl after a fork(), The child will not inherit the parent's
memory locks, and GLib mainloop is incompatible with fork().
Maybe you could copy the string to local variable.
I'm not sure if bare pthreads are guaranteed to work with GTK. You should use the GThread wrappers.
I think what the problem may be is that g_main_context_invoke() is adding set_icon() as an idle function. (It seems that that is what goes on behind the scenes, but I'm not sure.) Idle functions added using GLib's API, despite being executed on the main thread, need to hold the GDK lock. If you use the gdk_threads_add_idle() API (which is not deprecated) to invoke set_icon(), then everything should work properly with threading.
(Although this is just a wild guess.)
As a work around, if you just want to avoid blocking the UI while waiting for some IO you could use the asynchronous IO from GIO. That would avoid you having to manage threads yourself.
Edit: Thinking about it you could just mark your file descriptors as non-blocking and add them as a source to the glib main loop and it will poll them for you in the main event loop without having to mess about with threads.
You could avoid using threads by using gio_add_watch() which will invoke your callback function when there is data available on the channel.
Related
This is what says on http://invisible-island.net/ncurses/ncurses.faq.html#multithread
If you have a program which uses curses in more than one thread, you will almost certainly see odd behavior. That is because curses relies upon static variables for both input and output. Using one thread for input and other(s) for output cannot solve the problem, nor can extra screen updates help. This FAQ is not a tutorial on threaded programming.
Specifically, it mentions it is not safe even if input and output are done on separate threads. Would it be safe if we further use a mutex for the whole ncurses library so that at most one thread can be calling any ncurses function at a time? If not, what would be other cheap workarounds to use ncurses safely in multi-thread application?
I'm asking this question because I notice a real application often has its own event loop but relies on ncurses getch function to get keyboard input. But if the main thread is block waiting in its own event loop, then it has no chance to call getch. A seemingly applicable solution is to call getch in a different thread, which hasn't caused me a problem yet, but as what says above is actually not safe, and was verified by another user here. So I'm wondering what is the best way to merge getch into an application's own event loop.
I'm considering making getch non-blocking and waking up the main thread regularly (every 10-100 ms) to check if there is something to read. But this adds an additional delay between key events and makes the application less responsive. Also, I'm not sure if that would cause any problems with some ncurses internal delay such as ESCDELAY.
Another solution I'm considering is to poll stdin directly. But I guess ncurses should also be doing something like that and reading the same stream from two different places looks bad.
The text also mentions the "ncursest" or "ncursestw" libraries, but they seem to be less available, for example, if you are using a different language binding of curses. It would be great if there is a viable solution with the standard ncurses library.
Without the thread-support, you're out of luck for using curses functions in more than one thread. That's because most of the curses calls use static or global data. The getch function for instance calls refresh which can update the whole screen—using the global pointers curscr and stdscr. The difference in the thread-support configuration is that global values are converted to functions and mutex's added.
If you want to read stdin from a different thread and run curses in one thread, you probably can make that work by checking the file descriptor (i.e., 0) for pending activity and alerting the thread which runs curses to tell it to read data.
I've programmed a GTK3 application in C. To speed up performance I want to put some calculations in separate threads. Currently I have not yet decided how to exactly implement it. But I think I will go with a GTask that I will trigger to run in a separate thread.
I want to to emit certain status updates about the calculation progress on my GUI.
They way I imagine this:
I've got a calculation GObject with a do_the_stuff_async() function that triggers the thread/GTask. Ideally, I want to connect to a 'progress-changed' signal which gives me the current status that I can display on my GUI. Also it would be great to trigger an event once the task has finished, which seems doable with a GTask
How do I safely emit a signal from a GTask/GThread to my GTK main loop?
Because I have not yet started implementing the asynchronous stuff: Is a GTask a suitable way for this or should I use something entirely different?
A GTask is suitable for this.
To emit the signal in a different thread:
Store the GMainContext of the main thread somewhere, and pass it into the GTask as task data.
When you want to emit a signal, create a GSource with g_idle_source_new(), add a callback for it, and attach it to the GMainContext of the main thread. That will make the callback be called in the main thread the next time the main thread’s context iterates.
The callback should call g_signal_emit() as appropriate.
Unless you want to make the GObject that you’re emitting the signal from thread safe, you should not pass it to the GTask worker thread. My general advice would be to avoid locking by only passing immutable objects to and from the worker thread.
Note that you could use g_idle_add() to create an idle GSource and add it to the global default GMainContext (the one GTK uses in the main thread). However, this makes the use of the GMainContext less explicit, and hence makes the code less maintainable. It’s not an approach which I would recommend in general.
I know similar questions have been asked, but I think my situation is little bit different. I need to check if child thread is alive, and if it's not print error message. Child thread is supposed to run all the time. So basically I just need non-block pthread_join and in my case there are no race conditions. Child thread can be killed so I can't set some kind of shared variable from child thread when it completes because it will not be set in this case.
Killing of child thread can be done like this:
kill -9 child_pid
EDIT: alright, this example is wrong but still I'm sure there exists way to kill a specific thread in some way.
EDIT: my motivation for this is to implement another layer of security in my application which requires this check. Even though this check can be bypassed but that is another story.
EDIT: lets say my application is intended as a demo for reverse engineering students. And their task is to hack my application. But I placed some anti-hacking/anti-debugging obstacles in child thread. And I wanted to be sure that this child thread is kept alive. As mentioned in some comments - it's probably not that easy to kill child without messing parent so maybe this check is not necessary. Security checks are present in main thread also but this time I needed to add them in another thread to make main thread responsive.
killed by what and why that thing can't indicate the thread is dead? but even then this sounds fishy
it's almost universally a design error if you need to check if a thread/process is alive - the logic in the code should implicitly handle this.
In your edit it seems you want to do something about a possibility of a thread getting killed by something completely external.
Well, good news. There is no way to do that without bringing the whole process down. All ways of non-voluntary death of a thread kill all threads in the process, apart from cancellation but that can only be triggered by something else in the same process.
The kill(1) command does not send signals to some thread, but to a entire process. Read carefully signal(7) and pthreads(7).
Signals and threads don't mix well together. As a rule of thumb, you don't want to use both.
BTW, using kill -KILL or kill -9 is a mistake. The receiving process don't have the opportunity to handle the SIGKILL signal. You should use SIGTERM ...
If you want to handle SIGTERM in a multi-threaded application, read signal-safety(7) and consider setting some pipe(7) to self (and use poll(2) in some event loop) which the signal handler would write(2). That well-known trick is well explained in Qt documentation. You could also consider the signalfd(2) Linux specific syscall.
If you think of using pthread_kill(3), you probably should not in your case (however, using it with a 0 signal is a valid but crude way to check that the thread exists). Read some Pthread tutorial. Don't forget to pthread_join(3) or pthread_detach(3).
Child thread is supposed to run all the time.
This is the wrong approach. You should know when and how a child thread terminates because you are coding the function passed to pthread_create(3) and you should handle all error cases there and add relevant cleanup code (and perhaps synchronization). So the child thread should run as long as you want it to run and should do appropriate cleanup actions when ending.
Consider also some other inter-process communication mechanism (like socket(7), fifo(7) ...); they are generally more suitable than signals, notably for multi-threaded applications. For example you might design your application as some specialized web or HTTP server (using libonion or some other HTTP server library). You'll then use your web browser, or some HTTP client command (like curl) or HTTP client library like libcurl to drive your multi-threaded application. Or add some RPC ability into your application, perhaps using JSONRPC.
(your putative usage of signals smells very bad and is likely to be some XY problem; consider strongly using something better)
my motivation for this is to implement another layer of security in my application
I don't understand that at all. How can signal and threads add security? I'm guessing you are decreasing the security of your software.
I wanted to be sure that this child thread is kept alive.
You can't be sure, other than by coding well and avoiding bugs (but be aware of Rice's theorem and the Halting Problem: there cannot be any reliable and sound static source code program analysis to check that). If something else (e.g. some other thread, or even bad code in your own one) is e.g. arbitrarily modifying the call stack of your thread, you've got undefined behavior and you can just be very scared.
In practice tools like the gdb debugger, address and thread sanitizers, other compiler instrumentation options, valgrind, can help to find most such bugs, but there is No Silver Bullet.
Maybe you want to take advantage of process isolation, but then you should give up your multi-threading approach, and consider some multi-processing approach. By definition, threads share a lot of resources (notably their virtual address space) with other threads of the same process. So the security checks mentioned in your question don't make much sense. I guess that they are adding more code, but just decrease security (since you'll have more bugs).
Reading a textbook like Operating Systems: Three Easy Pieces should be worthwhile.
You can use pthread_kill() to check if a thread exists.
SYNOPSIS
#include <signal.h>
int pthread_kill(pthread_t thread, int sig);
DESCRIPTION
The pthread_kill() function shall request that a signal be delivered
to the specified thread.
As in kill(), if sig is zero, error checking shall be performed
but no signal shall actually be sent.
Something like
int rc = pthread_kill( thread_id, 0 );
if ( rc != 0 )
{
// thread no longer exists...
}
It's not very useful, though, as stated by others elsewhere, and it's really weak as any type of security measure. Anything with permissions to kill a thread will be able to stop it from running without killing it, or make it run arbitrary code so that it doesn't do what you want.
I wrote a C/S application using udp and it keeps giving me errors, which I believe has something to do with the way I use threads.
When the client program starts, it first initializes a login window and starts a new thread to listen to the response from the server. After it submits user name and password, the new thread will receive a message indicating whether it submitted the right info. If it did, then the thread would initializes the main GUI window. But it would give strange errors:
Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0
or
python: Fatal IO error 0 (Success) on X server :0.0
I found a similar question here, but it's not solved.
Some say GUI should only be manipulated in the main thread, but others say it's not true.
I also tried using gdk_threads_enter() and gdk_threads_enter() around gtk_main() and the code where I initialize window in that listen thread. But it didn't seem to work.
I don't know much about threads so be patient when pointing out where I have done wrong.
Thanks.
These error messages, I have found, pop up from time to time when you are not holding the GTK lock properly.
You should put gdk_threads_enter() and gdk_threads_leave() around the original gtk_main() call, and also around every call to a GTK function that takes place
outside the thread from which you called gtk_main()
but not in a signal, idle, or timeout handler.
This usage is on its way out though as I understand, and in future versions of GTK it will only be possible to manipulate GTK from the main thread.
It is true that GTK windows should only be manipulated from the main thread.
That said, in some architectures (notably GNU/Linux) you can manipulate GTK windows from another thread provided that you properly use the global lock with gdk_threads_enter() / gdk_threads_leave(). The key word is "properly", that's not as easy as it seems.
And that said, in some architectures (notably MS-Windows) doing that may seem to work in some simple programs, but will fail miserably in more complex ones.
About your question, you don't say it, but you seem to be using Python somewhere, but you don't say where... Mixing Python and native threads is probably not such a good idea, either.
I'm working with both libfuse and the glib event interface and I've run into an issue where I need to run multiple main loops concurrently (glib's g_main_loop_run and fuse_loop_mt).
I've already attempted to created a detached thread for glib's event loop under a secondary context, e.g.:
static void *
event_loop(void *arg)
{
GMainLoop *event_loop;
GMainContext *context;
context = g_main_context_new();
g_main_context_push_thread_default(context);
event_loop = g_main_loop_new(context, FALSE);
g_main_loop_run(event_loop);
return NULL;
}
...
pthread_t event_thread;
pthread_attr_t thread_attr;
pthread_attr_init(&thread_attr);
pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_DETACHED);
event_thread = pthread_create(&event_thread, &thread_attr,
event_loop, NULL);
However the glib event loop doesn't pick up on any of the fired events. Am I totally off-base here? What's the proper way to tackle multiple main loops?
The GLib main loop supports custom event sources. I don't know much about FUSE, but you might be able to run FUSE's main loop within another thread, and integrate its events into the GLib loop.
A quick search suggests that you might be able to use a lower-level FUSE API to write your own main loop, which could presumably be integrated more readily into GLib's by simply skipping the "loop" part.
In general, though, multiple main loops are just bad news; that's why they're called main loops. :) The best way to handle them is to eliminate them by hooking events directly into whatever loop works best for you. Unfortunately, not all APIs provide the sufficient hooks to make that possible.
Apart from setting up main loops in a separate thread or a process (from the little bit of experience I have had, separate process has worked better for me but then again thread might work well in your case), you can consider integrating fuse main loop in GLib's main loop (Unfortunately I have no prior experience with this). You can check this thread discussion about the same (in case you have not seen it already). As suggested at the end of the thread " Register the fuse device file descriptor
(fuse_chan_fd()) with the glib event loop. Then call fuse_chan_recv()
and fuse_session_process() when the event trigger". To track the fd you will need to use GIO(More info on Nokia developer page).
Hopefully this can provide some hints!