rtpdec: Clean up FMTP parsing code in AMR RTP depacketizer

Patch by Josh Allmann, joshua dot allmann at gmail

Originally committed as revision 23861 to svn://svn.ffmpeg.org/ffmpeg/trunk
oldabi
Josh Allmann 15 years ago committed by Martin Storsjö
parent af1308f024
commit a494295197
  1. 80
      libavformat/rtpdec_amr.c

@ -30,6 +30,26 @@ static const uint8_t frame_sizes_wb[16] = {
17, 23, 32, 36, 40, 46, 50, 58, 60, 5, 5, 0, 0, 0, 0, 0 17, 23, 32, 36, 40, 46, 50, 58, 60, 5, 5, 0, 0, 0, 0, 0
}; };
struct PayloadContext {
int octet_align;
int crc;
int interleaving;
int channels;
};
static PayloadContext *amr_new_context(void)
{
PayloadContext *data = av_mallocz(sizeof(PayloadContext));
if(!data) return data;
data->channels = 1;
return data;
}
static void amr_free_context(PayloadContext *data)
{
av_free(data);
}
static int amr_handle_packet(AVFormatContext *ctx, static int amr_handle_packet(AVFormatContext *ctx,
PayloadContext *data, PayloadContext *data,
AVStream *st, AVStream *st,
@ -120,50 +140,48 @@ static int amr_handle_packet(AVFormatContext *ctx,
return 0; return 0;
} }
static int amr_parse_sdp_line(AVFormatContext *s, int st_index, static int amr_parse_fmtp(AVStream *stream, PayloadContext *data,
PayloadContext *data, const char *line) char *attr, char *value)
{ {
const char *p;
char attr[25], value[25];
/* Parse an fmtp line this one:
* a=fmtp:97 octet-align=1; interleaving=0
* That is, a normal fmtp: line followed by semicolon & space
* separated key/value pairs.
*/
if (av_strstart(line, "fmtp:", &p)) {
int octet_align = 0;
int crc = 0;
int interleaving = 0;
int channels = 1;
while (*p && *p == ' ') p++; /* strip spaces */
while (*p && *p != ' ') p++; /* eat protocol identifier */
while (*p && *p == ' ') p++; /* strip trailing spaces */
while (ff_rtsp_next_attr_and_value(&p, attr, sizeof(attr), value, sizeof(value))) {
/* Some AMR SDP configurations contain "octet-align", without /* Some AMR SDP configurations contain "octet-align", without
* the trailing =1. Therefore, if the value is empty, * the trailing =1. Therefore, if the value is empty,
* interpret it as "1". * interpret it as "1".
*/ */
if (!strcmp(value, "")) { if (!strcmp(value, "")) {
av_log(s, AV_LOG_WARNING, "AMR fmtp attribute %s had " av_log(NULL, AV_LOG_WARNING, "AMR fmtp attribute %s had "
"nonstandard empty value\n", attr); "nonstandard empty value\n", attr);
strcpy(value, "1"); strcpy(value, "1");
} }
if (!strcmp(attr, "octet-align")) if (!strcmp(attr, "octet-align"))
octet_align = atoi(value); data->octet_align = atoi(value);
else if (!strcmp(attr, "crc")) else if (!strcmp(attr, "crc"))
crc = atoi(value); data->crc = atoi(value);
else if (!strcmp(attr, "interleaving")) else if (!strcmp(attr, "interleaving"))
interleaving = atoi(value); data->interleaving = atoi(value);
else if (!strcmp(attr, "channels")) else if (!strcmp(attr, "channels"))
channels = atoi(value); data->channels = atoi(value);
} return 0;
if (!octet_align || crc || interleaving || channels != 1) { }
static int amr_parse_sdp_line(AVFormatContext *s, int st_index,
PayloadContext *data, const char *line)
{
const char *p;
int ret;
/* Parse an fmtp line this one:
* a=fmtp:97 octet-align=1; interleaving=0
* That is, a normal fmtp: line followed by semicolon & space
* separated key/value pairs.
*/
if (av_strstart(line, "fmtp:", &p)) {
ret = ff_parse_fmtp(s->streams[st_index], data, p, amr_parse_fmtp);
if (!data->octet_align || data->crc ||
data->interleaving || data->channels != 1) {
av_log(s, AV_LOG_ERROR, "Unsupported RTP/AMR configuration!\n"); av_log(s, AV_LOG_ERROR, "Unsupported RTP/AMR configuration!\n");
return -1; return -1;
} }
return ret;
} }
return 0; return 0;
} }
@ -173,6 +191,8 @@ RTPDynamicProtocolHandler ff_amr_nb_dynamic_handler = {
.codec_type = AVMEDIA_TYPE_AUDIO, .codec_type = AVMEDIA_TYPE_AUDIO,
.codec_id = CODEC_ID_AMR_NB, .codec_id = CODEC_ID_AMR_NB,
.parse_sdp_a_line = amr_parse_sdp_line, .parse_sdp_a_line = amr_parse_sdp_line,
.open = amr_new_context,
.close = amr_free_context,
.parse_packet = amr_handle_packet, .parse_packet = amr_handle_packet,
}; };
@ -181,6 +201,8 @@ RTPDynamicProtocolHandler ff_amr_wb_dynamic_handler = {
.codec_type = AVMEDIA_TYPE_AUDIO, .codec_type = AVMEDIA_TYPE_AUDIO,
.codec_id = CODEC_ID_AMR_WB, .codec_id = CODEC_ID_AMR_WB,
.parse_sdp_a_line = amr_parse_sdp_line, .parse_sdp_a_line = amr_parse_sdp_line,
.open = amr_new_context,
.close = amr_free_context,
.parse_packet = amr_handle_packet, .parse_packet = amr_handle_packet,
}; };

Loading…
Cancel
Save