static void pat_cb(void *opaque, const uint8_t *section, int section_len) { MpegTSContext *ts = opaque; SectionHeader h1, *h = &h1; const uint8_t *p, *p_end; int sid, pmt_pid; #ifdef DEBUG_SI printf("PAT:\n"); av_hex_dump(stdout, (uint8_t *)section, section_len); #endif p_end = section + section_len - 4; p = section; if (parse_section_header(h, &p, p_end) < 0) return; if (h->tid != PAT_TID) return; for(;;) { sid = get16(&p, p_end); if (sid < 0) break; pmt_pid = get16(&p, p_end) & 0x1fff; if (pmt_pid < 0) break; #ifdef DEBUG_SI printf("sid=0x%x pid=0x%x\n", sid, pmt_pid); #endif if (sid == 0x0000) { /* NIT info */ } else { if (ts->req_sid == sid) { ts->pmt_filter = mpegts_open_section_filter(ts, pmt_pid, pmt_cb, ts, 1); goto found; } } } /* not found */ ts->set_service_cb(ts->set_service_opaque, -1); found: mpegts_close_filter(ts, ts->pat_filter); ts->pat_filter = NULL; }
static void pmt_cb(void *opaque, const uint8_t *section, int section_len) { MpegTSContext *ts = opaque; SectionHeader h1, *h = &h1; const uint8_t *p, *p_end; int program_info_length, pcr_pid, pid, stream_type, desc_length; #ifdef DEBUG_SI printf("PMT:\n"); av_hex_dump(stdout, (uint8_t *)section, section_len); #endif p_end = section + section_len - 4; p = section; if (parse_section_header(h, &p, p_end) < 0) return; #ifdef DEBUG_SI printf("sid=0x%x sec_num=%d/%d\n", h->id, h->sec_num, h->last_sec_num); #endif if (h->tid != PMT_TID || (ts->req_sid >= 0 && h->id != ts->req_sid) ) return; pcr_pid = get16(&p, p_end) & 0x1fff; if (pcr_pid < 0) return; ts->pcr_pid = pcr_pid; #ifdef DEBUG_SI printf("pcr_pid=0x%x\n", pcr_pid); #endif program_info_length = get16(&p, p_end) & 0xfff; if (program_info_length < 0) return; p += program_info_length; if (p >= p_end) return; for(;;) { stream_type = get8(&p, p_end); if (stream_type < 0) break; pid = get16(&p, p_end) & 0x1fff; if (pid < 0) break; desc_length = get16(&p, p_end) & 0xfff; if (desc_length < 0) break; p += desc_length; if (p > p_end) return; #ifdef DEBUG_SI printf("stream_type=%d pid=0x%x\n", stream_type, pid); #endif /* now create ffmpeg stream */ switch(stream_type) { case STREAM_TYPE_AUDIO_MPEG1: case STREAM_TYPE_AUDIO_MPEG2: case STREAM_TYPE_VIDEO_MPEG1: case STREAM_TYPE_VIDEO_MPEG2: case STREAM_TYPE_VIDEO_MPEG4: case STREAM_TYPE_VIDEO_H264: case STREAM_TYPE_AUDIO_AAC: case STREAM_TYPE_AUDIO_AC3: add_pes_stream(ts, pid, stream_type); break; default: /* we ignore the other streams */ break; } } /* all parameters are there */ ts->set_service_cb(ts->set_service_opaque, 0); mpegts_close_filter(ts, ts->pmt_filter); ts->pmt_filter = NULL; }
static void pmt_cb(void *opaque, const uint8_t *section, int section_len) { MpegTSContext *ts = opaque; SectionHeader h1, *h = &h1; PESContext *pes; AVStream *st; const uint8_t *p, *p_end, *desc_list_end, *desc_end; int program_info_length, pcr_pid, pid, stream_type; int desc_list_len, desc_len, desc_tag; int comp_page = 0, anc_page = 0; /* initialize to kill warnings */ char language[4]; #ifdef DEBUG_SI printf("PMT:\n"); av_hex_dump(stdout, (uint8_t *)section, section_len); #endif p_end = section + section_len - 4; p = section; if (parse_section_header(h, &p, p_end) < 0) return; #ifdef DEBUG_SI printf("sid=0x%x sec_num=%d/%d\n", h->id, h->sec_num, h->last_sec_num); #endif if (h->tid != PMT_TID || (ts->req_sid >= 0 && h->id != ts->req_sid) ) return; pcr_pid = get16(&p, p_end) & 0x1fff; if (pcr_pid < 0) return; ts->pcr_pid = pcr_pid; #ifdef DEBUG_SI printf("pcr_pid=0x%x\n", pcr_pid); #endif program_info_length = get16(&p, p_end) & 0xfff; if (program_info_length < 0) return; p += program_info_length; if (p >= p_end) return; for(;;) { language[0] = 0; st = 0; stream_type = get8(&p, p_end); if (stream_type < 0) break; pid = get16(&p, p_end) & 0x1fff; if (pid < 0) break; desc_list_len = get16(&p, p_end) & 0xfff; if (desc_list_len < 0) break; desc_list_end = p + desc_list_len; if (desc_list_end > p_end) break; for(;;) { desc_tag = get8(&p, desc_list_end); if (desc_tag < 0) break; if (stream_type == STREAM_TYPE_PRIVATE_DATA) { if((desc_tag == 0x6A) || (desc_tag == 0x7A)) { /*assume DVB AC-3 Audio*/ stream_type = STREAM_TYPE_AUDIO_AC3; } else if(desc_tag == 0x7B) { /* DVB DTS audio */ stream_type = STREAM_TYPE_AUDIO_DTS; } } desc_len = get8(&p, desc_list_end); desc_end = p + desc_len; if (desc_end > desc_list_end) break; #ifdef DEBUG_SI printf("tag: 0x%02x len=%d\n", desc_tag, desc_len); #endif switch(desc_tag) { case DVB_SUBT_DESCID: if (stream_type == STREAM_TYPE_PRIVATE_DATA) stream_type = STREAM_TYPE_SUBTITLE_DVB; language[0] = get8(&p, desc_end); language[1] = get8(&p, desc_end); language[2] = get8(&p, desc_end); language[3] = 0; get8(&p, desc_end); comp_page = get16(&p, desc_end); anc_page = get16(&p, desc_end); break; case 0x0a: /* ISO 639 language descriptor */ language[0] = get8(&p, desc_end); language[1] = get8(&p, desc_end); language[2] = get8(&p, desc_end); language[3] = 0; break; default: break; } p = desc_end; } p = desc_list_end; #ifdef DEBUG_SI printf("stream_type=%d pid=0x%x\n", stream_type, pid); #endif /* now create ffmpeg stream */ switch(stream_type) { case STREAM_TYPE_AUDIO_MPEG1: case STREAM_TYPE_AUDIO_MPEG2: case STREAM_TYPE_VIDEO_MPEG1: case STREAM_TYPE_VIDEO_MPEG2: case STREAM_TYPE_VIDEO_MPEG4: case STREAM_TYPE_VIDEO_H264: case STREAM_TYPE_AUDIO_AAC: case STREAM_TYPE_AUDIO_AC3: case STREAM_TYPE_AUDIO_DTS: case STREAM_TYPE_SUBTITLE_DVB: pes = add_pes_stream(ts, pid, stream_type); if (pes) st = new_pes_av_stream(pes, 0); break; default: /* we ignore the other streams */ break; } if (st) { if (language[0] != 0) { st->language[0] = language[0]; st->language[1] = language[1]; st->language[2] = language[2]; st->language[3] = language[3]; } if (stream_type == STREAM_TYPE_SUBTITLE_DVB) { st->codec->sub_id = (anc_page << 16) | comp_page; } } } /* all parameters are there */ ts->set_service_cb(ts->set_service_opaque, 0); mpegts_close_filter(ts, ts->pmt_filter); ts->pmt_filter = NULL; }