source: roaraudio/libroararts/libartsc.c @ 466:cffb75652a09

Last change on this file since 466:cffb75652a09 was 466:cffb75652a09, checked in by phi, 16 years ago

added some more calls to arts_stream_get() and arts_stream_set(), XMMS is working now!

File size: 6.5 KB
Line 
1//libartsc.c:
2
3#include <roaraudio.h>
4#include <kde/artsc/artsc.h>
5
6struct roar_connection _libroarartsc_connection[1];
7
8struct _libroarartsc_stream {
9 struct roar_stream stream;
10 int fh;
11 int blocking;
12 int block_size;
13 int dir;
14};
15
16int arts_init(void) {
17 return roar_simple_connect(_libroarartsc_connection, NULL, "libroarartsc client");
18}
19
20void arts_free(void) {
21 roar_disconnect(_libroarartsc_connection);
22}
23
24/**
25 * asks aRtsd to free the DSP device and return 1 if it was successful,
26 * 0 if there were active non-suspendable modules
27 */
28int arts_suspend(void) {
29 return roar_set_standby(_libroarartsc_connection, ROAR_STANDBY_ACTIVE) == 0 ? 1 : 0;
30}
31
32/**
33 * asks aRtsd if the DSP device is free and return 1 if it is,
34 * 0 if not
35 */
36int arts_suspended(void) {
37 return roar_get_standby(_libroarartsc_connection) == ROAR_STANDBY_ACTIVE;
38}
39
40
41/**
42 * converts an error code to a human readable error message
43 *
44 * @param errorcode the errorcode (from another arts function that failed)
45 * @returns a text string with the error message
46 */
47const char *arts_error_text(int errorcode) {
48 return strerror(errorcode);
49}
50
51/**
52 * open a stream for playing
53 *
54 * @param rate the sampling rate (something like 44100)
55 * @param bits how many bits each sample has (8 or 16)
56 * @param channels how many channels, 1 is mono, 2 is stereo
57 * @param name the name of the stream (these will be used so that the user can
58 *          assign streams to effects/mixer channels and similar)
59 *
60 * @return a stream
61 */
62arts_stream_t arts_play_stream(int rate, int bits, int channels, const char *name) {
63 struct _libroarartsc_stream * s = malloc(sizeof(struct _libroarartsc_stream));
64 struct roar_meta meta;
65 struct roar_stream_info info;
66
67 if ( !s )
68  return NULL;
69
70 if ( (s->fh = roar_simple_new_stream_obj(_libroarartsc_connection, &(s->stream),
71                                 rate, channels, bits, ROAR_CODEC_DEFAULT, ROAR_DIR_PLAY)) == -1 ) {
72  free(s);
73  return NULL;
74 }
75
76 s->dir = ROAR_DIR_PLAY;
77
78 s->blocking = 1;
79
80 if ( roar_stream_get_info(_libroarartsc_connection, &(s->stream), &info) != -1 ) {
81  s->block_size = info.block_size;
82 } else {
83  close(s->fh);
84  free(s);
85  return NULL;
86 }
87
88 if ( name && *name ) {
89  meta.value  = (char*)name;
90  meta.key[0] = 0;
91  meta.type   = ROAR_META_TYPE_DESCRIPTION;
92
93  roar_stream_meta_set(_libroarartsc_connection, &(s->stream), ROAR_META_MODE_SET, &meta);
94 }
95
96 return (arts_stream_t) s;
97}
98
99/**
100 * open a stream for recording
101 *
102 * @param rate the sampling rate (something like 44100)
103 * @param bits how many bits each sample has (8 or 16)
104 * @param channels how many channels, 1 is mono, 2 is stereo
105 * @param name the name of the stream (these will be used so that the user can
106 *          assign streams to effects/mixer channels and similar)
107 *
108 * @return a stream
109 */
110arts_stream_t arts_record_stream(int rate, int bits, int channels, const char *name) {
111 struct _libroarartsc_stream * s = malloc(sizeof(struct _libroarartsc_stream));
112 struct roar_meta meta;
113 struct roar_stream_info info;
114
115 if ( !s )
116  return NULL;
117
118 if ( (s->fh = roar_simple_new_stream_obj(_libroarartsc_connection, &(s->stream),
119                                 rate, channels, bits, ROAR_CODEC_DEFAULT, ROAR_DIR_RECORD)) == -1 ) {
120  free(s);
121  return NULL;
122 }
123
124 s->dir = ROAR_DIR_RECORD;
125
126 s->blocking = 1;
127
128 if ( roar_stream_get_info(_libroarartsc_connection, &(s->stream), &info) != -1 ) {
129  s->block_size = info.block_size;
130 } else {
131  close(s->fh);
132  free(s);
133  return NULL;
134 }
135
136 if ( name && *name ) {
137  meta.value  = (char*)name;
138  meta.key[0] = 0;
139  meta.type   = ROAR_META_TYPE_DESCRIPTION;
140
141  roar_stream_meta_set(_libroarartsc_connection, &(s->stream), ROAR_META_MODE_SET, &meta);
142 }
143
144 return (arts_stream_t) s;
145}
146
147/**
148 * close a stream
149 */
150void arts_close_stream(arts_stream_t stream) {
151 struct _libroarartsc_stream * s = (struct _libroarartsc_stream *) stream;
152 if ( !stream )
153  return;
154
155 close(s->fh);
156
157 free(stream);
158}
159
160/**
161 * read samples from stream
162 *
163 * @param stream a previously opened record stream
164 * @param buffer a buffer with sample data
165 * @param count the number of bytes contained in the buffer
166 *
167 * @returns number of read bytes on success or error code
168 */
169int arts_read(arts_stream_t stream, void *buffer, int count) {
170 struct _libroarartsc_stream * s = (struct _libroarartsc_stream *) stream;
171 if ( !stream )
172  return -1;
173
174 return read(s->fh, buffer, count);
175}
176
177/**
178 * write samples to to stream
179 *
180 * @param stream a previously opened play stream
181 * @param buffer a buffer with sample data
182 * @param count the number of bytes contained in the buffer
183 *
184 * @returns number of written bytes on success or error code
185 */
186int arts_write(arts_stream_t stream, const void *buffer, int count) {
187 struct _libroarartsc_stream * s = (struct _libroarartsc_stream *) stream;
188 if ( !stream )
189  return -1;
190
191 return write(s->fh, buffer, count);
192}
193
194/**
195 * configure a parameter of a stream
196 *
197 * @param stream an opened record or play stream
198 * @param parameter the parameter you want to modify
199 * @param value the new value
200 *
201 * @returns the new value of the parameter (which may or may not be the value
202 *          you wanted to have), or an error code if something went wrong
203 */
204int arts_stream_set(arts_stream_t stream, arts_parameter_t param, int value) {
205 struct _libroarartsc_stream * s = (struct _libroarartsc_stream *) stream;
206 if ( !stream )
207  return -1;
208
209 if ( param == ARTS_P_BLOCKING ) {
210  if ( roar_socket_nonblock(s->fh, value ? ROAR_SOCKET_BLOCK : ROAR_SOCKET_NONBLOCK) == -1 )
211   return -1;
212  return arts_stream_get(stream, param);
213 }
214
215 return arts_stream_get(stream, param);
216}
217
218/**
219 * query a parameter of a stream
220 *
221 * @param stream an opened record or play stream
222 * @param parameter the parameter you want to query
223 *
224 * @returns the value of the parameter, or an error code
225 */
226int arts_stream_get(arts_stream_t stream, arts_parameter_t param) {
227 struct _libroarartsc_stream * s = (struct _libroarartsc_stream *) stream;
228 fd_set sl;
229 struct timeval tv;
230
231 if ( !stream )
232  return -1;
233
234 if ( param == ARTS_P_PACKET_SIZE ) {
235   return s->block_size;
236 } else if ( param == ARTS_P_BUFFER_SPACE ) {
237  FD_ZERO(&sl);
238  FD_SET(s->fh, &sl);
239
240  tv.tv_sec  = 0;
241  tv.tv_usec = 1;
242
243  if ( s->dir == ROAR_DIR_PLAY ) {
244   if (select(s->fh + 1, NULL, &sl, NULL, &tv) > 0)
245    return s->block_size;
246  } else {
247   if (select(s->fh + 1, &sl, NULL, NULL, &tv) > 0)
248    return s->block_size;
249  }
250
251  return 0;
252 } else if ( param == ARTS_P_BUFFER_SIZE ) {
253   return s->block_size*2;
254 } else if ( param == ARTS_P_PACKET_COUNT ) {
255  return 1;
256 } else if ( param == ARTS_P_BLOCKING ) {
257  return s->blocking;
258 }
259
260 return -1;
261}
262
263//ll
Note: See TracBrowser for help on using the repository browser.