source: roaraudio/libroaresd/esdctl.c @ 1660:99bfd21f00ef

Last change on this file since 1660:99bfd21f00ef was 1660:99bfd21f00ef, checked in by phi, 15 years ago

changed name of fh in con struct to fh, this should all apps requiring the private member to fail to build, added function to get fh, change code to use them both everythere

File size: 9.3 KB
Line 
1//esdctl.c:
2
3/*
4 *      Copyright (C) Philipp 'ph3-der-loewe' Schafft - 2008
5 *  The code (may) include prototypes and comments (and maybe
6 *  other code fragements) from EsounD.
7 *  They are mostly copyrighted by Eric B. Mitchell (aka 'Ricdude)
8 *  <ericmit@ix.netcom.com>. For more information see AUTHORS.esd.
9 *
10 *  This file is part of libroaresd 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, 675 Mass Ave, Cambridge, MA 02139, USA.
26 *
27 *  NOTE for everyone want's to change something and send patches:
28 *  read README and HACKING! There a addition information on
29 *  the license of this document you need to read before you send
30 *  any patches.
31 *
32 *  NOTE for uses of non-GPL (LGPL,...) software using libesd, libartsc
33 *  or libpulse*:
34 *  The libs libroaresd, libroararts and libroarpulse link this libroar
35 *  and are therefore GPL. Because of this it may be illigal to use
36 *  them with any software that uses libesd, libartsc or libpulse*.
37 */
38
39#include "libroaresd.h"
40
41/* lock/unlock will disable/enable foreign clients from connecting */
42
43// we do not have such a thing at the moment...
44// so always return -1
45int esd_lock( int esd ) {
46 return -1;
47}
48int esd_unlock( int esd ) {
49 return -1;
50}
51
52/* standby/resume will free/reclaim audio device so others may use it */
53int esd_standby( int esd ) {
54 struct roar_connection con;
55
56 roar_connect_fh(&con, esd);
57
58 return roar_set_standby(&con, ROAR_STANDBY_ACTIVE);
59}
60
61int esd_resume( int esd ) {
62 struct roar_connection con;
63
64 roar_connect_fh(&con, esd);
65
66 return roar_set_standby(&con, ROAR_STANDBY_INACTIVE);
67}
68
69/* print server into to stdout */
70void esd_print_server_info( esd_server_info_t *server_info ) {
71 char buf[80] = "";
72
73 if ( server_info->format & ESD_BITS16 )
74  strcat(buf, "16 bit ");
75 else
76  strcat(buf, "8 bit ");
77
78 if ( server_info->format & ESD_STEREO )
79  strcat(buf, "stereo ");
80 else
81  strcat(buf, "mono ");
82
83 printf("server version   = %i\n",        server_info->version);
84 printf("server format    = 0x%08x %s\n", server_info->format, buf);
85 printf("server rate      = %i\n",        server_info->rate);
86}
87
88
89void esd_print_player_info( esd_player_info_t *player_info ) {
90 char buf[80] = "";
91
92 if ( player_info->format & ESD_BITS16 )
93  strcat(buf, "16 bit ");
94 else
95  strcat(buf, "8 bit ");
96
97 if ( player_info->format & ESD_MONO )
98  strcat(buf, "stereo ");
99 else
100  strcat(buf, "mono ");
101
102 printf("player %i name    = %s\n",        player_info->source_id, player_info->name);
103 printf("player %i format  = 0x%08x %s\n", player_info->source_id, player_info->format, buf);
104 printf("player %i rate    = %i\n",        player_info->source_id, player_info->rate);
105 printf("player %i left    = %i\n",        player_info->source_id, player_info->left_vol_scale );
106 printf("player %i right   = %i\n",        player_info->source_id, player_info->right_vol_scale );
107}
108
109void esd_print_sample_info( esd_sample_info_t *sample_info ) {
110}
111
112/* print all info to stdout */
113void esd_print_all_info( esd_info_t *all_info ) {
114 esd_player_info_t *player;
115 esd_sample_info_t *sample;
116
117
118 esd_print_server_info(all_info->server);
119
120 player = all_info->player_list;
121
122 while (player) {
123  esd_print_player_info(player);
124  player = player->next;
125 }
126
127 sample = all_info->sample_list;
128
129 while (sample) {
130  esd_print_sample_info(sample);
131  sample = sample->next;
132 }
133
134}
135
136/* retrieve server properties (sample rate, format, version number) */
137esd_server_info_t *esd_get_server_info( int esd ) {
138 esd_server_info_t * r;
139 struct roar_stream     s;
140 struct roar_connection con;
141 struct roar_message    m;
142
143 r = malloc(sizeof(esd_server_info_t));
144
145 if ( r == NULL )
146  return NULL;
147
148 r->version = 0; // seems to be static
149
150 roar_connect_fh(&con, esd);
151 m.cmd     = ROAR_CMD_SERVER_OINFO;
152 m.datalen = 0;
153
154 if ( roar_req(&con, &m, NULL) == -1 ) {
155  free(r);
156  return NULL;
157 }
158
159 if ( m.cmd != ROAR_CMD_OK ) {
160  free(r);
161  return NULL;
162 }
163
164 if ( roar_stream_m2s(&s, &m) == -1 ) {
165  free(r);
166  return NULL;
167 }
168
169 r->rate   = s.info.rate;
170 r->format = 0;
171
172 if ( s.info.channels  == 1 )
173  r->format |= ESD_MONO;
174 else
175  r->format |= ESD_STEREO;
176
177 if ( s.info.bits == 8 )
178  r->format |= ESD_BITS8;
179 else
180  r->format |= ESD_BITS16;
181
182 return r;
183}
184/* release all memory allocated for the server properties structure */
185void esd_free_server_info( esd_server_info_t *server_info ) {
186 if (server_info)
187  free(server_info);
188}
189
190/* retrieve all information from server */
191esd_info_t *esd_get_all_info( int esd ) {
192 esd_info_t * r;
193 int i;
194 int num;
195 int clients[ROAR_CLIENTS_MAX];
196 struct roar_client c;
197 struct roar_stream s;
198 struct roar_connection con[1];
199 struct roar_mixer_settings mixer;
200 int channels;
201 esd_player_info_t * new_player, * cur = NULL; // = NULL to avoid gcc warning
202
203 roar_connect_fh(con, esd);
204
205 r = malloc(sizeof(esd_info_t));
206
207 if ( r == NULL )
208  return NULL;
209
210 r->server      = esd_get_server_info(esd);
211 r->player_list = NULL;
212 r->sample_list = NULL;
213
214 if ( (num = roar_list_clients(con, clients, ROAR_CLIENTS_MAX)) == -1 ) {
215  ROAR_ERR("esd_get_all_info(*): can not get client list");
216  num = 0;
217 }
218
219 for (i = 0; i < num; i++) {
220  if ( roar_get_client(con, &c, clients[i]) == -1 ) {
221   ROAR_ERR("esd_get_all_info(*): can not get client info");
222   continue;
223  }
224
225  if ( c.execed != -1 ) {
226   if ( roar_get_stream(con, &s, c.execed) == -1 ) {
227    ROAR_ERR("esd_get_all_info(*): can not get stream info");
228    continue;
229   }
230
231   if ( (new_player = malloc(sizeof(esd_player_info_t))) == NULL ) {
232    ROAR_ERR("esd_get_all_info(*): can not alloc memory for new player! BAD");
233    continue;
234   }
235
236   new_player->next = NULL;
237
238   new_player->source_id      = c.execed;
239   new_player->rate           = s.info.rate;
240
241   new_player->format         = ROAR_S2ESD(&s);
242//   sprintf(new_player->name, "roar stream %i", c.execed);
243   strncpy(new_player->name, c.name, ESD_NAME_MAX < ROAR_BUFFER_NAME ? ESD_NAME_MAX : ESD_NAME_MAX);
244
245   new_player->server         = r->server;
246
247   if ( roar_get_vol(con, c.execed, &mixer, &channels) == -1 ) {
248    ROAR_ERR("esd_get_all_info(*): can not get stream mixer info");
249    new_player->left_vol_scale = new_player->right_vol_scale = 256;
250   } else {
251    if ( channels == 1 ) {
252     new_player->left_vol_scale = new_player->right_vol_scale = mixer.mixer[0] == 65536 ? 256 : mixer.mixer[0] / 256;
253    } else {
254     if ( channels != 2 ) {
255      ROAR_ERR("esd_get_all_info(*): server seems to run in > 2 channel mode. ignoring any but the first two channels!");
256     }
257     new_player->left_vol_scale  = mixer.mixer[0] == 65536 ? 256 : mixer.mixer[0] / 256;
258     new_player->right_vol_scale = mixer.mixer[1] == 65536 ? 256 : mixer.mixer[1] / 256;
259    }
260   }
261
262
263   if ( r->player_list == NULL ) {
264     r->player_list = cur = new_player;
265   } else {
266     cur->next = new_player; // add to old player
267     cur       = new_player; // hop to next player
268   }
269
270  }
271 }
272
273 return r;
274}
275
276/* retrieve all information from server, and update until unsubsribed or closed */
277esd_info_t *esd_subscribe_all_info( int esd );
278
279/* call to update the info structure with new information, and call callbacks */
280esd_info_t *esd_update_info( int esd, esd_info_t *info,
281                             esd_update_info_callbacks_t *callbacks );
282esd_info_t *esd_unsubscribe_info( int esd );
283
284/* release all memory allocated for the esd info structure */
285void esd_free_all_info( esd_info_t *info ) {
286 esd_player_info_t *player, *oplayer;
287 esd_sample_info_t *sample, *osample;
288
289 if ( info != NULL ) {
290
291/*
292  if ( info->server )
293   free(info->server);
294*/
295  esd_free_server_info(info->server);
296
297
298/*
299  // TODO: do we need to free more?
300  if ( info->player_list )
301   free(info->player_list);
302
303  if ( info->sample_list )
304   free(info->sample_list);
305*/
306
307 player = info->player_list;
308
309 while (player) {
310  oplayer = player;
311  player  = player->next;
312
313  free(oplayer);
314 }
315
316 sample = info->sample_list;
317
318 while (sample) {
319  osample = sample;
320  sample  = sample->next;
321
322  free(osample);
323 }
324
325  free(info);
326 }
327}
328
329
330/* reset the volume panning for a stream */
331int esd_set_stream_pan( int esd, int stream_id,
332                        int left_scale, int right_scale ) {
333 struct roar_connection con;
334 struct roar_mixer_settings mixer;
335
336 roar_connect_fh(&con, esd);
337
338 mixer.mixer[0] = left_scale  == 256 ? 65535 : left_scale  * 256;
339 mixer.mixer[1] = right_scale == 256 ? 65535 : right_scale * 256;
340
341 ROAR_DBG("esd_set_stream_pan(esd=%i, stream_id=%i, left_scale=%i, right_scale=%i) = ?",
342                esd, stream_id, left_scale, right_scale);
343
344 return roar_set_vol(&con, stream_id, &mixer, 2);
345}
346
347/* reset the default volume panning for a sample */
348int esd_set_default_sample_pan( int esd, int sample_id,
349                                int left_scale, int right_scale ) {
350 return -1;
351}
352
353/* see if the server is in stnaby, autostandby, etc */
354esd_standby_mode_t esd_get_standby_mode( int esd ) {
355 return roar_simple_get_standby(esd);
356}
357
358//ll
Note: See TracBrowser for help on using the repository browser.