OSDN Git Service

セクションクラスを追加とその他いろいろ修正
authorkoukou <koukou@users.sourceforge.jp>
Thu, 24 Feb 2011 12:05:04 +0000 (21:05 +0900)
committerkoukou <koukou@users.sourceforge.jp>
Thu, 24 Feb 2011 12:05:04 +0000 (21:05 +0900)
src/ARIB/converter.h
src/ARIB/si.cpp
src/ARIB/si.h
src/TS/descriptor.cpp
src/TS/descriptor.h
src/TS/psi.cpp
src/TS/psi.h
src/TS/ts_packet.cpp
src/TS/ts_packet.h
src/TS/utils.h

index 83aa35f..3dc78bd 100644 (file)
@@ -2,6 +2,7 @@
 
 #include <inttypes.h>
 #include <time.h>
+#include <stdio.h>
 #include <stdlib.h>
 
 
index 106a55e..349a645 100644 (file)
@@ -39,17 +39,10 @@ ServiceInformation::STATUS ServiceInformation::parse( SectionBuffer &sec)
                sec += SI_PARSE_SIZE;
        }
 
-       return parseSection( sec);
-}
-
-ServiceInformation::STATUS ServiceInformation::parseSection( SectionBuffer &sec)
-{
-       erase_buffer = false;
        return SUCCESS;
 }
 
 
-
 NIT::NIT( DescriptorParser *des_parser)
        : ServiceInformation( -1, des_parser)
 {
@@ -70,12 +63,17 @@ void NIT::clear()
        ServiceInformation::clear();
 }
 
-NIT::STATUS NIT::parseSection( SectionBuffer &sec)
+NIT::STATUS NIT::parse( SectionBuffer &sec)
 {
        int32_t         size = 0;
        STREAM          s;
        
        clearNIT();
+       
+       STATUS state = ServiceInformation::parse( sec);
+       if( state != SUCCESS) {
+               return state;
+       }
 
        if( sec.length() < 2) {
                return ERROR_PARSE_SECTION;
@@ -162,12 +160,17 @@ void SDT::clear()
        ServiceInformation::clear();
 }\r
 \r
-SDT::STATUS SDT::parseSection( SectionBuffer &sec)\r
+SDT::STATUS SDT::parse( SectionBuffer &sec)\r
 {
        int32_t         size = 0;\r
        SERVICE         s;
        
        clearSDT();\r
+       \r
+       STATUS state = ServiceInformation::parse( sec);\r
+       if( state != SUCCESS) {\r
+               return state;\r
+       }\r
        
        if( sec.length() < SD_PARSE_SIZE) {
                return ERROR_PARSE_SECTION;
@@ -244,12 +247,17 @@ void EIT::clear()
        ServiceInformation::clear();
 }\r
 \r
-EIT::STATUS EIT::parseSection( SectionBuffer &sec)\r
+EIT::STATUS EIT::parse( SectionBuffer &sec)\r
 {
        int32_t         size = 0;\r
        EVENT           e;
        
        clearEIT();\r
+       \r
+       STATUS state = ServiceInformation::parse( sec);\r
+       if( state != SUCCESS) {\r
+               return state;\r
+       }\r
        
        if( sec.length() < EI_PARSE_SIZE) {
                return ERROR_PARSE_SECTION;
@@ -303,3 +311,104 @@ void EIT::clearEIT()
        }
        events.clear();
 }\r
+\r
+\r
+\r
+TDT::TDT( DescriptorParser *des_parser)\r
+       : Section( -1, des_parser)\r
+{\r
+}\r
+\r
+TDT::~TDT()\r
+{\r
+}\r
+\r
+TDT::STATUS TDT::parse( SectionBuffer &sec)\r
+{\r
+       int32_t         size = 0;\r
+       \r
+       if( sec.length() < TD_PARSE_SIZE) {\r
+               return ERROR_PARSE_SECTION;\r
+       }\r
+       \r
+       JST_time                                = Converter::date( &sec[ 0]);\r
+       sec += TD_PARSE_SIZE;\r
+       \r
+       erase_buffer = true;\r
+       return SUCCESS;\r
+}\r
+\r
+bool TDT::checkID( uint8_t id)\r
+{\r
+       return (id == TDT_ID);\r
+}\r
+\r
+\r
+\r
+\r
+TOT::TOT( DescriptorParser *des_parser)\r
+       : TDT( des_parser)\r
+{\r
+}\r
+\r
+TOT::~TOT()\r
+{\r
+       clearTOT();\r
+}\r
+\r
+void TOT::clear()\r
+{\r
+       clearTOT();\r
+       Section::clear();\r
+}\r
+\r
+TOT::STATUS TOT::parse( SectionBuffer &sec)\r
+{\r
+       int32_t         size = 0;\r
+       \r
+       clearTOT();\r
+       \r
+       STATUS state = TDT::parse( sec);\r
+       if( state != SUCCESS) {\r
+               return state;\r
+       }\r
+       if( table_id == TDT_ID) {\r
+               return SUCCESS;\r
+       }\r
+       \r
+       if( sec.length() < TO_PARSE_SIZE) {\r
+               return ERROR_PARSE_SECTION;\r
+       }\r
+       \r
+       reserved_2                              = (sec[ 0] >> 4) & 0x0f;\r
+       descriptors_loop_length = ((sec[ 0] & 0x0f) << 8) + sec[ 1];\r
+       sec += TO_PARSE_SIZE;\r
+\r
+       size = parseDescriptors( sec, descriptors_loop_length, &descriptors);\r
+       if( size == -1) {\r
+               return ERROR_PARSE_SECTION;\r
+       }\r
+       sec += size;\r
+       \r
+       erase_buffer = true;\r
+       return SUCCESS;\r
+}\r
+\r
+bool TOT::checkID( uint8_t id)\r
+{
+       if( TDT::checkID( id)) {
+               return true;
+       }
+       else if( id == TOT_ID) {
+               return true;
+       }
+       else {\r
+               return false;
+       }\r
+}\r
+\r
+void TOT::clearTOT()\r
+{\r
+       clearDescriptors( &descriptors);\r
+}\r
+\r
index e5cc77e..3287f4f 100644 (file)
@@ -37,8 +37,7 @@ public:
        virtual ~ServiceInformation();
 
 protected:
-       STATUS                  parse( SectionBuffer &sec);
-       virtual STATUS  parseSection( SectionBuffer &sec);
+       virtual STATUS  parse( SectionBuffer &sec);
 };
 
 class NIT : public ServiceInformation
@@ -70,7 +69,7 @@ public:
        void    clear();
        
 private:
-       STATUS  parseSection( SectionBuffer &sec);
+       STATUS  parse( SectionBuffer &sec);
        bool    checkID( uint8_t id);
 
        void    clearNIT();
@@ -109,7 +108,7 @@ public:
        void    clear();
        
 private:
-       STATUS  parseSection( SectionBuffer &sec);
+       STATUS  parse( SectionBuffer &sec);
        bool    checkID( uint8_t id);
 
        void    clearSDT();
@@ -149,12 +148,61 @@ public:
        void    clear();
        
 private:
-       STATUS  parseSection( SectionBuffer &sec);
+       STATUS  parse( SectionBuffer &sec);
        bool    checkID( uint8_t id);
 
        void    clearEIT();
 };
 
