OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2008 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #ifndef BASE_MESSAGE_PUMP_GLIB_H_ |
| 6 #define BASE_MESSAGE_PUMP_GLIB_H_ |
| 7 |
| 8 #include <glib.h> |
| 9 |
| 10 #include "base/message_pump.h" |
| 11 #include "base/time.h" |
| 12 |
| 13 namespace base { |
| 14 |
| 15 // This class implements a MessagePump needed for TYPE_UI MessageLoops on |
| 16 // OS_LINUX platforms using GLib. |
| 17 class MessagePumpForUI : public MessagePump { |
| 18 public: |
| 19 MessagePumpForUI(); |
| 20 ~MessagePumpForUI(); |
| 21 |
| 22 virtual void Run(Delegate* delegate); |
| 23 virtual void Quit(); |
| 24 virtual void ScheduleWork(); |
| 25 virtual void ScheduleDelayedWork(const Time& delayed_work_time); |
| 26 |
| 27 private: |
| 28 // We may make recursive calls to Run, so we save state that needs to be |
| 29 // separate between them in this structure type. |
| 30 struct RunState { |
| 31 // This is the delegate argument passed to Run. |
| 32 Delegate* delegate; |
| 33 // This tells us when to exit the event pump. |
| 34 bool keep_running; |
| 35 // This tells our work source when to dispatch DoWork and DoDelayedWork. |
| 36 bool should_do_work; |
| 37 // This tells our idle source when to dispatch DoIdleWork. |
| 38 bool should_do_idle_work; |
| 39 // Unlike the work source, which is shared by all calls to Run, each Run |
| 40 // call gets its own idle source because we need to destroy it when we have |
| 41 // no idle work, and we don't want to destroy someone else's source. |
| 42 GSource* idle_source; |
| 43 }; |
| 44 |
| 45 struct WorkSource : GSource { |
| 46 MessagePumpForUI* self; |
| 47 }; |
| 48 |
| 49 // The source with these callbacks remain in the main loop forever. They |
| 50 // will dispatch DoWork and DoDelayedWork, and calculate when and how long |
| 51 // to block when GLib calls poll internally. |
| 52 static GSourceFuncs WorkSourceFuncs; |
| 53 static gboolean WorkSourcePrepare(GSource* source, gint* timeout_ms); |
| 54 static gboolean WorkSourceCheck(GSource* source); |
| 55 static gboolean WorkSourceDispatch(GSource* source, GSourceFunc unused_func, |
| 56 gpointer unused_data); |
| 57 |
| 58 // The source that uses these callbacks is added as an idle source, which |
| 59 // means GLib will call it when there is no other work to do. We continue |
| 60 // doing work as long as DoIdleWork or the other work functions return true. |
| 61 // Once no work remains, we remove the idle source so GLib will block instead |
| 62 // of firing it. Then we re-add it when we wake up. |
| 63 static GSourceFuncs IdleSourceFuncs; |
| 64 static gboolean IdleSourcePrepare(GSource* source, gint* timeout_ms); |
| 65 static gboolean IdleSourceCheck(GSource* source); |
| 66 static gboolean IdleSourceDispatch(GSource* source, GSourceFunc unused_func, |
| 67 gpointer unused_data); |
| 68 |
| 69 // This adds a GLib source to the main loop. |
| 70 GSource* AddSource(GSourceFuncs* funcs, gint priority, |
| 71 GPollFD* optional_poll_fd); |
| 72 |
| 73 RunState* state_; |
| 74 |
| 75 // This is a GLib structure that we can add event sources to. We use the |
| 76 // default GLib context, which is the one to which all GTK events are |
| 77 // dispatched. |
| 78 GMainContext* context_; |
| 79 |
| 80 // This is the time when we need to do delayed work. |
| 81 Time delayed_work_time_; |
| 82 |
| 83 // We use a pipe to schedule work in a thread-safe way that doesn't interfere |
| 84 // with our state. When ScheduleWork is called, we write into the pipe which |
| 85 // ensures poll will not sleep, since we use the read end as an event source. |
| 86 // When we find data pending on the pipe, we clear it out and know we have |
| 87 // been given new work. |
| 88 int write_fd_work_scheduled_; |
| 89 int read_fd_work_scheduled_; |
| 90 |
| 91 // The work source. It is shared by all calls to Run and destroyed when |
| 92 // the message pump is destroyed. |
| 93 GSource* work_source_; |
| 94 |
| 95 DISALLOW_COPY_AND_ASSIGN(MessagePumpForUI); |
| 96 }; |
| 97 |
| 98 } // namespace base |
| 99 |
| 100 #endif // BASE_MESSAGE_PUMP_GLIB_H_ |
OLD | NEW |