Re: Proper way to provide gtk+ app with asynchronous data?
- From: "NavEcos" <ecos navosha com>
- To: "Dmitry M. Shatrov" <zzidre mail ru>
- Cc: gtk-list gnome org
- Subject: Re: Proper way to provide gtk+ app with asynchronous data?
- Date: Fri, 9 Jul 2004 04:17:20 -0700
You can use a pipe and use 3 threads.
Use one thread for the "main" gtk loop - this will the thread the calls
gtk_main()
Use one thread to acquire data and send the data through a pipe
Use one thread to do the updates to the screen asynchrnously - it will get
its data via a pipe.
It's been a while since I've use pipes, but as I recall (dimly) it's pretty
straighforward, just do a "man 2 pipe"
Another note about using threads with gtk - do NOT do this in your
asynchronous thread:
for (;;)
{
gdk_threads_enter()
// wait for data (!)
// update screen
gdk_threads_leave();
}
do this instead
for (;;)
{
// wait for data (don't block between gdk_threads_enter & leave)
gdk_threads_enter()
// update screen
gdk_threads_leave();
}
If you do the first one, you'll lock up your application update while data
is waiting to be received.
Do not waste a lot of time trying to do gdk_threads_enter() and ...leave()
in lots of places to minimize the time spent in the gdk_threads_enter() and
...leave() areas - do NOT think of it as a critical section another words.
Keep it simple!
Another fun thing - if you try to set a breakpoint in gdb where
gdk_threads_enter() has been entered, it will lock up your entire screen
sometimes. It pays to have two X11 sessions or 2 machines: OR better yet:
you can get around this though using Xvnc - use a virtual X11 display. Xvnc
is part of TightVNC, do a man on vncviewer and vncserver. There are
vncviewers available for Windows, and let me tell you, it's great.
Good luck, it's not a lot of fun to deal with threads in my opinion with
GTK.
-Rich
P.S. If you've not played with it, try fooling around with TightVNC a bit.
It's a wonderful little program and extremely useful, and the best kept
secret of Linux in my opinion. With it, we run 5 users on a single machine,
and use dumb terminals with either Knoppix or Windoze to connect. It
greatly reduces our IT headaches, and saved us lots of money.
----- Original Message -----
From: "Dmitry M. Shatrov" <zzidre mail ru>
To: "NavEcos" <ecos navosha com>
Cc: "zze-DEPREZ Olivier FTRD/DMI/SOP" <olivier deprez rd francetelecom com>;
<gtk-list gnome org>
Sent: Thursday, July 08, 2004 10:47 AM
Subject: Re: Proper way to provide gtk+ app with asynchronous data?
> Ok, gdk_threads_enter/leave is the way, but before coding it I'd like to
> figure out if this could be done in a message-oriented manner,
> not in cross-locking one.
>
> The proplem is that the thread that receives data does other
> time-critical things as well, so it seems improper to block it for UI
> purposes.
> What about something like messages to the main message loop?
>
> Though I can create additional helper-thread to gather data and draw it
> via gdk_therads_enter, so that receiver-thread doesn't get blocked.
> But it's an additional thread, here comes the desing cleaness issue.
>
> Regards, Dmitry.
>
> NavEcos wrote:
>
> >Excuse me for jumping in the fray, but let me expand on this because
it's
> >simple to use threads if you use some simple rules:
> >
> >In your primary thread (i.e. the thread that will eventually call
> >gtk_main():
> >o you MUST call g_thread_init(NULL); - call this before calling
> >gnome_init();
> >o when you call gtk_main() put a gdk_threads_enter() and
> gdk_threads_leave()
> >around it, i.e.
> > - gdk_threads_enter()
> > - gdk_main()
> > - gdk_threads_leave()
> > I do not know why this must be done, just that it must be done. I
> am not
> >sure it even must be done, just that everybody does it!
> >
> >In the thread that does the asynchronous update on the display (the
> >secondary thread)
> >o once you get your data that will change the screen,
> > - call gdk_threads_enter()
> > - then update the screen doing whatever gtk calls you do normally
> > - you can OPTIONALLY (and probably want to) call gdk_flush() - if you
> >don't, the screen won't update promptly.
> > - then call gdk_threads_leave()
> >
> >If you ever call gdk_threads_enter() twice withouth calling
> >gdk_threads_leave() first, your screen will lockup. That's very fun.
You
> >need to go to another machine or log in on the console (ALT-CTL-F1) and
> >kill -9 your program. This *will* happen to you.
> >
> >If you don't call gdk_threads_enter() before updating the screen,
> you'll get
> >a mysterous error talking about asynchronous something stuff, and your
> >program will crash. I don't remember the exact error, but you'll
probably
> >do it at least once. When you get this error, it's because you didn't
> call
> >gdk_threads_enter() from your SECONDARY thread first. This problem
> will be
> >INTERMITTENT and RANDOM, so you won't be sure you have this error
> until you
> >run the code - a lot.
> >
> >Never call gdk_threads_enter() from your primary thread except around
> >gdk_main()
> >
> >I have a suggestion or 2 about all this BTW:
> >
> >1) gdk_threads_enter() should have a reference count to detect when it's
> >called twice and notify you when it is called twice. It might be nice
to
> >ALLOW gdk_threads_enter() to be called multiple times by the same
> thread as
> >long as a number of matching gdk_threads_leave() gets called.
> >
> >2) Also, it seems silly to me that you need to surround gdk_main() with
> >gdk_threads_enter() and gdk_threads_leave() - calling
g_thread_init(NULL)
> >should do that for you by setting some internal variable that will cause
> >gdk_main() to do it automatically. It's pretty esoteric and odd the way
> >it's currently setup.
> >
> >I'm also curious why gtk_threads_init() doesn't just do the
> >gdk_threads_enter() and gdk_threads_leave() for ALL GTK functions? GTK
> >knows the PID of the process that called gnome_init() - if the PID is
> >different than the primary threads, why not just handle
> gdk_threads_enter()
> >and .._leave() for you by all the gtk functions? I know this is a major
> >overhaul, but it doesn't seem like it would incurr much of a penalty in
> >performance, especially considering how much error checking is done
> already
> >on casting variables.
> >
> >-Rich
> >
> >
>
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]