+// TDT
+class TDT : public Section
+{
+public:
+       static const int32_t    TDT_ID                  = 0x70;
+private:
+       static const uint32_t   TD_PARSE_SIZE   = 5;
+
+public:
+       time_t                  JST_time;                                               // 40bit
+       uint8_t                 reserved_2;                                             // 4bit
+       uint16_t                descriptors_loop_length;                // 12bit
+       DESCRIPTORS             descriptors;
+
+
+       TDT( TS::Description::DescriptorParser *des_parser = NULL);
+       virtual ~TDT();
+       
+protected:
+       virtual STATUS  parse( SectionBuffer &sec);
+       virtual bool    checkID( uint8_t id);
+};
+
+// TOT
+class TOT : public TDT
+{
+public:
+       static const int32_t    TOT_ID                  = 0x73;
+private:
+       static const uint32_t   TO_PARSE_SIZE   = 2;
+
+public:
+       uint8_t                 reserved_2;                                             // 4bit
+       uint16_t                descriptors_loop_length;                // 12bit
+       DESCRIPTORS             descriptors;
+
+
+       TOT( TS::Description::DescriptorParser *des_parser = NULL);
+       virtual ~TOT();
+
+       void    clear();
+
+private:
+       STATUS  parse( SectionBuffer &sec);
+       bool    checkID( uint8_t id);
+
+       void    clearTOT();
+};
+
                }
        }
 }
index 3c519f3..839d6ae 100644 (file)
@@ -52,6 +52,30 @@ Descriptor* DescriptorParser::parse( const uint8_t *data, const uint16_t len, ui
        }
 
        return p;
+}\r
+\r
+Descriptor* DescriptorParser::clone( const Descriptor *des)\r
+{\r
+       int16_t         ret;\r
+       Descriptor      *p = NULL;\r
+\r
+       p = create( des->descriptor_tag, des->descriptor_length);\r
+       if( !p) {\r
+               return p;\r
+       }\r
+\r
+       ret = p->parse( des->descriptor.begin(), des->descriptor.size());\r
+       if( ret < 0) {\r
+               fprintf( stderr, "Descriptor clone error tag = 0x%02X", des->descriptor_tag);\r
+               delete p;\r
+               p = NULL;\r
+       }\r
+       else if( ret != des->descriptor_length) {\r
+               fprintf( stderr, "clone des overflow tag = 0x%02X, len = %d, ret = %d\n", des->descriptor_tag, des->descriptor_length, ret);\r
+               delete p;\r
+               p = NULL;\r
+       }\r
+       return p;\r
 }
 
 Descriptor* DescriptorParser::create( const uint8_t tag, const uint8_t length)
