X-Git-Url: http://git.ffmpeg.org/gitweb/ffmpeg.git/blobdiff_plain/2912e87a6c9264d556734e2bf94a99c64cf9b102..e90a6846c2c006fbebd00e1f2789f4a86fafacef:/libavdevice/jack_audio.c diff --git a/libavdevice/jack_audio.c b/libavdevice/jack_audio.c index 4af89bd..280f24d 100644 --- a/libavdevice/jack_audio.c +++ b/libavdevice/jack_audio.c @@ -26,9 +26,12 @@ #include "libavutil/log.h" #include "libavutil/fifo.h" +#include "libavutil/opt.h" +#include "libavutil/time.h" #include "libavcodec/avcodec.h" #include "libavformat/avformat.h" -#include "libavformat/timefilter.h" +#include "libavformat/internal.h" +#include "timefilter.h" /** * Size of the internal FIFO buffers as a number of audio packets @@ -36,6 +39,7 @@ #define FIFO_PACKETS_NUM 16 typedef struct { + AVClass *class; jack_client_t * client; int activated; sem_t packet_count; @@ -88,7 +92,13 @@ static int process_callback(jack_nframes_t nframes, void *arg) /* Copy and interleave audio data from the JACK buffer into the packet */ for (i = 0; i < self->nports; i++) { + #if HAVE_JACK_PORT_GET_LATENCY_RANGE + jack_latency_range_t range; + jack_port_get_latency_range(self->ports[i], JackCaptureLatency, &range); + latency += range.max; + #else latency += jack_port_get_total_latency(self->client, self->ports[i]); + #endif buffer = jack_port_get_buffer(self->ports[i], self->buffer_size); for (j = 0; j < self->buffer_size; j++) pkt_data[j * self->nports + i] = buffer[j]; @@ -136,7 +146,7 @@ static int supply_new_packets(JackData *self, AVFormatContext *context) return 0; } -static int start_jack(AVFormatContext *context, AVFormatParameters *params) +static int start_jack(AVFormatContext *context) { JackData *self = context->priv_data; jack_status_t status; @@ -153,7 +163,6 @@ static int start_jack(AVFormatContext *context, AVFormatParameters *params) sem_init(&self->packet_count, 0, 0); self->sample_rate = jack_get_sample_rate(self->client); - self->nports = params->channels; self->ports = av_malloc(self->nports * sizeof(*self->ports)); self->buffer_size = jack_get_buffer_size(self->client); @@ -219,19 +228,16 @@ static void stop_jack(JackData *self) ff_timefilter_destroy(self->timefilter); } -static int audio_read_header(AVFormatContext *context, AVFormatParameters *params) +static int audio_read_header(AVFormatContext *context) { JackData *self = context->priv_data; AVStream *stream; int test; - if (params->sample_rate <= 0 || params->channels <= 0) - return -1; - - if ((test = start_jack(context, params))) + if ((test = start_jack(context))) return test; - stream = av_new_stream(context, 0); + stream = avformat_new_stream(context, NULL); if (!stream) { stop_jack(self); return AVERROR(ENOMEM); @@ -239,14 +245,14 @@ static int audio_read_header(AVFormatContext *context, AVFormatParameters *param stream->codec->codec_type = AVMEDIA_TYPE_AUDIO; #if HAVE_BIGENDIAN - stream->codec->codec_id = CODEC_ID_PCM_F32BE; + stream->codec->codec_id = AV_CODEC_ID_PCM_F32BE; #else - stream->codec->codec_id = CODEC_ID_PCM_F32LE; + stream->codec->codec_id = AV_CODEC_ID_PCM_F32LE; #endif stream->codec->sample_rate = self->sample_rate; stream->codec->channels = self->nports; - av_set_pts_info(stream, 64, 1, 1000000); /* 64 bits pts in us */ + avpriv_set_pts_info(stream, 64, 1, 1000000); /* 64 bits pts in us */ return 0; } @@ -272,7 +278,7 @@ static int audio_read_packet(AVFormatContext *context, AVPacket *pkt) } } - /* Wait for a packet comming back from process_callback(), if one isn't available yet */ + /* Wait for a packet coming back from process_callback(), if one isn't available yet */ timeout.tv_sec = av_gettime() / 1000000 + 2; if (sem_timedwait(&self->packet_count, &timeout)) { if (errno == ETIMEDOUT) { @@ -314,13 +320,26 @@ static int audio_read_close(AVFormatContext *context) return 0; } +#define OFFSET(x) offsetof(JackData, x) +static const AVOption options[] = { + { "channels", "Number of audio channels.", OFFSET(nports), AV_OPT_TYPE_INT, { .i64 = 2 }, 1, INT_MAX, AV_OPT_FLAG_DECODING_PARAM }, + { NULL }, +}; + +static const AVClass jack_indev_class = { + .class_name = "JACK indev", + .item_name = av_default_item_name, + .option = options, + .version = LIBAVUTIL_VERSION_INT, +}; + AVInputFormat ff_jack_demuxer = { - "jack", - NULL_IF_CONFIG_SMALL("JACK Audio Connection Kit"), - sizeof(JackData), - NULL, - audio_read_header, - audio_read_packet, - audio_read_close, - .flags = AVFMT_NOFILE, + .name = "jack", + .long_name = NULL_IF_CONFIG_SMALL("JACK Audio Connection Kit"), + .priv_data_size = sizeof(JackData), + .read_header = audio_read_header, + .read_packet = audio_read_packet, + .read_close = audio_read_close, + .flags = AVFMT_NOFILE, + .priv_class = &jack_indev_class, };