| OLD | NEW | 
| (Empty) |  | 
 |    1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 
 |    2 // Use of this source code is governed by a BSD-style license that can be | 
 |    3 // found in the LICENSE file. | 
 |    4  | 
 |    5 #include "media/mpeg2/mpeg2ts_pmt.h" | 
 |    6  | 
 |    7 #include <map> | 
 |    8  | 
 |    9 #include "base/logging.h" | 
 |   10 #include "media/base/bit_reader.h" | 
 |   11 #include "media/mpeg2/mpeg2ts_common.h" | 
 |   12  | 
 |   13 namespace media { | 
 |   14 namespace mpeg2ts { | 
 |   15  | 
 |   16 Mpeg2TsPmtParser::Mpeg2TsPmtParser(RegisterPesCb register_pes_cb) | 
 |   17     : register_pes_cb_(register_pes_cb) { | 
 |   18 } | 
 |   19  | 
 |   20 Mpeg2TsPmtParser::~Mpeg2TsPmtParser() { | 
 |   21 } | 
 |   22  | 
 |   23 bool Mpeg2TsPmtParser::ParsePsiSection(BitReader* bit_reader) { | 
 |   24   // Read up to |last_section_number|. | 
 |   25   DCHECK_GE(bit_reader->bits_available(), 8 * 8); | 
 |   26   int table_id; | 
 |   27   DCHECK(bit_reader->ReadBits(8, &table_id)); | 
 |   28   bool section_syntax_indicator; | 
 |   29   DCHECK(bit_reader->ReadBits(1, §ion_syntax_indicator)); | 
 |   30   bool dummy_zero; | 
 |   31   DCHECK(bit_reader->ReadBits(1, &dummy_zero)); | 
 |   32   int reserved; | 
 |   33   DCHECK(bit_reader->ReadBits(2, &reserved)); | 
 |   34   int section_length; | 
 |   35   DCHECK(bit_reader->ReadBits(12, §ion_length)); | 
 |   36   int program_number; | 
 |   37   DCHECK(bit_reader->ReadBits(16, &program_number)); | 
 |   38   DCHECK(bit_reader->ReadBits(2, &reserved)); | 
 |   39   int version_number; | 
 |   40   DCHECK(bit_reader->ReadBits(5, &version_number)); | 
 |   41   bool current_next_indicator; | 
 |   42   DCHECK(bit_reader->ReadBits(1, ¤t_next_indicator)); | 
 |   43   int section_number; | 
 |   44   DCHECK(bit_reader->ReadBits(8, §ion_number)); | 
 |   45   int last_section_number; | 
 |   46   DCHECK(bit_reader->ReadBits(8, &last_section_number)); | 
 |   47   section_length -= 5; | 
 |   48  | 
 |   49   // Perform a few verifications: | 
 |   50   // - table ID should be 2 for a PMT. | 
 |   51   // - section_syntax_indicator should be one. | 
 |   52   // - section length should not exceed 1021. | 
 |   53   RCHECK(table_id == 0x2); | 
 |   54   RCHECK(section_syntax_indicator); | 
 |   55   RCHECK(!dummy_zero); | 
 |   56   RCHECK(section_length <= 1021); | 
 |   57   RCHECK(section_number == 0); | 
 |   58   RCHECK(last_section_number == 0); | 
 |   59  | 
 |   60   // TODO(damienv): | 
 |   61   // Verify that there is no mismatch between the program number | 
 |   62   // and the program number that was provided in a PAT for the current PMT. | 
 |   63  | 
 |   64   // Make sure there are enough bits for the rest of the section. | 
 |   65   int remaining_size = bit_reader->bits_available() / 8; | 
 |   66   if (remaining_size < section_length) { | 
 |   67     LOG(WARNING) << "remaining_size=" << remaining_size; | 
 |   68     return false; | 
 |   69   } | 
 |   70   LOG_IF(WARNING, remaining_size > section_length) | 
 |   71       << "Trailing bytes after the PMT: nbytes=" | 
 |   72       << (remaining_size - section_length); | 
 |   73  | 
 |   74   // Read the end of the fixed length section. | 
 |   75   if (section_length < 4) { | 
 |   76     LOG(WARNING) << "Section length too small"; | 
 |   77     return false; | 
 |   78   } | 
 |   79   DCHECK(bit_reader->ReadBits(3, &reserved)); | 
 |   80   int pcr_pid; | 
 |   81   DCHECK(bit_reader->ReadBits(13, &pcr_pid)); | 
 |   82   DCHECK(bit_reader->ReadBits(4, &reserved)); | 
 |   83   int program_info_length; | 
 |   84   DCHECK(bit_reader->ReadBits(12, &program_info_length)); | 
 |   85   RCHECK(program_info_length < 1024); | 
 |   86   section_length -= 4; | 
 |   87  | 
 |   88   // Read the program info descriptor. | 
 |   89   // TODO(damienv): check wether any of the descriptors could be useful. | 
 |   90   // Defined in section 2.6 of ISO-13818. | 
 |   91   if (section_length < program_info_length) { | 
 |   92     LOG(WARNING) << "Section length too small"; | 
 |   93     return false; | 
 |   94   } | 
 |   95   for (int k = 0; k < program_info_length; k++) { | 
 |   96     int dummy; | 
 |   97     DCHECK(bit_reader->ReadBits(8, &dummy)); | 
 |   98   } | 
 |   99   section_length -= program_info_length; | 
 |  100  | 
 |  101   // Read the ES description table. | 
 |  102   // 5 bytes: minimum size of an ES descriptor. | 
 |  103   std::map<int, int> pid_map; | 
 |  104   while (section_length >= 5) { | 
 |  105     int stream_type; | 
 |  106     DCHECK(bit_reader->ReadBits(8, &stream_type)); | 
 |  107     int reserved; | 
 |  108     DCHECK(bit_reader->ReadBits(3, &reserved)); | 
 |  109     int pid_es; | 
 |  110     DCHECK(bit_reader->ReadBits(13, &pid_es)); | 
 |  111     DCHECK(bit_reader->ReadBits(4, &reserved)); | 
 |  112     int es_info_length; | 
 |  113     DCHECK(bit_reader->ReadBits(12, &es_info_length)); | 
 |  114     section_length -= 5; | 
 |  115  | 
 |  116     // Do not register the PID right away. | 
 |  117     // Wait for the end of the section to be fully parsed | 
 |  118     // to make sure there is no error. | 
 |  119     pid_map.insert(std::pair<int,int>(pid_es, stream_type)); | 
 |  120  | 
 |  121     // Read the ES info descriptors. | 
 |  122     // TODO(damienv): check wether any of the descriptors could be useful. | 
 |  123     // Defined in section 2.6 of ISO-13818. | 
 |  124     if (section_length < es_info_length) { | 
 |  125       LOG(WARNING) << "section_length=" << section_length | 
 |  126                    << " es_info_length=" << es_info_length; | 
 |  127       return false; | 
 |  128     } | 
 |  129     for (int k = 0; k < es_info_length; k++) { | 
 |  130       int dummy; | 
 |  131       DCHECK(bit_reader->ReadBits(8, &dummy)); | 
 |  132     } | 
 |  133     section_length -= es_info_length; | 
 |  134   } | 
 |  135  | 
 |  136   // Read the CRC. | 
 |  137   if (section_length < 4) { | 
 |  138     LOG(WARNING) << "Section length too small: " << section_length; | 
 |  139     return false; | 
 |  140   } | 
 |  141   int crc32; | 
 |  142   DCHECK(bit_reader->ReadBits(32, &crc32)); | 
 |  143   section_length -= 4; | 
 |  144  | 
 |  145   // Should not happen if the PMT size was correctly encoded into the stream. | 
 |  146   LOG_IF(WARNING, section_length != 0) | 
 |  147       << "section_length=" << section_length; | 
 |  148  | 
 |  149   // Once the PMT has been proved to be correct, register the PIDs. | 
 |  150   for (std::map<int, int>::iterator it = pid_map.begin(); | 
 |  151        it != pid_map.end(); ++it) { | 
 |  152     register_pes_cb_.Run(it->first, it->second); | 
 |  153   } | 
 |  154  | 
 |  155   return true; | 
 |  156 } | 
 |  157  | 
 |  158 }  // namespace mpeg2ts | 
 |  159 }  // namespace media | 
| OLD | NEW |