summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/demuxers/demux_tta.c58
1 files changed, 40 insertions, 18 deletions
diff --git a/src/demuxers/demux_tta.c b/src/demuxers/demux_tta.c
index 1b50edcd4..3158a9ed6 100644
--- a/src/demuxers/demux_tta.c
+++ b/src/demuxers/demux_tta.c
@@ -164,6 +164,12 @@ static int demux_tta_send_chunk(demux_plugin_t *this_gen) {
static void demux_tta_send_headers(demux_plugin_t *this_gen) {
demux_tta_t *this = (demux_tta_t *) this_gen;
buf_element_t *buf;
+ xine_waveformatex wave;
+ uint32_t total_size = sizeof(xine_waveformatex) + sizeof(this->header) +
+ sizeof(uint32_t)*this->totalframes;
+ unsigned char *header;
+
+ header = malloc(total_size);
this->audio_fifo = this->stream->audio_fifo;
@@ -181,27 +187,43 @@ static void demux_tta_send_headers(demux_plugin_t *this_gen) {
/* send start buffers */
_x_demux_control_start(this->stream);
- /* send init info to decoders */
- if (this->audio_fifo) {
- xine_waveformatex wave;
-
- buf = this->audio_fifo->buffer_pool_alloc (this->audio_fifo);
- buf->type = BUF_AUDIO_TTA;
- buf->decoder_flags = BUF_FLAG_HEADER|BUF_FLAG_STDHEADER|BUF_FLAG_FRAME_END;
- buf->decoder_info[0] = 0;
- buf->decoder_info[1] = le2me_32(this->header.tta.samplerate);
- buf->decoder_info[2] = le2me_16(this->header.tta.bits_per_sample);
- buf->decoder_info[3] = le2me_16(this->header.tta.channels);
+ /* create header */
+ wave.cbSize = total_size - sizeof(xine_waveformatex);
- buf->size = sizeof(xine_waveformatex) + sizeof(this->header) + sizeof(uint32_t)*this->totalframes;
- memcpy(buf->content+sizeof(xine_waveformatex), this->header.buffer, sizeof(this->header));
- memcpy(buf->content+sizeof(xine_waveformatex)+sizeof(this->header), this->seektable, sizeof(uint32_t)*this->totalframes);
+ memcpy(header, &wave, sizeof(wave));
+ memcpy(header+sizeof(xine_waveformatex), this->header.buffer, sizeof(this->header));
+ memcpy(header+sizeof(xine_waveformatex)+sizeof(this->header), this->seektable, sizeof(uint32_t)*this->totalframes);
- wave.cbSize = buf->size - sizeof(xine_waveformatex);
- memcpy(buf->content, &wave, sizeof(wave));
-
- this->audio_fifo->put (this->audio_fifo, buf);
+ /* send init info to decoders */
+ if (this->audio_fifo) {
+ uint32_t bytes_left = total_size;
+
+ /* We are sending the seektable as well, and this may be larger than
+ buf->max_size */
+ while (bytes_left) {
+ buf = this->audio_fifo->buffer_pool_alloc (this->audio_fifo);
+ buf->decoder_flags = BUF_FLAG_HEADER|BUF_FLAG_STDHEADER;
+ buf->type = BUF_AUDIO_TTA;
+
+ /* Copy min(bytes_left, max_size) bytes */
+ buf->size = bytes_left < buf->max_size ? bytes_left : buf->max_size;
+ memcpy(buf->content, header+(total_size-bytes_left), buf->size);
+
+ bytes_left -= buf->size;
+
+ /* The decoder information only needs the decoder information on the last
+ buffer element. */
+ if (!bytes_left) {
+ buf->decoder_flags |= BUF_FLAG_FRAME_END;
+ buf->decoder_info[0] = 0;
+ buf->decoder_info[1] = le2me_32(this->header.tta.samplerate);
+ buf->decoder_info[2] = le2me_16(this->header.tta.bits_per_sample);
+ buf->decoder_info[3] = le2me_16(this->header.tta.channels);
+ }
+ this->audio_fifo->put (this->audio_fifo, buf);
+ }
}
+ free(header);
}
static int demux_tta_seek (demux_plugin_t *this_gen,