|
|
|
@ -114,55 +114,6 @@ static VLC vlc_spectral[11]; |
|
|
|
|
|
|
|
|
|
static const char overread_err[] = "Input buffer exhausted before END element found\n"; |
|
|
|
|
|
|
|
|
|
static ChannelElement *get_che(AACContext *ac, int type, int elem_id) |
|
|
|
|
{ |
|
|
|
|
// For PCE based channel configurations map the channels solely based on tags.
|
|
|
|
|
if (!ac->m4ac.chan_config) { |
|
|
|
|
return ac->tag_che_map[type][elem_id]; |
|
|
|
|
} |
|
|
|
|
// For indexed channel configurations map the channels solely based on position.
|
|
|
|
|
switch (ac->m4ac.chan_config) { |
|
|
|
|
case 7: |
|
|
|
|
if (ac->tags_mapped == 3 && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][2]; |
|
|
|
|
} |
|
|
|
|
case 6: |
|
|
|
|
/* Some streams incorrectly code 5.1 audio as SCE[0] CPE[0] CPE[1] SCE[1]
|
|
|
|
|
instead of SCE[0] CPE[0] CPE[1] LFE[0]. If we seem to have |
|
|
|
|
encountered such a stream, transfer the LFE[0] element to the SCE[1]'s mapping */ |
|
|
|
|
if (ac->tags_mapped == tags_per_config[ac->m4ac.chan_config] - 1 && (type == TYPE_LFE || type == TYPE_SCE)) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[type][elem_id] = ac->che[TYPE_LFE][0]; |
|
|
|
|
} |
|
|
|
|
case 5: |
|
|
|
|
if (ac->tags_mapped == 2 && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][1]; |
|
|
|
|
} |
|
|
|
|
case 4: |
|
|
|
|
if (ac->tags_mapped == 2 && ac->m4ac.chan_config == 4 && type == TYPE_SCE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_SCE][elem_id] = ac->che[TYPE_SCE][1]; |
|
|
|
|
} |
|
|
|
|
case 3: |
|
|
|
|
case 2: |
|
|
|
|
if (ac->tags_mapped == (ac->m4ac.chan_config != 2) && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][0]; |
|
|
|
|
} else if (ac->m4ac.chan_config == 2) { |
|
|
|
|
return NULL; |
|
|
|
|
} |
|
|
|
|
case 1: |
|
|
|
|
if (!ac->tags_mapped && type == TYPE_SCE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_SCE][elem_id] = ac->che[TYPE_SCE][0]; |
|
|
|
|
} |
|
|
|
|
default: |
|
|
|
|
return NULL; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static int count_channels(uint8_t (*layout)[3], int tags) |
|
|
|
|
{ |
|
|
|
|
int i, sum = 0; |
|
|
|
@ -437,6 +388,76 @@ static av_cold int output_configure(AACContext *ac, |
|
|
|
|
return 0; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Set up channel positions based on a default channel configuration |
|
|
|
|
* as specified in table 1.17. |
|
|
|
|
* |
|
|
|
|
* @return Returns error status. 0 - OK, !0 - error |
|
|
|
|
*/ |
|
|
|
|
static av_cold int set_default_channel_config(AVCodecContext *avctx, |
|
|
|
|
uint8_t (*layout_map)[3], |
|
|
|
|
int *tags, |
|
|
|
|
int channel_config) |
|
|
|
|
{ |
|
|
|
|
if (channel_config < 1 || channel_config > 7) { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, "invalid default channel configuration (%d)\n", |
|
|
|
|
channel_config); |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
*tags = tags_per_config[channel_config]; |
|
|
|
|
memcpy(layout_map, aac_channel_layout_map[channel_config-1], *tags * sizeof(*layout_map)); |
|
|
|
|
return 0; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static ChannelElement *get_che(AACContext *ac, int type, int elem_id) |
|
|
|
|
{ |
|
|
|
|
// For PCE based channel configurations map the channels solely based on tags.
|
|
|
|
|
if (!ac->m4ac.chan_config) { |
|
|
|
|
return ac->tag_che_map[type][elem_id]; |
|
|
|
|
} |
|
|
|
|
// For indexed channel configurations map the channels solely based on position.
|
|
|
|
|
switch (ac->m4ac.chan_config) { |
|
|
|
|
case 7: |
|
|
|
|
if (ac->tags_mapped == 3 && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][2]; |
|
|
|
|
} |
|
|
|
|
case 6: |
|
|
|
|
/* Some streams incorrectly code 5.1 audio as SCE[0] CPE[0] CPE[1] SCE[1]
|
|
|
|
|
instead of SCE[0] CPE[0] CPE[1] LFE[0]. If we seem to have |
|
|
|
|
encountered such a stream, transfer the LFE[0] element to the SCE[1]'s mapping */ |
|
|
|
|
if (ac->tags_mapped == tags_per_config[ac->m4ac.chan_config] - 1 && (type == TYPE_LFE || type == TYPE_SCE)) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[type][elem_id] = ac->che[TYPE_LFE][0]; |
|
|
|
|
} |
|
|
|
|
case 5: |
|
|
|
|
if (ac->tags_mapped == 2 && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][1]; |
|
|
|
|
} |
|
|
|
|
case 4: |
|
|
|
|
if (ac->tags_mapped == 2 && ac->m4ac.chan_config == 4 && type == TYPE_SCE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_SCE][elem_id] = ac->che[TYPE_SCE][1]; |
|
|
|
|
} |
|
|
|
|
case 3: |
|
|
|
|
case 2: |
|
|
|
|
if (ac->tags_mapped == (ac->m4ac.chan_config != 2) && type == TYPE_CPE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_CPE][elem_id] = ac->che[TYPE_CPE][0]; |
|
|
|
|
} else if (ac->m4ac.chan_config == 2) { |
|
|
|
|
return NULL; |
|
|
|
|
} |
|
|
|
|
case 1: |
|
|
|
|
if (!ac->tags_mapped && type == TYPE_SCE) { |
|
|
|
|
ac->tags_mapped++; |
|
|
|
|
return ac->tag_che_map[TYPE_SCE][elem_id] = ac->che[TYPE_SCE][0]; |
|
|
|
|
} |
|
|
|
|
default: |
|
|
|
|
return NULL; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Decode an array of 4 bit element IDs, optionally interleaved with a stereo/mono switching bit. |
|
|
|
|
* |
|
|
|
@ -529,27 +550,6 @@ static int decode_pce(AVCodecContext *avctx, MPEG4AudioConfig *m4ac, |
|
|
|
|
return tags; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Set up channel positions based on a default channel configuration |
|
|
|
|
* as specified in table 1.17. |
|
|
|
|
* |
|
|
|
|
* @return Returns error status. 0 - OK, !0 - error |
|
|
|
|
*/ |
|
|
|
|
static av_cold int set_default_channel_config(AVCodecContext *avctx, |
|
|
|
|
uint8_t (*layout_map)[3], |
|
|
|
|
int *tags, |
|
|
|
|
int channel_config) |
|
|
|
|
{ |
|
|
|
|
if (channel_config < 1 || channel_config > 7) { |
|
|
|
|
av_log(avctx, AV_LOG_ERROR, "invalid default channel configuration (%d)\n", |
|
|
|
|
channel_config); |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
*tags = tags_per_config[channel_config]; |
|
|
|
|
memcpy(layout_map, aac_channel_layout_map[channel_config-1], *tags * sizeof(*layout_map)); |
|
|
|
|
return 0; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Decode GA "General Audio" specific configuration; reference: table 4.1. |
|
|
|
|
* |
|
|
|
|