]> git.ozlabs.org Git - ccan-lca-2011.git/blob - ccan/tevent/tevent_immediate.c
lca2011: hacky import of tevent.
[ccan-lca-2011.git] / ccan / tevent / tevent_immediate.c
1 /*
2    Unix SMB/CIFS implementation.
3
4    common events code for immediate events
5
6    Copyright (C) Stefan Metzmacher 2009
7
8      ** NOTE! The following LGPL license applies to the tevent
9      ** library. This does NOT imply that all of Samba is released
10      ** under the LGPL
11
12    This library is free software; you can redistribute it and/or
13    modify it under the terms of the GNU Lesser General Public
14    License as published by the Free Software Foundation; either
15    version 3 of the License, or (at your option) any later version.
16
17    This library is distributed in the hope that it will be useful,
18    but WITHOUT ANY WARRANTY; without even the implied warranty of
19    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
20    Lesser General Public License for more details.
21
22    You should have received a copy of the GNU Lesser General Public
23    License along with this library; if not, see <http://www.gnu.org/licenses/>.
24 */
25
26 #include <ccan/tevent/tevent.h>
27 #include <ccan/tevent/tevent_internal.h>
28 #include <ccan/tevent/tevent_util.h>
29
30 static void tevent_common_immediate_cancel(struct tevent_immediate *im)
31 {
32         if (!im->event_ctx) {
33                 return;
34         }
35
36         tevent_debug(im->event_ctx, TEVENT_DEBUG_TRACE,
37                      "Cancel immediate event %p \"%s\"\n",
38                      im, im->handler_name);
39
40         /* let the backend free im->additional_data */
41         if (im->cancel_fn) {
42                 im->cancel_fn(im);
43         }
44
45         DLIST_REMOVE(im->event_ctx->immediate_events, im);
46         im->event_ctx           = NULL;
47         im->handler             = NULL;
48         im->private_data        = NULL;
49         im->handler_name        = NULL;
50         im->schedule_location   = NULL;
51         im->cancel_fn           = NULL;
52         im->additional_data     = NULL;
53
54         talloc_set_destructor(im, NULL);
55 }
56
57 /*
58   destroy an immediate event
59 */
60 static int tevent_common_immediate_destructor(struct tevent_immediate *im)
61 {
62         tevent_common_immediate_cancel(im);
63         return 0;
64 }
65
66 /*
67  * schedule an immediate event on
68  */
69 void tevent_common_schedule_immediate(struct tevent_immediate *im,
70                                       struct tevent_context *ev,
71                                       tevent_immediate_handler_t handler,
72                                       void *private_data,
73                                       const char *handler_name,
74                                       const char *location)
75 {
76         tevent_common_immediate_cancel(im);
77
78         if (!handler) {
79                 return;
80         }
81
82         im->event_ctx           = ev;
83         im->handler             = handler;
84         im->private_data        = private_data;
85         im->handler_name        = handler_name;
86         im->schedule_location   = location;
87         im->cancel_fn           = NULL;
88         im->additional_data     = NULL;
89
90         DLIST_ADD_END(ev->immediate_events, im, struct tevent_immediate *);
91         talloc_set_destructor(im, tevent_common_immediate_destructor);
92
93         tevent_debug(ev, TEVENT_DEBUG_TRACE,
94                      "Schedule immediate event \"%s\": %p\n",
95                      handler_name, im);
96 }
97
98 /*
99   trigger the first immediate event and return true
100   if no event was triggered return false
101 */
102 bool tevent_common_loop_immediate(struct tevent_context *ev)
103 {
104         struct tevent_immediate *im = ev->immediate_events;
105         tevent_immediate_handler_t handler;
106         void *private_data;
107
108         if (!im) {
109                 return false;
110         }
111
112         tevent_debug(ev, TEVENT_DEBUG_TRACE,
113                      "Run immediate event \"%s\": %p\n",
114                      im->handler_name, im);
115
116         /*
117          * remember the handler and then clear the event
118          * the handler might reschedule the event
119          */
120         handler = im->handler;
121         private_data = im->private_data;
122
123         DLIST_REMOVE(im->event_ctx->immediate_events, im);
124         im->event_ctx           = NULL;
125         im->handler             = NULL;
126         im->private_data        = NULL;
127         im->handler_name        = NULL;
128         im->schedule_location   = NULL;
129         im->cancel_fn           = NULL;
130         im->additional_data     = NULL;
131
132         talloc_set_destructor(im, NULL);
133
134         handler(ev, im, private_data);
135
136         return true;
137 }
138