30#include <libavcodec/avcodec.h>
55 LOGFATAL(
"audiocodec: %s: can't allocate audio decoder frame buffer", __FUNCTION__);
88 if (codecId == AV_CODEC_ID_AC3) {
89 if (!(codec = avcodec_find_decoder_by_name(
"ac3_fixed"))) {
90 LOGFATAL(
"audiocodec: %s: codec ac3_fixed ID %#06x not found", __FUNCTION__, codecId);
92 }
else if (codecId == AV_CODEC_ID_AAC) {
93 if (!(codec = avcodec_find_decoder_by_name(
"aac_fixed"))) {
94 LOGFATAL(
"audiocodec: %s: codec aac_fixed ID %#06x not found", __FUNCTION__, codecId);
97 if (!(codec = avcodec_find_decoder(codecId))) {
98 LOGFATAL(
"audiocodec: %s: codec %s ID %#06x not found", __FUNCTION__,
99 avcodec_get_name(codecId), codecId);
103 if (!(
m_pAudioCtx = avcodec_alloc_context3(codec)))
104 LOGFATAL(
"audiocodec: %s: can't allocate audio codec context", __FUNCTION__);
108 if (par && ((avcodec_parameters_to_context(
m_pAudioCtx, par)) < 0))
109 LOGERROR(
"audiocodec: %s: insert parameters to context failed!", __FUNCTION__);
112 LOGFATAL(
"audiocodec: %s: can't open audio codec", __FUNCTION__);
168 if (spdifSize < avpkt->size + 8) {
169 LOGERROR(
"audiocodec: %s: too much data for spdif buffer!", __FUNCTION__);
174 int bitstreamMode = avpkt->data[5] & 0x07;
178 spdif[3] = htole16(avpkt->size * 8);
180 swab(avpkt->data, spdif + 4, avpkt->size);
181 memset(spdif + 4 + avpkt->size / 2, 0, spdifSize - 8 - avpkt->size);
198 if (spdifSize < m_spdifIndex + avpkt->size + 8) {
199 LOGERROR(
"audiocodec: %s: too much data for spdif buffer!", __FUNCTION__);
204 int fscod = (avpkt->data[4] >> 6) & 0x3;
206 int fscod2 = (avpkt->data[4] >> 4) & 0x3;
207 static const uint8_t eac3_repeat[4] = { 6, 3, 2, 1 };
208 repeat = eac3_repeat[fscod2];
216 swab(avpkt->data, spdif + 4 +
m_spdifIndex, avpkt->size);
243 nbs = (uint8_t)((avpkt->data[4] & 0x01) << 6) |
244 ((avpkt->data[5] >> 2) & 0x3f);
266 burstSz = (nbs + 1) * 32 * 2 + 2;
271 if (burstSz < avpkt->size + 8) {
272 LOGERROR(
"audiocodec: %s: too much data for spdif buffer!", __FUNCTION__);
277 spdif[2] = htole16(bsid);
278 spdif[3] = htole16(avpkt->size * 8);
282 swab(avpkt->data, spdif + 4, avpkt->size);
283 memset(spdif + 4 + avpkt->size, 0, burstSz - 8 - avpkt->size);
302 int isPassthrough = 0;
305 LOGDEBUG2(
L_SOUND,
"audiocodec: %s: format change %s %dHz *%d channels%s%s%s%s%s%d", __FUNCTION__,
343 LOGERROR(
"audiocodec: %s: format change update error", __FUNCTION__);
362 av_frame_unref(frame);
367 LOGERROR(
"audiocodec: %s: avcodec_send_packet error: %s", __FUNCTION__, av_err2str(retSend));
369 retRec = avcodec_receive_frame(
m_pAudioCtx, frame);
372 if (retRec != AVERROR(EAGAIN))
373 LOGERROR(
"audiocodec: %s: avcodec_receive_frame error: %s", __FUNCTION__, av_err2str(retRec));
377 av_frame_unref(frame);
386 (int64_t)(frame->nb_samples / av_q2d(
m_pAudioCtx->pkt_timebase) / frame->sample_rate);
397 LOGERROR(
"audiocodec: %s: unsupported format!", __FUNCTION__);
398 av_frame_unref(frame);
403 av_frame_unref(frame);
410 }
while (retSend == AVERROR(EAGAIN));
Audio and alsa module header file.
int DecodePassthrough(const AVPacket *, AVFrame *)
Passthrough audio data.
uint16_t m_spdifOutput[MAX_FRAME_SIZE *2]
SPDIF output buffer.
int UpdateFormat(void)
Handle audio format changes.
AVCodecContext * m_pAudioCtx
ffmpeg audio codec context
virtual ~cAudioDecoder(void)
Audio decoder class destructor.
int m_currentHwSampleRate
current hw sample rate
void FlushBuffers(void)
Flush the audio decoder.
int m_currentHwNumChannels
current number of hw channels
void Decode(const AVPacket *)
Decode an audio packet.
AVFrame * m_pFrame
decoded ffmpeg audio frame
int m_spdifIndex
index into SPDIF output buffer
int m_passthroughMask
passthrough mask to be set
AVCodecID m_codecId
current codec id
int m_currentPassthrough
current passthrough mask
cAudioDecoder(cSoftHdAudio *)
Audio decoder class constructor.
int m_spdifRepeatCount
SPDIF repeat counter.
int64_t m_lastPts
last seen PTS
int m_currentSampleRate
current sample rate
cSoftHdAudio * m_pAudio
audio module
void SetPassthrough(int)
Set audio pass-through mask.
int m_currentNumChannels
current number of channels
void Open(AVCodecID, AVCodecParameters *=nullptr, AVRational={ .num=1,.den=90000 })
Open and initiate the audio decoder.
void Close(void)
Close the audio decoder.
cSoftHdAudio - Audio class
void Filter(AVFrame *, AVCodecContext *)
Send audio frame to filter and enqueue it.
int Setup(AVCodecContext *, int, int, int)
Setup alsa.
void Enqueue(uint16_t *, int, AVFrame *)
Send audio data to ringbuffer.
int GetPassthrough(void) const
void SetTimebase(AVRational *timebase)
Audio decoder header file.
#define IEC61937_PREAMBLE2
#define CODEC_PCM
bits used for the passthrough mask
#define CODEC_EAC3
E-AC-3 bit mask.
@ IEC61937_DTS3
DTS type III (2048 samples)
@ IEC61937_DTS2
DTS type II (1024 samples)
@ IEC61937_EAC3
E-AC-3 data.
@ IEC61937_DTS1
DTS type I (512 samples)
#define DTS_PREAMBLE_16BE_1
#define DTS_PREAMBLE_16BE_2
#define IEC61937_PREAMBLE1
#define CODEC_AC3
AC-3 bit mask.
#define DTS1_FRAME_SIZE
Codec frame sizes.
#define CODEC_DTS
DTS bit mask.
Logger class header file.
#define LOGFATAL
Logger macros.
Misc function header file.