Exemple #1
0
static gint
xmms_opus_read (xmms_xform_t *xform, gpointer buf, gint len,
                  xmms_error_t *err)
{
	gint ret = 0;
	gint c;
	xmms_opus_data_t *data;

	g_return_val_if_fail (xform, -1);

	data = xmms_xform_private_data_get (xform);
	g_return_val_if_fail (data, -1);

	ret = xmms_opus_op_read (data->opusfile, (gchar *) buf, len,
	                           G_BYTE_ORDER == G_BIG_ENDIAN,
	                           xmms_sample_size_get (XMMS_SAMPLE_FORMAT_S16),
	                           1, &c);

	if (ret < 0) {
		return -1;
	}

	if (ret && c != data->current) {
		xmms_opus_read_metadata (xform, data);
		data->current = c;
	}

	return ret;
}
Exemple #2
0
/**
 * Get number of bytes used for one sample length worth of music.
 *
 * That is, (size of one sample) * channels.
 */
gint
xmms_sample_frame_size_get (const xmms_stream_type_t *st)
{
	gint format, channels;
	format = xmms_stream_type_get_int (st, XMMS_STREAM_TYPE_FMT_FORMAT);
	channels = xmms_stream_type_get_int (st, XMMS_STREAM_TYPE_FMT_CHANNELS);
	return xmms_sample_size_get (format) * channels;
}
Exemple #3
0
static gint
xmms_mad_read (xmms_xform_t *xform, gpointer buf, gint len, xmms_error_t *err)
{
	xmms_mad_data_t *data;
	xmms_samples16_t *out = (xmms_samples16_t *)buf;
	gint ret;
	gint j;
	gint read = 0;

	data = xmms_xform_private_data_get (xform);

	j = 0;

	while (read < len) {

		/* use already synthetized frame first */
		if (data->synthpos < data->synth.pcm.length) {
			out[j++] = scale_linear (data->synth.pcm.samples[0][data->synthpos]);
			if (data->channels == 2) {
				out[j++] = scale_linear (data->synth.pcm.samples[1][data->synthpos]);
				read += 2 * xmms_sample_size_get (XMMS_SAMPLE_FORMAT_S16);
			} else {
				read += xmms_sample_size_get (XMMS_SAMPLE_FORMAT_S16);
			}
			data->synthpos++;
			continue;
		}

		/* then try to decode another frame */
		if (mad_frame_decode (&data->frame, &data->stream) != -1) {

			/* mad_synthpop_frame - go Depeche! */
			mad_synth_frame (&data->synth, &data->frame);

			if (data->frames_to_skip) {
				data->frames_to_skip--;
				data->synthpos = 0x7fffffff;
			} else if (data->samples_to_skip) {
				if (data->samples_to_skip > data->synth.pcm.length) {
					data->synthpos = 0x7fffffff;
					data->samples_to_skip -= data->synth.pcm.length;
				} else {
					data->synthpos = data->samples_to_skip;
					data->samples_to_skip = 0;
				}
			} else {
				if (data->samples_to_play == 0) {
					return read;
				} else if (data->samples_to_play > 0) {
					if (data->synth.pcm.length > data->samples_to_play) {
						data->synth.pcm.length = data->samples_to_play;
					}
					data->samples_to_play -= data->synth.pcm.length;
				}
				data->synthpos = 0;
			}
			continue;
		}


		/* if there is no frame to decode stream more data */
		if (data->stream.next_frame) {
			guchar *buffer = data->buffer;
			const guchar *nf = data->stream.next_frame;
			memmove (data->buffer, data->stream.next_frame,
			         data->buffer_length = (&buffer[data->buffer_length] - nf));
		}

		ret = xmms_xform_read (xform,
		                       (gchar *)data->buffer + data->buffer_length,
		                       4096 - data->buffer_length,
		                       err);

		if (ret <= 0) {
			return ret;
		}

		data->buffer_length += ret;
		mad_stream_buffer (&data->stream, data->buffer, data->buffer_length);
	}

	return read;
}
Exemple #4
0
static gint
xmms_faad_read (xmms_xform_t *xform, xmms_sample_t *buf, gint len, xmms_error_t *err)
{
	xmms_faad_data_t *data;
	xmms_error_t error;

	NeAACDecFrameInfo frameInfo;
	gpointer sample_buffer;
	guint size, bytes_read = 0;

	data = xmms_xform_private_data_get (xform);
	g_return_val_if_fail (data, -1);

	size = MIN (data->outbuf->len, len);
	while (size == 0) {
		gboolean need_read;

		/* MP4 demuxer always gives full packets so we need different handling */
		if (data->filetype == FAAD_TYPE_MP4)
			need_read = (data->buffer_length == 0);
		else
			need_read = (data->buffer_length < data->buffer_size);

		if (need_read) {
			bytes_read = xmms_xform_read (xform,
			                              (gchar *) data->buffer + data->buffer_length,
			                              data->buffer_size - data->buffer_length,
			                              &error);

			if (bytes_read <= 0 && data->buffer_length == 0) {
				XMMS_DBG ("EOF");
				return 0;
			}

			data->buffer_length += bytes_read;
		}

		sample_buffer = NeAACDecDecode (data->decoder, &frameInfo, data->buffer,
		                               data->buffer_length);

		g_memmove (data->buffer, data->buffer + frameInfo.bytesconsumed,
		           data->buffer_length - frameInfo.bytesconsumed);
		data->buffer_length -= frameInfo.bytesconsumed;
		bytes_read = frameInfo.samples * xmms_sample_size_get (data->sampleformat);

		if (bytes_read > 0 && frameInfo.error == 0) {
			gint32 temp, toskip = 0;

			if (data->samplerate != frameInfo.samplerate ||
			    data->channels != frameInfo.channels) {
				/* We should inform output to change parameters somehow */
				XMMS_DBG ("Output format changed in the middle of a read!");
				data->samplerate = frameInfo.samplerate;
				data->channels = frameInfo.channels;
			}

			if (xmms_xform_auxdata_get_int (xform, "frame_offset", &temp)) {
				toskip = (temp * frameInfo.channels *
				          xmms_sample_size_get (data->sampleformat));
			}

			if (xmms_xform_auxdata_get_int (xform, "frame_duration", &temp)) {
				bytes_read = (temp * frameInfo.channels *
				              xmms_sample_size_get (data->sampleformat));
			}

			g_string_append_len (data->outbuf, sample_buffer + toskip,
			                     bytes_read - toskip);
		} else if (frameInfo.error > 0) {
			XMMS_DBG ("ERROR %d in faad decoding: %s", frameInfo.error,
			          NeAACDecGetErrorMessage (frameInfo.error));
			return -1;
		}

		size = MIN (data->outbuf->len, len);
	}

	memcpy (buf, data->outbuf->str, size);
	g_string_erase (data->outbuf, 0, size);
	return size;
}