ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/Glib-EV/EV.xs
Revision: 1.5
Committed: Mon Nov 1 22:23:31 2010 UTC (13 years, 6 months ago) by root
Branch: MAIN
CVS Tags: rel-2_02, HEAD
Changes since 1.4: +3 -3 lines
Log Message:
2.02

File Contents

# Content
1 #include "EXTERN.h"
2 #include "perl.h"
3 #include "XSUB.h"
4
5 #include <glib.h>
6 #include "EVAPI.h"
7
8 static GMainContext *
9 get_gcontext (SV *context)
10 {
11 if (!SvOK (context))
12 return g_main_context_default ();
13
14 croak ("only the default context is currently supported.");
15 }
16
17 static void
18 timeout_cb (EV_P_ ev_timer *w, int revents)
19 {
20 ev_break (EV_A, EVBREAK_ONE);
21 }
22
23 typedef struct
24 {
25 struct ev_io io;
26 int *got_events;
27 GPollFD *pfd;
28 } slot;
29
30 static void
31 io_cb (EV_P_ ev_io *w, int revents)
32 {
33 slot *s = (slot *)w;
34 int oev = s->pfd->revents;
35
36 s->pfd->revents |= s->pfd->events &
37 ((revents & EV_READ ? G_IO_IN : 0)
38 | (revents & EV_WRITE ? G_IO_OUT : 0));
39
40 if (!oev && s->pfd->revents)
41 ++*(s->got_events);
42
43 ev_break (EV_A, EVBREAK_ONE);
44 }
45
46 static gint
47 event_poll_func (GPollFD *fds, guint nfds, gint timeout)
48 {
49 dSP;
50 // yes, I use C99. If your compiler barfs here, fix it, but don't
51 // tell me your compiler vendor was too incompetent to implement
52 // the C standard within the last eight years.
53 ev_timer to;
54 slot slots[nfds];
55 int got_events = 0;
56 int n;
57
58 for (n = 0; n < nfds; ++n)
59 {
60 GPollFD *pfd = fds + n;
61 slot *s = slots + n;
62
63 pfd->revents = 0;
64
65 s->pfd = pfd;
66 s->got_events = &got_events;
67
68 ev_io_init (
69 &s->io,
70 io_cb,
71 pfd->fd,
72 (pfd->events & G_IO_IN ? EV_READ : 0)
73 | (pfd->events & G_IO_OUT ? EV_WRITE : 0)
74 );
75 ev_io_start (EV_DEFAULT, &s->io);
76 }
77
78 if (timeout >= 0)
79 {
80 ev_timer_init (&to, timeout_cb, timeout * 1e-3, 0.);
81 ev_timer_start (EV_DEFAULT, &to);
82 }
83
84 ev_run (EV_DEFAULT, 0);
85
86 if (timeout >= 0)
87 ev_timer_stop (EV_DEFAULT, &to);
88
89 for (n = 0; n < nfds; ++n)
90 ev_io_stop (EV_DEFAULT, &slots[n].io);
91
92 return got_events;
93 }
94
95 MODULE = Glib::EV PACKAGE = Glib::EV
96
97 PROTOTYPES: ENABLE
98
99 BOOT:
100 {
101 I_EV_API ("Glib::EV");
102 }
103
104 long
105 install (SV *context)
106 CODE:
107 {
108 GMainContext *ctx = get_gcontext (context);
109
110 RETVAL = (long)g_main_context_get_poll_func (ctx);
111
112 g_main_context_set_poll_func (ctx, event_poll_func);
113 }
114 OUTPUT:
115 RETVAL
116
117 void
118 uninstall (SV *context, long prev_poll_func)
119 CODE:
120 {
121 GMainContext *ctx = get_gcontext (context);
122
123 g_main_context_set_poll_func (ctx, (GPollFunc) prev_poll_func);
124 }
125
126