source: roaraudio/libroarpulse/mainloop-signal.c @ 5381:430b1d26e12d

Last change on this file since 5381:430b1d26e12d was 5381:430b1d26e12d, checked in by phi, 12 years ago

updated copyright years

File size: 4.9 KB
Line 
1//mainloop-signal.c:
2
3/*
4 *      Copyright (C) Philipp 'ph3-der-loewe' Schafft - 2010-2012
5 *  The code (may) include prototypes and comments (and maybe
6 *  other code fragements) from libpulse*. They are mostly copyrighted by:
7 *  Lennart Poettering <poettering@users.sourceforge.net> and
8 *  Pierre Ossman <drzeus@drzeus.cx>
9 *
10 *  This file is part of libroarpulse a part of RoarAudio,
11 *  a cross-platform sound system for both, home and professional use.
12 *  See README for details.
13 *
14 *  This file is free software; you can redistribute it and/or modify
15 *  it under the terms of the GNU General Public License version 3
16 *  as published by the Free Software Foundation.
17 *
18 *  RoarAudio is distributed in the hope that it will be useful,
19 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
20 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21 *  GNU General Public License for more details.
22 *
23 *  You should have received a copy of the GNU General Public License
24 *  along with this software; see the file COPYING.  If not, write to
25 *  the Free Software Foundation, 51 Franklin Street, Fifth Floor,
26 *  Boston, MA 02110-1301, USA.
27 *
28 *  NOTE for everyone want's to change something and send patches:
29 *  read README and HACKING! There a addition information on
30 *  the license of this document you need to read before you send
31 *  any patches.
32 *
33 *  NOTE for uses of non-GPL (LGPL,...) software using libesd, libartsc
34 *  or libpulse*:
35 *  The libs libroaresd, libroararts and libroarpulse link this libroar
36 *  and are therefore GPL. Because of this it may be illigal to use
37 *  them with any software that uses libesd, libartsc or libpulse*.
38 */
39
40#include <libroarpulse/libroarpulse.h>
41
42#define MAX_SIG 64 /* there is no way to find out */
43
44typedef void (*pa_signal_cb_t) (pa_mainloop_api *api, pa_signal_event*e, int sig, void *userdata);
45
46struct pa_signal_event {
47 int used;
48 int sig;
49 pa_signal_cb_t cb;
50 void * userdata;
51};
52
53static int _roar_pa_signal_inited = 0;
54
55static struct {
56 pa_mainloop_api * api;
57 pa_signal_event sig[MAX_SIG];
58#ifdef ROAR_HAVE_PIPE
59 int pipefh[2];
60 pa_io_event * io_event;
61#endif
62} _roar_pa_signal;
63
64static void _roar_pa_signal_iocb(
65#ifndef ROAR_HAVE_PIPE
66                                 int                 sig
67#else
68                                 pa_mainloop_api   * a,
69                                 pa_io_event       * e,
70                                 int                 fd,
71                                 pa_io_event_flags_t f,
72                                 void *userdata
73#endif
74                                ) {
75 pa_signal_event * se;
76#ifdef ROAR_HAVE_PIPE
77 int sig;
78 size_t ret;
79#endif
80
81 (void)a, (void)e, (void)f, (void)userdata;
82
83#ifdef ROAR_HAVE_PIPE
84 ret = read(fd, &sig, sizeof(sig));
85
86 if ( ret != sizeof(sig) )
87  return;
88#endif
89
90 if ( sig >= MAX_SIG )
91  return;
92
93 se = &(_roar_pa_signal.sig[sig]);
94
95 if ( !se->used )
96  return;
97
98 ROAR_DBG("_roar_pa_signal_iocb(*): sig=%s(%i), se->cb=%p", strsignal(sig), sig, se->cb);
99
100 if ( se->cb != NULL )
101  se->cb(_roar_pa_signal.api, se, sig, se->userdata);
102}
103
104static void _roar_pa_signal_handler (int sig) {
105#ifdef ROAR_HAVE_PIPE
106 write(_roar_pa_signal.pipefh[1], &sig, sizeof(sig));
107#else
108 _roar_pa_signal_iocb(sig);
109#endif
110}
111
112/** Initialize the UNIX signal subsystem and bind it to the specified main loop */
113int pa_signal_init(pa_mainloop_api *api) {
114
115 if ( _roar_pa_signal_inited )
116  return -1;
117
118 memset(&_roar_pa_signal, 0, sizeof(_roar_pa_signal));
119
120 _roar_pa_signal.api = api;
121
122#ifdef ROAR_HAVE_PIPE
123 if ( pipe(_roar_pa_signal.pipefh) == -1 )
124  return -1;
125
126 _roar_pa_signal.io_event = api->io_new(api, _roar_pa_signal.pipefh[0], PA_IO_EVENT_INPUT, _roar_pa_signal_iocb, NULL);
127#endif
128
129 _roar_pa_signal_inited = 1;
130
131 return 0;
132}
133
134/** Cleanup the signal subsystem */
135void pa_signal_done(void) {
136 int i;
137
138 for (i = 0; i < MAX_SIG; i++) {
139  _roar_pa_signal.sig[i].used = 0;
140 }
141
142#ifdef ROAR_HAVE_PIPE
143 _roar_pa_signal.api->io_free(_roar_pa_signal.io_event);
144#endif
145
146 _roar_pa_signal_inited = 0;
147}
148
149/** Create a new UNIX signal event source object */
150pa_signal_event* pa_signal_new(int sig, pa_signal_cb_t callback, void *userdata) {
151 if ( !_roar_pa_signal_inited )
152  return NULL;
153
154 if ( sig >= MAX_SIG )
155  return NULL;
156
157 _roar_pa_signal.sig[sig].used     = 1;
158 _roar_pa_signal.sig[sig].sig      = sig;
159 _roar_pa_signal.sig[sig].cb       = callback;
160 _roar_pa_signal.sig[sig].userdata = userdata;
161
162 signal(sig, _roar_pa_signal_handler);
163
164 return &(_roar_pa_signal.sig[sig]);
165}
166
167/** Free a UNIX signal event source object */
168void pa_signal_free(pa_signal_event *e) {
169 if ( !_roar_pa_signal_inited )
170  return;
171
172 if ( e == NULL )
173  return;
174
175 signal(e->sig, SIG_DFL);
176
177 e->used = 0;
178}
179
180/** Set a function that is called when the signal event source is destroyed. Use this to free the userdata argument if required */
181void pa_signal_set_destroy(pa_signal_event *e, void (*callback) (pa_mainloop_api *api, pa_signal_event*e, void *userdata));
182
183//ll
Note: See TracBrowser for help on using the repository browser.