index 6a429f6..d2f2b0a 100644 (file)
@@ -15,6 +15,7 @@ class DescriptorParser
 {
 public:
        Descriptor*     parse( const uint8_t *data, const uint16_t len, uint16_t *parse_size);
+       Descriptor* clone( const Descriptor *des);
 
 protected:
        virtual Descriptor*     create( const uint8_t tag, const uint8_t length);
index e8de170..ffc0e81 100644 (file)
@@ -7,20 +7,50 @@ using namespace TS::PSI;
 using namespace TS::Description;
 
 Section::Section( int32_t id, DescriptorParser *des_parser)
-       : check_id( id)
 {
+       check_id                        = id;
        descriptor_parser       = des_parser;
        ts_packet                       = NULL;
 
        clear();
 }
 
+Section::Section( const Section &src)
+{
+       copy( &src, false);
+}
+
 Section::~Section()
 {
        clear();
 }
 
-Section::STATUS Section::append( TSPacket *p, uint32_t *payload_index)
+void Section::copy(  const Section *src, bool recursive)
+{
+       table_id                                        = src->table_id;
+       section_syntax_indicator        = src->section_syntax_indicator;
+       private_indicator                       = src->private_indicator;
+       reserved_1                                      = src->reserved_1;
+       section_length                          = src->section_length;
+       CRC_32                                          = src->CRC_32;
+
+       section_continue                        = src->section_continue;
+       erase_buffer                            = src->erase_buffer;
+       check_crc                                       = src->check_crc;
+       descriptor_parser                       = src->descriptor_parser;
+
+       check_id                                        = src->check_id;
+       ts_pid                                          = src->ts_pid;
+       prev_ts_counter                         = src->prev_ts_counter;
+       parse_end                                       = src->parse_end;
+
+       if( !erase_buffer) {
+               section_buffer                  = section_buffer;
+       }
+       ts_packet                                       = NULL;
+}
+
+Section::STATUS Section::append( const TSPacket *p, uint32_t *payload_index)
 {
        uint8_t         *payload, *begin, *end;
        uint32_t        payload_len;
@@ -131,6 +161,7 @@ Section::STATUS Section::append( TSPacket *p, uint32_t *payload_index)
        else {
                section_buffer.reset();
        }
+       parse_end = true;
 
        if( payload_len > 0 && payload[ 0] != 0xFF) {
                *payload_index = payload - begin;
@@ -141,7 +172,7 @@ Section::STATUS Section::append( TSPacket *p, uint32_t *payload_index)
 
 bool Section::finish()
 {
-       return !section_continue;
+       return parse_end;
 }
 
 Section::STATUS Section::getTSPacket( TSPacket **packet, uint8_t *counter, AdaptationField *af, bool next)
@@ -243,6 +274,7 @@ void Section::clear()
        section_continue        = false;
        erase_buffer            = true;
        check_crc                       = true;
+       parse_end                       = false;
 
        if( ts_packet) {
                delete ts_packet;
@@ -288,6 +320,29 @@ int32_t Section::parseDescriptors( const uint8_t *data, const uint16_t len, DESC
        return index;
 }
 
+bool Section::cloneDescriptors( DESCRIPTORS *dst, const DESCRIPTORS *src)
+{
+       DescriptorParser                parser;
+       DescriptorParser                *p = descriptor_parser;
+       Descriptor                              *des;
+
+       DESCRIPTORS::const_iterator     src_it;
+
+       if( !p) {
+               p = &parser;
+       }
+
+       dst->clear();
+       for( src_it = src->begin(); src_it != src->end(); src_it++) {
+               des = p->clone( *src_it);
+               if( !des) {
+                       return false;
+               }
+               dst->push_back( des);
+       }
+       return true;
+}
+
 void Section::clearDescriptors( DESCRIPTORS *list)
 {
        DESCRIPTORS::iterator i;
@@ -300,7 +355,7 @@ void Section::clearDescriptors( DESCRIPTORS *list)
        list->clear();
 }
 
-Section::STATUS Section::checkTSPacket( TSPacket *p)
+Section::STATUS Section::checkTSPacket( const TSPacket *p)
 {
        uint16_t        pid             = p->getPID();
        uint8_t         counter = p->getHeader()->getContinuityCounter();
@@ -413,10 +468,32 @@ ProgramSpecificInfomation::ProgramSpecificInfomation( int32_t id, DescriptorPars
        last_section_number                     = 0x00;
 }
 
+ProgramSpecificInfomation::ProgramSpecificInfomation( const ProgramSpecificInfomation &src)
+       : Section( src)
+{
+       copy( &src, false);
+}
+
 ProgramSpecificInfomation::~ProgramSpecificInfomation()
 {
 }
 
+void ProgramSpecificInfomation::copy( const Section *src, bool recursive)
+{
+       if( recursive) {
+               Section::copy( src, recursive);
+       }
+
+       const ProgramSpecificInfomation *psi = (const ProgramSpecificInfomation *)src;
+
+       psi_id.transport_stream_id      = psi->psi_id.transport_stream_id;
+       reserved_2                                      = psi->reserved_2;
+       version_number                          = psi->version_number;
+       current_next_indicator          = psi->current_next_indicator;
+       section_number                          = psi->section_number;
+       last_section_number                     = psi->last_section_number;
+}
+
 ProgramSpecificInfomation::STATUS ProgramSpecificInfomation::parse( SectionBuffer &sec)
 {
        if( section_syntax_indicator != 0) {
@@ -434,12 +511,6 @@ ProgramSpecificInfomation::STATUS ProgramSpecificInfomation::parse( SectionBuffe
                sec += PSI_HEADER_SIZE;
        }
 
-       return parseSection( sec);
-}
-
-ProgramSpecificInfomation::STATUS ProgramSpecificInfomation::parseSection( SectionBuffer &sec)
-{
-       erase_buffer = true;
        return SUCCESS;
 }
 
@@ -475,21 +546,51 @@ PAT::PAT( DescriptorParser *des_parser)
        program_map_PID.clear();
 }
 
+PAT::PAT( const PAT &src)
+       : ProgramSpecificInfomation( src)
+{
+       copy( &src, false);
+}
+
 PAT::~PAT()
 {
        program_map_PID.clear();
 }
 
+void PAT::copy( const Section *src, bool recursive)
+{
+       if( recursive) {
+               ProgramSpecificInfomation::copy( src, recursive);
+       }
+
+       const PAT *pat = (const PAT *)src;
+
+       network_PID             = pat->network_PID;
+       program_map_PID = pat->program_map_PID;
+}
+
+PAT& PAT::operator=( const PAT &src)
+{
+       clear();
+       copy( &src);
+       return *this;
+}
+
 void PAT::clear()
 {
        program_map_PID.clear();
        ProgramSpecificInfomation::clear();
 }
 
-PAT::STATUS PAT::parseSection( SectionBuffer &sec)
+PAT::STATUS PAT::parse( SectionBuffer &sec)
 {
        uint32_t        i;
        uint16_t        prog_num, pid;
+       
+       STATUS state = ProgramSpecificInfomation::parse( sec);
+       if( state != SUCCESS) {
+               return state;
+       }
 
        for( i = 0; i < sec.length() - CRC32_SIZE; i += 4) {
                prog_num        =  (sec[ i + 0] << 8) + sec[ i + 1];
@@ -554,23 +655,70 @@ PMT::PMT( DescriptorParser *des_parser)
 {
 }
 
+PMT::PMT( const PMT &src)
+       : ProgramSpecificInfomation( src)
+{
+       copy( &src);
+}
+
 PMT::~PMT()
 {
        clearPMT();
 }
 
+void PMT::copy( const Section *src, bool recursive)
+{
+       if( recursive) {
+               ProgramSpecificInfomation::copy( src, recursive);
+       }
+
+       const PMT *pmt = (const PMT *)src;
+
+       reserved_3                      = pmt->reserved_3;
+       PCR_PID                         = pmt->PCR_PID;
+       reserved_4                      = pmt->reserved_4;
+       program_info_length     = pmt->program_info_length;
+
+       cloneDescriptors( &program_info_descriptors, &pmt->program_info_descriptors);
+
+       ELEMENT                                         e;
+       ELEMENTS::const_iterator        i;
+       for( i = pmt->elements.begin(); i != pmt->elements.end(); i++) {
+               e.stream_type                   = i->stream_type;
+               e.reserved_1                    = i->reserved_1;
+               e.elementary_PID                = i->elementary_PID;
+               e.reserved_2                    = i->reserved_2;
+               e.ES_info_length                = i->ES_info_length;
+
+               this->cloneDescriptors( &e.descriptors, &i->descriptors);
+               elements.push_back( e);
+       }
+}
+
+PMT& PMT::operator=( const PMT &src)
+{
+       clear();
+       copy( &src);
+       return *this;
+}
+
 void PMT::clear()
 {
        clearPMT();
        ProgramSpecificInfomation::clear();
 }
 
-PMT::STATUS PMT::parseSection( SectionBuffer &sec)
+PMT::STATUS PMT::parse( SectionBuffer &sec)
 {
        int32_t         size = 0;
        ELEMENT         e;
        
        clearPMT();
+       
+       STATUS state = ProgramSpecificInfomation::parse( sec);
+       if( state != SUCCESS) {
+               return state;
+       }
 
        if( sec.length() < PMS_HEADER_SIZE) {
                return ERROR_PARSE_SECTION;
@@ -744,11 +892,16 @@ void CAT::clear()
        ProgramSpecificInfomation::clear();
 }
 
-CAT::STATUS CAT::parseSection( SectionBuffer &sec)
+CAT::STATUS CAT::parse( SectionBuffer &sec)
 {
        int32_t         size = 0;
 
        clearCAT();
+       
+       STATUS state = ProgramSpecificInfomation::parse( sec);
+       if( state != SUCCESS) {
+               return state;
+       }
 
        while( sec.length() > CRC32_SIZE) {
                size = parseDescriptors( sec, sec.length() - CRC32_SIZE, &descriptors);
@@ -787,11 +940,16 @@ void TSDT::clear()
        ProgramSpecificInfomation::clear();
 }
 
-TSDT::STATUS TSDT::parseSection( SectionBuffer &sec)
+TSDT::STATUS TSDT::parse( SectionBuffer &sec)
 {
        int32_t         size = 0;
 
        clearTSDT();
+       
+       STATUS state = ProgramSpecificInfomation::parse( sec);
+       if( state != SUCCESS) {
+               return state;
+       }
 
        while( sec.length() > CRC32_SIZE) {
                size = parseDescriptors( sec, sec.length() - CRC32_SIZE, &descriptors);
index 921b1e4..f1b0677 100644 (file)
@@ -16,9 +16,6 @@ protected:
        static const uint32_t   SECTION_PARSE_SIZE      = 3;
        static const uint32_t   CRC32_SIZE                      = 4;
 
-private:
-       const int32_t           check_id;
-
 public:
        typedef std::list< TS::Description::Descriptor *>       DESCRIPTORS;
        enum STATUS {
@@ -58,6 +55,8 @@ protected:
         TS::Description::DescriptorParser      *descriptor_parser;
 
 private:
+       bool                            parse_end;
+       int32_t                         check_id;
        uint16_t                        ts_pid;
        uint8_t                         prev_ts_counter;
        SectionBuffer           section_buffer;
@@ -68,23 +67,29 @@ public:
        Section( int32_t id = -1, TS::Description::DescriptorParser *des_parser = NULL);
        virtual ~Section();
 
-       STATUS                          append( TSPacket *p, uint32_t *payload_index);
+protected:
+       Section( const Section &src);
+
+public:
+
+       STATUS                          append( const TSPacket *p, uint32_t *payload_index);
        bool                            finish();
        virtual void            clear();
-
        STATUS                          getTSPacket( TSPacket **packet, uint8_t *counter, AdaptationField *af, bool next = true);
 
 protected:
+       virtual void            copy( const Section *src, bool recursive = true);
+
        int32_t                         parseDescriptors( const uint8_t *data, const uint16_t len, DESCRIPTORS *list);
+       bool                            cloneDescriptors( DESCRIPTORS *dst, const DESCRIPTORS *src);
        void                            clearDescriptors( DESCRIPTORS *list);
 
+
 private:
-       STATUS                          checkTSPacket( TSPacket *p);
+       STATUS                          checkTSPacket( const TSPacket *p);
        void                            parseHeader( SectionBuffer &sec);
-
        virtual STATUS          parse( SectionBuffer &sec);
        virtual bool            checkID( uint8_t id);
-
        STATUS                          createBytes();
        virtual STATUS          getBytes( SectionBuffer &buf);
 };
@@ -112,12 +117,13 @@ public:
        ProgramSpecificInfomation( int32_t id = -1, TS::Description::DescriptorParser *des_parser = NULL);
        virtual ~ProgramSpecificInfomation();
 
-
 protected:
-       STATUS                  parse( SectionBuffer &sec);
-       virtual STATUS  parseSection( SectionBuffer &sec);
+       ProgramSpecificInfomation( const ProgramSpecificInfomation &src);
 
+       virtual STATUS  parse( SectionBuffer &sec);
        virtual STATUS  getBytes( SectionBuffer &buf);
+       //void                  copy( const ProgramSpecificInfomation *src);
+       virtual void    copy( const Section *src, bool recursive = true);
 };
 
 
@@ -132,14 +138,17 @@ public:
        PROGRAM_MAP     program_map_PID;
 
        PAT( TS::Description::DescriptorParser *des_parser = NULL);
+       PAT( const PAT &src);
        virtual ~PAT();
 
+public:
        void                    clear();
+       PAT&                    operator=( const PAT &src);
 
 private:
-       STATUS                  parseSection( SectionBuffer &sec);
-
+       STATUS                  parse( SectionBuffer &sec);
        STATUS                  getBytes( SectionBuffer &buf);
+       void                    copy( const Section *src, bool recursive = true);
 };
 
 
@@ -169,16 +178,18 @@ public:
        ELEMENTS                        elements;
 
        PMT( TS::Description::DescriptorParser *des_parser = NULL);
+       PMT( const PMT &src);
        virtual ~PMT();
 
        void                    clear();
        void                    eraseElement( uint8_t stream_type);
+       PMT&                    operator=( const PMT &src);
 
 private:
-       STATUS                  parseSection( SectionBuffer &sec);
-       void                    clearPMT();
-
+       STATUS                  parse( SectionBuffer &sec);
        STATUS                  getBytes( SectionBuffer &buf);
+       void                    clearPMT();
+       void                    copy( const Section *src, bool recursive = true);
 
 };
 
@@ -196,7 +207,7 @@ public:
        void                    clear();
 
 private:
-    STATUS                     parseSection( SectionBuffer &sec);
+    STATUS                     parse( SectionBuffer &sec);
     void                       clearCAT();
 };
 
@@ -214,7 +225,7 @@ public:
        void                    clear();
 
 private:
-    STATUS                     parseSection( SectionBuffer &sec);
+    STATUS                     parse( SectionBuffer &sec);
     void                       clearTSDT();
 };
 
index 4b054e5..46bc828 100644 (file)
@@ -17,7 +17,7 @@ Header::~Header()
 {
 }
 
-int Header::getBytes( uint8_t *buf, uint32_t size)
+int Header::getBytes( uint8_t *buf, uint32_t size) const
 {
        if( size < TS_HEADER_SZIE) {
                return -1;
@@ -70,9 +70,9 @@ AdaptationField::AdaptationField()
 #endif
 }
 
-AdaptationField::AdaptationField( AdaptationField &src)
+AdaptationField::AdaptationField( const AdaptationField &src)
 {
-       src.copy( *this);
+       copy( &src);
 }
 
 AdaptationField::~AdaptationField()
@@ -80,13 +80,51 @@ AdaptationField::~AdaptationField()
        clear();
 }
 
-AdaptationField& AdaptationField::operator=( AdaptationField &src)
+void AdaptationField::clear()
+{
+       if( adaptation_field) {
+               delete[] adaptation_field;
+       }
+       adaptation_field        = NULL;
+       field_data                      = NULL;
+       field_data_length       = 0;
+}
+
+AdaptationField& AdaptationField::operator=( const AdaptationField &src)
 {
-       src.copy( *this);
+       clear();
+       copy( &src);
        return *this;
 }
 
-int AdaptationField::getBytes( uint8_t *buf, uint32_t size)
+void AdaptationField::copy( const AdaptationField *src)
+{
+       const uint8_t af_len = src->getAdaptationFieldLength();
+
+       if( src->adaptation_field) {
+               adaptation_field = new uint8_t[ af_len + 1];
+               memcpy( adaptation_field, src->adaptation_field, af_len + 1);
+
+               if( src->field_data_length > 0) {
+                       field_data_length       = src->field_data_length;
+                       field_data                      = &adaptation_field[ 2];
+               }
+       }
+
+#ifdef PACKET_DEBUG
+       adaptation_field_length                                 = src->adaptation_field_length;
+       discontinuity_indicator                                 = src->discontinuity_indicator;
+       random_access_indicator                                 = src->random_access_indicator;
+       elementary_stream_priority_indicator    = src->elementary_stream_priority_indicator;
+       PCR_flag                                                                = src->PCR_flag;
+       OPCR_flag                                                               = src->OPCR_flag;
+       splicing_point_flag                                             = src->splicing_point_flag;
+       transport_private_data_flag                             = src->transport_private_data_flag;
+       adaptation_field_extension_flag                 = src->adaptation_field_extension_flag;
+#endif
+}
+
+int AdaptationField::getBytes( uint8_t *buf, uint32_t size) const
 {
        int      index = 0;
        const uint8_t af_len = getAdaptationFieldLength();
@@ -146,45 +184,6 @@ int AdaptationField::parse( uint8_t *buf, uint32_t len)
        return index;
 }
 
-
-void AdaptationField::copy( AdaptationField &dst)
-{
-       const uint8_t af_len = getAdaptationFieldLength();
-
-       dst.clear();
-       if( adaptation_field) {
-               dst.adaptation_field = new uint8_t[ af_len + 1];
-               memcpy( dst.adaptation_field, adaptation_field, af_len + 1);
-
-               if( field_data_length > 0) {
-                       dst.field_data_length   = field_data_length;
-                       dst.field_data                  = &dst.adaptation_field[ 2];
-               }
-       }
-
-#ifdef PACKET_DEBUG
-       dst.adaptation_field_length                                     = adaptation_field_length;
-       dst.discontinuity_indicator                                     = discontinuity_indicator;
-       dst.random_access_indicator                                     = random_access_indicator;
-       dst.elementary_stream_priority_indicator        = elementary_stream_priority_indicator;
-       dst.PCR_flag                                                            = PCR_flag;
-       dst.OPCR_flag                                                           = OPCR_flag;
-       dst.splicing_point_flag                                         = splicing_point_flag;
-       dst.transport_private_data_flag                         = transport_private_data_flag;
-       dst.adaptation_field_extension_flag                     = adaptation_field_extension_flag;
-#endif
-}
-
-void AdaptationField::clear()
-{
-       if( adaptation_field) {
-               delete[] adaptation_field;
-       }
-       adaptation_field        = NULL;
-       field_data                      = NULL;
-       field_data_length       = 0;
-}
-
 TSPacket::TSPacket( Header *h, AdaptationField *af, uint8_t *p, uint32_t p_len)
 {
        header                          = h;
@@ -218,32 +217,32 @@ TSPacket::~TSPacket()
        payload_length = 0;
 }
 
-uint16_t TSPacket::getPID()
+uint16_t TSPacket::getPID() const
 {
        return header->getPid();
 }
 
-Header* TSPacket::getHeader()
+Header* TSPacket::getHeader() const
 {
        return header;
 }
 
-AdaptationField* TSPacket::getAdaptationField()
+AdaptationField* TSPacket::getAdaptationField() const
 {
        return adaptation_field;
 }
-uint32_t TSPacket::getPayloadLength()
+uint32_t TSPacket::getPayloadLength() const
 {
        return payload_length;
 }
 
-uint32_t TSPacket::getPayload( uint8_t **p)
+uint32_t TSPacket::getPayload( uint8_t **p) const
 {
        *p = payload;
        return payload_length;
 }
 
-int TSPacket::getBytes( uint8_t *buf, uint32_t size)
+int TSPacket::getBytes( uint8_t *buf, uint32_t size) const
 {
        int     index = 0;
        int w;
index 8d7b984..e0c21c8 100644 (file)
@@ -6,6 +6,20 @@
 
 namespace TS {
 
+enum PID {
+       PID_PAT         = 0x0000,
+       PID_CAT         = 0x0001,
+       PID_TSDT        = 0x0002,
+       PID_NIT         = 0x0010,
+       PID_SDT         = 0x0011,
+       PID_EIT         = 0x0012,
+       PID_TDT         = 0x0014,
+       PID_TOT         = 0x0014,
+
+       PID_EIT1        = 0x0026,
+       PID_EIT2        = 0x0027,
+};
+
 class Header {
 public:
        static const int                TS_HEADER_SZIE  = 4;
@@ -29,18 +43,18 @@ public:
        Header();
        virtual ~Header();
 
-       int                                     getBytes( uint8_t *buf, uint32_t size);
+       int                                     getBytes( uint8_t *buf, uint32_t size) const;
        int                                     parse( const uint8_t *buf, uint32_t len);
 
-       uint32_t                        size();
+       uint32_t                        size() const;
 
-       uint8_t                         getTransportErrorIndicator();
-       uint8_t                         getPayloadUnitStartIndicator();
-       uint8_t                         getTransportPriority();
-       uint16_t                        getPid();
-       uint8_t                         getTransportScramblingControl();
-       uint8_t                         getAdaptationFieldControl();
-       uint8_t                         getContinuityCounter();
+       uint8_t                         getTransportErrorIndicator() const;
+       uint8_t                         getPayloadUnitStartIndicator() const;
+       uint8_t                         getTransportPriority() const;
+       uint16_t                        getPid() const;
+       uint8_t                         getTransportScramblingControl() const;
+       uint8_t                         getAdaptationFieldControl() const;
+       uint8_t                         getContinuityCounter() const;
 
        void                            setTransportErrorIndicator( uint8_t val);
        void                            setPayloadUnitStartIndicator( uint8_t val);
@@ -53,6 +67,8 @@ public:
 
 class AdaptationField {
 private:
+       const static int        PCR_SIZE        = 6;
+
        uint8_t                         *adaptation_field;
 
 #ifdef PACKET_DEBUG
@@ -72,29 +88,33 @@ private:
        
 public:
        AdaptationField();
-       AdaptationField( AdaptationField &src);
+       AdaptationField( const AdaptationField &src);
        virtual ~AdaptationField();
 
-       int                                     getBytes( uint8_t *buf, uint32_t size);
+       int                                     getBytes( uint8_t *buf, uint32_t size) const;
        int                                     parse( uint8_t *buf, uint32_t len);
 
-       uint32_t                        size();
+       uint32_t                        size() const;
 
-       uint8_t                         getAdaptationFieldLength();                                     //  8bit
-       uint8_t                         getDiscontinuityIndicator();                                    //  1bit
-       uint8_t                         getRandomAccessIndicator();                                     //  1bit
-       uint8_t                         getElementaryStreamPriorityIndicator(); //  1bit
-       uint8_t                         getPCRFlag();                                                                   //  1bit
-       uint8_t                         getOPCRFlag();                                                                  //  1bit
-       uint8_t                         getSplicingPointFlag();                                         //  1bit
-       uint8_t                         getTransportPrivateDataFlag();                          //  1bit
-       uint8_t                         getAdaptationFieldExtensionFlag();                      //  1bit
+       uint8_t                         getAdaptationFieldLength() const;                               //  8bit
+       uint8_t                         getDiscontinuityIndicator() const;                              //  1bit
+       uint8_t                         getRandomAccessIndicator()  const;                              //  1bit
+       uint8_t                         getElementaryStreamPriorityIndicator() const;   //  1bit
+       uint8_t                         getPCRFlag()  const;                                                            //  1bit
+       uint8_t                         getOPCRFlag()  const;                                                           //  1bit
+       uint8_t                         getSplicingPointFlag() const;                                   //  1bit
+       uint8_t                         getTransportPrivateDataFlag() const;                    //  1bit
+       uint8_t                         getAdaptationFieldExtensionFlag() const;                //  1bit
 
+       // PCR
+       uint64_t                        getProgramClockReferenceBase() const;                   // 33bit
+       uint16_t                        getProgramClockReferenceExtension() const;              //  9bit
+       uint64_t                        getProgramClockReference() const;
 
-       AdaptationField&        operator=( AdaptationField &src);
+       AdaptationField&        operator=( const AdaptationField &src);
 
 private:
-       void                    copy( AdaptationField &dst);
+       void                    copy( const AdaptationField *src);
        void                    clear();
 };
 
@@ -116,13 +136,13 @@ public:
        virtual ~TSPacket();
 
 public:
-       uint16_t                        getPID();
-       Header*                         getHeader();
-       AdaptationField*        getAdaptationField();
-       uint32_t                        getPayloadLength();
-       uint32_t                        getPayload( uint8_t **p);
+       uint16_t                        getPID() const;
+       Header*                         getHeader() const;
+       AdaptationField*        getAdaptationField() const;
+       uint32_t                        getPayloadLength() const;
+       uint32_t                        getPayload( uint8_t **p) const;
 
-       int                                     getBytes( uint8_t *buf, uint32_t size);
+       int                                     getBytes( uint8_t *buf, uint32_t size) const;
 
        static TSPacket*        parse( uint8_t *buf, uint32_t len, uint32_t *read_len);
        static TSPacket*        create( Header *h, AdaptationField *af, uint8_t *p, uint32_t p_len);
@@ -133,12 +153,12 @@ private:
 
 
 
-inline uint32_t Header::size()
+inline uint32_t Header::size() const
 {
        return TS_HEADER_SZIE;
 }
 
-inline uint8_t Header::getTransportErrorIndicator()
+inline uint8_t Header::getTransportErrorIndicator() const
 {
        return Bits::get( header[ 1], 7, 0x01);
 }
@@ -148,7 +168,7 @@ inline void Header::setTransportErrorIndicator( uint8_t val)
        Bits::set( &header[ 1], val, 7, 0x01);
 }
 
-inline uint8_t Header::getPayloadUnitStartIndicator()
+inline uint8_t Header::getPayloadUnitStartIndicator() const
 {
        return Bits::get( header[ 1], 6, 0x01);
 }
@@ -158,7 +178,7 @@ inline void Header::setPayloadUnitStartIndicator( uint8_t val)
        Bits::set( &header[ 1], val, 6, 0x01);
 }
 
-inline uint8_t Header::getTransportPriority()
+inline uint8_t Header::getTransportPriority() const
 {
        return Bits::get( header[ 1], 5, 0x01);
 }
@@ -168,7 +188,7 @@ inline void Header::setTransportPriority( uint8_t val)
        Bits::set( &header[ 1], val, 5, 0x01);
 }
 
-inline uint16_t Header::getPid()
+inline uint16_t Header::getPid() const
 {
        return (Bits::get( header[ 1], 0, 0x1f) << 8) + header[ 2];
 }
@@ -179,7 +199,7 @@ inline void Header::setPid( uint16_t val)
        header[ 2] = val & 0xff;
 }
 
-inline uint8_t Header::getTransportScramblingControl()
+inline uint8_t Header::getTransportScramblingControl() const
 {
        return Bits::get( header[ 3], 6, 0x03);
 }
@@ -189,7 +209,7 @@ inline void Header::setTransportScramblingControl( uint8_t val)
        Bits::set( &header[ 3], val, 6, 0x03);
 }
 
-inline uint8_t Header::getAdaptationFieldControl()
+inline uint8_t Header::getAdaptationFieldControl() const
 {
        return Bits::get( header[ 3], 4, 0x03);
 }
@@ -199,7 +219,7 @@ inline void Header::setAdaptationFieldControl( uint8_t val)
        Bits::set( &header[ 3], val, 4, 0x03);
 }
 
-inline uint8_t Header::getContinuityCounter()
+inline uint8_t Header::getContinuityCounter() const
 {
        return Bits::get( header[ 3], 0, 0x0f);
 }
@@ -211,12 +231,12 @@ inline void Header::setContinuityCounter( uint8_t val)
 
 
 
-inline uint32_t AdaptationField::size()
+inline uint32_t AdaptationField::size() const
 {
        return getAdaptationFieldLength() + 1;
 }
 
-inline uint8_t AdaptationField::getAdaptationFieldLength()
+inline uint8_t AdaptationField::getAdaptationFieldLength() const
 {
        if( adaptation_field) {
                return adaptation_field[ 0];
@@ -226,7 +246,7 @@ inline uint8_t AdaptationField::getAdaptationFieldLength()
        }
 }
 
-inline uint8_t AdaptationField::getDiscontinuityIndicator()
+inline uint8_t AdaptationField::getDiscontinuityIndicator() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 7, 0x01);
@@ -236,7 +256,7 @@ inline uint8_t AdaptationField::getDiscontinuityIndicator()
        }
 }
 
