patch by Anuradha Suraparaju, anuradha rd.bbc.co uk Originally committed as revision 14734 to svn://svn.ffmpeg.org/ffmpeg/trunktags/v0.5
@@ -482,6 +482,7 @@ static void pmt_cb(MpegTSFilter *filter, const uint8_t *section, int section_len | |||||
int comp_page = 0, anc_page = 0; /* initialize to kill warnings */ | int comp_page = 0, anc_page = 0; /* initialize to kill warnings */ | ||||
char language[4] = {0}; /* initialize to kill warnings */ | char language[4] = {0}; /* initialize to kill warnings */ | ||||
int has_hdmv_descr = 0; | int has_hdmv_descr = 0; | ||||
int has_dirac_descr = 0; | |||||
#ifdef DEBUG_SI | #ifdef DEBUG_SI | ||||
av_log(ts->stream, AV_LOG_DEBUG, "PMT: len %i\n", section_len); | av_log(ts->stream, AV_LOG_DEBUG, "PMT: len %i\n", section_len); | ||||
@@ -589,6 +590,18 @@ static void pmt_cb(MpegTSFilter *filter, const uint8_t *section, int section_len | |||||
language[2] = get8(&p, desc_end); | language[2] = get8(&p, desc_end); | ||||
language[3] = 0; | language[3] = 0; | ||||
break; | break; | ||||
case REGISTRATION_DESCRIPTOR: /*MPEG-2 Registration descriptor */ | |||||
{ | |||||
uint8_t bytes[4]; | |||||
bytes[0] = get8(&p, desc_end); | |||||
bytes[1] = get8(&p, desc_end); | |||||
bytes[2] = get8(&p, desc_end); | |||||
bytes[3] = get8(&p, desc_end); | |||||
if(bytes[0] == 'd' && bytes[1] == 'r' && | |||||
bytes[2] == 'a' && bytes[3] == 'c') | |||||
has_dirac_descr = 1; | |||||
break; | |||||
} | |||||
default: | default: | ||||
break; | break; | ||||
} | } | ||||
@@ -610,12 +623,14 @@ static void pmt_cb(MpegTSFilter *filter, const uint8_t *section, int section_len | |||||
case STREAM_TYPE_VIDEO_MPEG4: | case STREAM_TYPE_VIDEO_MPEG4: | ||||
case STREAM_TYPE_VIDEO_H264: | case STREAM_TYPE_VIDEO_H264: | ||||
case STREAM_TYPE_VIDEO_VC1: | case STREAM_TYPE_VIDEO_VC1: | ||||
case STREAM_TYPE_VIDEO_DIRAC: | |||||
case STREAM_TYPE_AUDIO_AAC: | case STREAM_TYPE_AUDIO_AAC: | ||||
case STREAM_TYPE_AUDIO_AC3: | case STREAM_TYPE_AUDIO_AC3: | ||||
case STREAM_TYPE_AUDIO_DTS: | case STREAM_TYPE_AUDIO_DTS: | ||||
case STREAM_TYPE_AUDIO_HDMV_DTS: | case STREAM_TYPE_AUDIO_HDMV_DTS: | ||||
case STREAM_TYPE_SUBTITLE_DVB: | case STREAM_TYPE_SUBTITLE_DVB: | ||||
if(stream_type == STREAM_TYPE_AUDIO_HDMV_DTS && !has_hdmv_descr) | |||||
if((stream_type == STREAM_TYPE_AUDIO_HDMV_DTS && !has_hdmv_descr) | |||||
|| (stream_type == STREAM_TYPE_VIDEO_DIRAC && !has_dirac_descr)) | |||||
break; | break; | ||||
if(ts->pids[pid] && ts->pids[pid]->type == MPEGTS_PES){ | if(ts->pids[pid] && ts->pids[pid]->type == MPEGTS_PES){ | ||||
pes= ts->pids[pid]->u.pes_filter.opaque; | pes= ts->pids[pid]->u.pes_filter.opaque; | ||||
@@ -944,6 +959,10 @@ static AVStream* new_pes_av_stream(PESContext *pes, uint32_t code) | |||||
codec_type = CODEC_TYPE_VIDEO; | codec_type = CODEC_TYPE_VIDEO; | ||||
codec_id = CODEC_ID_VC1; | codec_id = CODEC_ID_VC1; | ||||
break; | break; | ||||
case STREAM_TYPE_VIDEO_DIRAC: | |||||
codec_type = CODEC_TYPE_VIDEO; | |||||
codec_id = CODEC_ID_DIRAC; | |||||
break; | |||||
case STREAM_TYPE_AUDIO_AAC: | case STREAM_TYPE_AUDIO_AAC: | ||||
codec_type = CODEC_TYPE_AUDIO; | codec_type = CODEC_TYPE_AUDIO; | ||||
codec_id = CODEC_ID_AAC; | codec_id = CODEC_ID_AAC; | ||||
@@ -52,6 +52,7 @@ | |||||
#define STREAM_TYPE_VIDEO_MPEG4 0x10 | #define STREAM_TYPE_VIDEO_MPEG4 0x10 | ||||
#define STREAM_TYPE_VIDEO_H264 0x1b | #define STREAM_TYPE_VIDEO_H264 0x1b | ||||
#define STREAM_TYPE_VIDEO_VC1 0xea | #define STREAM_TYPE_VIDEO_VC1 0xea | ||||
#define STREAM_TYPE_VIDEO_DIRAC 0xd1 | |||||
#define STREAM_TYPE_AUDIO_AC3 0x81 | #define STREAM_TYPE_AUDIO_AC3 0x81 | ||||
#define STREAM_TYPE_AUDIO_DTS 0x8a | #define STREAM_TYPE_AUDIO_DTS 0x8a | ||||
@@ -220,6 +220,9 @@ static void mpegts_write_pmt(AVFormatContext *s, MpegTSService *service) | |||||
case CODEC_ID_H264: | case CODEC_ID_H264: | ||||
stream_type = STREAM_TYPE_VIDEO_H264; | stream_type = STREAM_TYPE_VIDEO_H264; | ||||
break; | break; | ||||
case CODEC_ID_DIRAC: | |||||
stream_type = STREAM_TYPE_VIDEO_DIRAC; | |||||
break; | |||||
case CODEC_ID_MP2: | case CODEC_ID_MP2: | ||||
case CODEC_ID_MP3: | case CODEC_ID_MP3: | ||||
stream_type = STREAM_TYPE_AUDIO_MPEG1; | stream_type = STREAM_TYPE_AUDIO_MPEG1; | ||||
@@ -267,6 +270,16 @@ static void mpegts_write_pmt(AVFormatContext *s, MpegTSService *service) | |||||
put16(&q, 1); /* ancillary page id */ | put16(&q, 1); /* ancillary page id */ | ||||
} | } | ||||
break; | break; | ||||
case CODEC_TYPE_VIDEO: | |||||
if (stream_type == STREAM_TYPE_VIDEO_DIRAC) { | |||||
*q++ = 0x05; /*MPEG-2 registration descriptor*/ | |||||
*q++ = 4; | |||||
*q++ = 'd'; | |||||
*q++ = 'r'; | |||||
*q++ = 'a'; | |||||
*q++ = 'c'; | |||||
} | |||||
break; | |||||
} | } | ||||
val = 0xf000 | (q - desc_length_ptr - 2); | val = 0xf000 | (q - desc_length_ptr - 2); | ||||
@@ -527,13 +540,17 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st, | |||||
*q++ = 0; | *q++ = 0; | ||||
} | } | ||||
if (is_start) { | if (is_start) { | ||||
int pes_extension = 0; | |||||
/* write PES header */ | /* write PES header */ | ||||
*q++ = 0x00; | *q++ = 0x00; | ||||
*q++ = 0x00; | *q++ = 0x00; | ||||
*q++ = 0x01; | *q++ = 0x01; | ||||
private_code = 0; | private_code = 0; | ||||
if (st->codec->codec_type == CODEC_TYPE_VIDEO) { | if (st->codec->codec_type == CODEC_TYPE_VIDEO) { | ||||
*q++ = 0xe0; | |||||
if (st->codec->codec_id == CODEC_ID_DIRAC) { | |||||
*q++ = 0xfd; | |||||
} else | |||||
*q++ = 0xe0; | |||||
} else if (st->codec->codec_type == CODEC_TYPE_AUDIO && | } else if (st->codec->codec_type == CODEC_TYPE_AUDIO && | ||||
(st->codec->codec_id == CODEC_ID_MP2 || | (st->codec->codec_id == CODEC_ID_MP2 || | ||||
st->codec->codec_id == CODEC_ID_MP3)) { | st->codec->codec_id == CODEC_ID_MP3)) { | ||||
@@ -554,6 +571,19 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st, | |||||
header_len += 5; | header_len += 5; | ||||
flags |= 0x40; | flags |= 0x40; | ||||
} | } | ||||
if (st->codec->codec_type == CODEC_TYPE_VIDEO && | |||||
st->codec->codec_id == CODEC_ID_DIRAC) { | |||||
/* set PES_extension_flag */ | |||||
pes_extension = 1; | |||||
flags |= 0x01; | |||||
/* | |||||
* One byte for PES2 extension flag + | |||||
* one byte for extension length + | |||||
* one byte for extension id | |||||
*/ | |||||
header_len += 3; | |||||
} | |||||
len = payload_size + header_len + 3; | len = payload_size + header_len + 3; | ||||
if (private_code != 0) | if (private_code != 0) | ||||
len++; | len++; | ||||
@@ -574,6 +604,16 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st, | |||||
write_pts(q, 1, dts); | write_pts(q, 1, dts); | ||||
q += 5; | q += 5; | ||||
} | } | ||||
if (pes_extension && st->codec->codec_id == CODEC_ID_DIRAC) { | |||||
flags = 0x01; /* set PES_extension_flag_2 */ | |||||
*q++ = flags; | |||||
*q++ = 0x80 | 0x01; /* marker bit + extension length */ | |||||
/* | |||||
* Set the stream id extension flag bit to 0 and | |||||
* write the extended stream id | |||||
*/ | |||||
*q++ = 0x00 | 0x60; | |||||
} | |||||
if (private_code != 0) | if (private_code != 0) | ||||
*q++ = private_code; | *q++ = private_code; | ||||
is_start = 0; | is_start = 0; | ||||