2 * libmad - MPEG audio decoder library
3 * Copyright (C) 2000-2004 Underbit Technologies, Inc.
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28 # ifdef HAVE_SYS_TYPES_H
29 # include <sys/types.h>
32 # ifdef HAVE_SYS_WAIT_H
33 # include <sys/wait.h>
54 * NAME: decoder->init()
55 * DESCRIPTION: initialize a decoder object with callback routines
57 void mad_decoder_init(struct mad_decoder
*decoder
, void *data
,
58 enum mad_flow (*input_func
)(void *,
60 enum mad_flow (*header_func
)(void *,
61 struct mad_header
const *),
62 enum mad_flow (*filter_func
)(void *,
63 struct mad_stream
const *,
65 enum mad_flow (*output_func
)(void *,
66 struct mad_header
const *,
68 enum mad_flow (*error_func
)(void *,
71 enum mad_flow (*message_func
)(void *,
72 void *, unsigned int *))
78 decoder
->async
.pid
= 0;
79 decoder
->async
.in
= -1;
80 decoder
->async
.out
= -1;
84 decoder
->cb_data
= data
;
86 decoder
->input_func
= input_func
;
87 decoder
->header_func
= header_func
;
88 decoder
->filter_func
= filter_func
;
89 decoder
->output_func
= output_func
;
90 decoder
->error_func
= error_func
;
91 decoder
->message_func
= message_func
;
94 int mad_decoder_finish(struct mad_decoder
*decoder
)
96 # if defined(USE_ASYNC)
97 if (decoder
->mode
== MAD_DECODER_MODE_ASYNC
&& decoder
->async
.pid
) {
101 close(decoder
->async
.in
);
104 pid
= waitpid(decoder
->async
.pid
, &status
, 0);
105 while (pid
== -1 && errno
== EINTR
);
109 close(decoder
->async
.out
);
111 decoder
->async
.pid
= 0;
112 decoder
->async
.in
= -1;
113 decoder
->async
.out
= -1;
118 return (!WIFEXITED(status
) || WEXITSTATUS(status
)) ? -1 : 0;
121 /* Avoid compiler warning */
128 # if defined(USE_ASYNC)
130 enum mad_flow
send_io(int fd
, void const *data
, size_t len
)
132 char const *ptr
= data
;
137 count
= write(fd
, ptr
, len
);
138 while (count
== -1 && errno
== EINTR
);
141 return MAD_FLOW_BREAK
;
147 return MAD_FLOW_CONTINUE
;
151 enum mad_flow
receive_io(int fd
, void *buffer
, size_t len
)
158 count
= read(fd
, ptr
, len
);
159 while (count
== -1 && errno
== EINTR
);
162 return (errno
== EAGAIN
) ? MAD_FLOW_IGNORE
: MAD_FLOW_BREAK
;
164 return MAD_FLOW_STOP
;
170 return MAD_FLOW_CONTINUE
;
174 enum mad_flow
receive_io_blocking(int fd
, void *buffer
, size_t len
)
177 enum mad_flow result
;
179 flags
= fcntl(fd
, F_GETFL
);
181 return MAD_FLOW_BREAK
;
183 blocking
= flags
& ~O_NONBLOCK
;
185 if (blocking
!= flags
&&
186 fcntl(fd
, F_SETFL
, blocking
) == -1)
187 return MAD_FLOW_BREAK
;
189 result
= receive_io(fd
, buffer
, len
);
191 if (flags
!= blocking
&&
192 fcntl(fd
, F_SETFL
, flags
) == -1)
193 return MAD_FLOW_BREAK
;
199 enum mad_flow
send(int fd
, void const *message
, unsigned int size
)
201 enum mad_flow result
;
205 result
= send_io(fd
, &size
, sizeof(size
));
209 if (result
== MAD_FLOW_CONTINUE
)
210 result
= send_io(fd
, message
, size
);
216 enum mad_flow
receive(int fd
, void **message
, unsigned int *size
)
218 enum mad_flow result
;
226 result
= receive_io(fd
, &actual
, sizeof(actual
));
228 /* receive message */
230 if (result
== MAD_FLOW_CONTINUE
) {
240 *message
= malloc(*size
);
242 return MAD_FLOW_BREAK
;
245 result
= receive_io_blocking(fd
, *message
, *size
);
248 /* throw away remainder of message */
250 while (actual
&& result
== MAD_FLOW_CONTINUE
) {
254 len
= actual
> sizeof(sink
) ? sizeof(sink
) : actual
;
256 result
= receive_io_blocking(fd
, sink
, len
);
266 enum mad_flow
check_message(struct mad_decoder
*decoder
)
268 enum mad_flow result
;
272 result
= receive(decoder
->async
.in
, &message
, &size
);
274 if (result
== MAD_FLOW_CONTINUE
) {
275 if (decoder
->message_func
== 0)
278 result
= decoder
->message_func(decoder
->cb_data
, message
, &size
);
280 if (result
== MAD_FLOW_IGNORE
||
281 result
== MAD_FLOW_BREAK
)
285 if (send(decoder
->async
.out
, message
, size
) != MAD_FLOW_CONTINUE
)
286 result
= MAD_FLOW_BREAK
;
297 enum mad_flow
error_default(void *data
, struct mad_stream
*stream
,
298 struct mad_frame
*frame
)
300 int *bad_last_frame
= data
;
302 switch (stream
->error
) {
303 case MAD_ERROR_BADCRC
:
305 mad_frame_mute(frame
);
309 return MAD_FLOW_IGNORE
;
312 return MAD_FLOW_CONTINUE
;
317 int run_sync(struct mad_decoder
*decoder
)
319 enum mad_flow (*error_func
)(void *, struct mad_stream
*, struct mad_frame
*);
321 int bad_last_frame
= 0;
322 struct mad_stream
*stream
;
323 struct mad_frame
*frame
;
324 struct mad_synth
*synth
;
327 if (decoder
->input_func
== 0)
330 if (decoder
->error_func
) {
331 error_func
= decoder
->error_func
;
332 error_data
= decoder
->cb_data
;
335 error_func
= error_default
;
336 error_data
= &bad_last_frame
;
339 stream
= &decoder
->sync
->stream
;
340 frame
= &decoder
->sync
->frame
;
341 synth
= &decoder
->sync
->synth
;
343 mad_stream_init(stream
);
344 mad_frame_init(frame
);
345 mad_synth_init(synth
);
347 mad_stream_options(stream
, decoder
->options
);
350 switch (decoder
->input_func(decoder
->cb_data
, stream
)) {
355 case MAD_FLOW_IGNORE
:
357 case MAD_FLOW_CONTINUE
:
362 # if defined(USE_ASYNC)
363 if (decoder
->mode
== MAD_DECODER_MODE_ASYNC
) {
364 switch (check_message(decoder
)) {
365 case MAD_FLOW_IGNORE
:
366 case MAD_FLOW_CONTINUE
:
376 if (decoder
->header_func
) {
377 if (mad_header_decode(&frame
->header
, stream
) == -1) {
378 if (!MAD_RECOVERABLE(stream
->error
))
381 switch (error_func(error_data
, stream
, frame
)) {
386 case MAD_FLOW_IGNORE
:
387 case MAD_FLOW_CONTINUE
:
393 switch (decoder
->header_func(decoder
->cb_data
, &frame
->header
)) {
398 case MAD_FLOW_IGNORE
:
400 case MAD_FLOW_CONTINUE
:
405 if (mad_frame_decode(frame
, stream
) == -1) {
406 if (!MAD_RECOVERABLE(stream
->error
))
409 switch (error_func(error_data
, stream
, frame
)) {
414 case MAD_FLOW_IGNORE
:
416 case MAD_FLOW_CONTINUE
:
424 if (decoder
->filter_func
) {
425 switch (decoder
->filter_func(decoder
->cb_data
, stream
, frame
)) {
430 case MAD_FLOW_IGNORE
:
432 case MAD_FLOW_CONTINUE
:
437 mad_synth_frame(synth
, frame
);
439 if (decoder
->output_func
) {
440 switch (decoder
->output_func(decoder
->cb_data
,
441 &frame
->header
, &synth
->pcm
)) {
446 case MAD_FLOW_IGNORE
:
447 case MAD_FLOW_CONTINUE
:
453 while (stream
->error
== MAD_ERROR_BUFLEN
);
459 mad_synth_finish(synth
);
460 mad_frame_finish(frame
);
461 mad_stream_finish(stream
);
466 # if defined(USE_ASYNC)
468 int run_async(struct mad_decoder
*decoder
)
471 int ptoc
[2], ctop
[2], flags
;
473 if (pipe(ptoc
) == -1)
476 if (pipe(ctop
) == -1) {
482 flags
= fcntl(ptoc
[0], F_GETFL
);
484 fcntl(ptoc
[0], F_SETFL
, flags
| O_NONBLOCK
) == -1) {
501 decoder
->async
.pid
= pid
;
509 decoder
->async
.in
= ctop
[0];
510 decoder
->async
.out
= ptoc
[1];
520 decoder
->async
.in
= ptoc
[0];
521 decoder
->async
.out
= ctop
[1];
523 _exit(run_sync(decoder
));
531 * NAME: decoder->run()
532 * DESCRIPTION: run the decoder thread either synchronously or asynchronously
534 int mad_decoder_run(struct mad_decoder
*decoder
, enum mad_decoder_mode mode
)
537 int (*run
)(struct mad_decoder
*) = 0;
539 switch (decoder
->mode
= mode
) {
540 case MAD_DECODER_MODE_SYNC
:
544 case MAD_DECODER_MODE_ASYNC
:
545 # if defined(USE_ASYNC)
554 decoder
->sync
= malloc(sizeof(*decoder
->sync
));
555 if (decoder
->sync
== 0)
558 result
= run(decoder
);
567 * NAME: decoder->message()
568 * DESCRIPTION: send a message to and receive a reply from the decoder process
570 int mad_decoder_message(struct mad_decoder
*decoder
,
571 void *message
, unsigned int *len
)
573 # if defined(USE_ASYNC)
574 if (decoder
->mode
!= MAD_DECODER_MODE_ASYNC
||
575 send(decoder
->async
.out
, message
, *len
) != MAD_FLOW_CONTINUE
||
576 receive(decoder
->async
.in
, &message
, len
) != MAD_FLOW_CONTINUE
)
581 /* Avoid compiler warnings */