-inline uint8_t AdaptationField::getRandomAccessIndicator()
+inline uint8_t AdaptationField::getRandomAccessIndicator() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 6, 0x01);
@@ -246,7 +266,7 @@ inline uint8_t AdaptationField::getRandomAccessIndicator()
        }
 }
 
-inline uint8_t AdaptationField::getElementaryStreamPriorityIndicator()
+inline uint8_t AdaptationField::getElementaryStreamPriorityIndicator() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 5, 0x01);
@@ -256,7 +276,7 @@ inline uint8_t AdaptationField::getElementaryStreamPriorityIndicator()
        }
 }
 
-inline uint8_t AdaptationField::getPCRFlag()
+inline uint8_t AdaptationField::getPCRFlag() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 4, 0x01);
@@ -266,7 +286,7 @@ inline uint8_t AdaptationField::getPCRFlag()
        }
 }
 
-inline uint8_t AdaptationField::getOPCRFlag()
+inline uint8_t AdaptationField::getOPCRFlag() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 3, 0x01);
@@ -276,7 +296,7 @@ inline uint8_t AdaptationField::getOPCRFlag()
        }
 }
 
-inline uint8_t AdaptationField::getSplicingPointFlag()
+inline uint8_t AdaptationField::getSplicingPointFlag() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 2, 0x01);
@@ -286,7 +306,7 @@ inline uint8_t AdaptationField::getSplicingPointFlag()
        }
 }
 
-inline uint8_t AdaptationField::getTransportPrivateDataFlag()
+inline uint8_t AdaptationField::getTransportPrivateDataFlag() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 1, 0x01);
@@ -296,7 +316,7 @@ inline uint8_t AdaptationField::getTransportPrivateDataFlag()
        }
 }
 
-inline uint8_t AdaptationField::getAdaptationFieldExtensionFlag()
+inline uint8_t AdaptationField::getAdaptationFieldExtensionFlag() const
 {
        if( adaptation_field) {
                return Bits::get( adaptation_field[ 1], 0, 0x01);
@@ -306,5 +326,32 @@ inline uint8_t AdaptationField::getAdaptationFieldExtensionFlag()
        }
 }
 
+inline uint64_t         AdaptationField::getProgramClockReferenceBase() const
+{
+       uint64_t base = 0;
+       if( getPCRFlag() && field_data && field_data_length >= PCR_SIZE) {
+               base =  ((uint64_t)field_data[ 0] << 25) + (field_data[ 1] << 17) +
+                               (field_data[ 2] <<  9) + (field_data[ 3] <<  1) +
+                               ((field_data[ 4] >>  7) & 0x01);
+       }
+       return base;
+}
+
+inline uint16_t         AdaptationField::getProgramClockReferenceExtension() const
+{
+       uint16_t ext = 0;
+       if( getPCRFlag() && field_data && field_data_length >= PCR_SIZE) {
+               ext =   ((field_data[ 4] & 0x01) << 8) + field_data[ 5];
+       }
+       return ext;
+}
+
+inline uint64_t AdaptationField::getProgramClockReference() const
+{
+       uint64_t base   = getProgramClockReferenceBase();
+       uint16_t ext    = getProgramClockReferenceExtension();
+       return (base * 300 + ext);
+}
+
 }
 
index 0734721..1492090 100644 (file)
@@ -92,7 +92,7 @@ public:
                }
        }
 
-       uint8_t*        begin() {
+       uint8_t*        begin() const {
                return _data;
        }