Parse files consisting of multiple concatenated sequences.
[dirac_parser.git] / src / parser / .svn / text-base / Parser.hpp.svn-base
blob21e0affb3b716f3637e382a283669ebbf65c354a
1 /* ***** BEGIN LICENSE BLOCK *****
3 * $Id$
5 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
7 * The contents of this file are subject to the Mozilla Public License
8 * Version 1.1 (the "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 * http://www.mozilla.org/MPL/
12 * Software distributed under the License is distributed on an "AS IS" basis,
13 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for
14 * the specific language governing rights and limitations under the License.
16 * The Original Code is BBC Research code.
18 * The Initial Developer of the Original Code is the British Broadcasting
19 * Corporation.
20 * Portions created by the Initial Developer are Copyright (C) 2007.
21 * All Rights Reserved.
23 * Contributor(s): Andrea Gabriellini (Original Author)
25 * Alternatively, the contents of this file may be used under the terms of
26 * the GNU General Public License Version 2 (the "GPL"), or the GNU Lesser
27 * Public License Version 2.1 (the "LGPL"), in which case the provisions of
28 * the GPL or the LGPL are applicable instead of those above. If you wish to
29 * allow use of your version of this file only under the terms of the either
30 * the GPL or LGPL and not to allow others to use your version of this file
31 * under the MPL, indicate your decision by deleting the provisions above
32 * and replace them with the notice and other provisions required by the GPL
33 * or LGPL. If you do not delete the provisions above, a recipient may use
34 * your version of this file under the terms of any one of the MPL, the GPL
35 * or the LGPL.
36 * ***** END LICENSE BLOCK ***** */
38 #ifndef _PARSER_HPP_
39 #define _PARSER_HPP_
41 #ifdef HAVE_CONFIG_H
42 #include "config.h"
43 #endif
45 #include <common/dirac.h>
46 #include <common/util.hpp>
47 #include <parser/StreamReader.hpp>
48 #include <parser/parser.h>
49 #include <parser/AccessUnit.hpp>
51 #include <iterator>
52 #include <memory>
55 namespace dirac
57 namespace parser_project
59   
60   //! C++ wrapper for the parser API - aims to offer the same functionality
61   class Parser {
62     typedef int (*parser_getter) ( uint8 const**, size_t, size_t*);
63     
64   public: 
65     explicit Parser ( std::auto_ptr<StreamReader> str ) : str_ ( str ) 
66     {
67       checkValidity();
68     }
69     ~Parser() 
70     {
71       checkValidity();
72     }
73   private:  // compiler generated methods are not allowed
74     Parser ( Parser const& );
75     Parser& operator= ( Parser const& );
76     
77   public: 
78     //! retrieves the next sequence header in the associated stream
79     //! au will contain a copy of the sequence header, if found
80     //! the cursor will not be moved past the beginning of the seqhdr, if found
81     bool              getNextSequenceHeader ( AccessUnit& au)
82     {
83       checkValidity();
84       return getAccessUnitFwd ( dirac_parser_get_sequence_header, au );
85     }
86     
87     //! retrieves the next picture in the stream and copies content in au
88     //! the cursor will point to the start of the pic, if found
89     bool              getNextPicture ( AccessUnit& au )
90     {
91       checkValidity();
92       return getAccessUnitFwd ( dirac_parser_get_next_picture, au );
93     }
94     
95     //! retrieves the next i picture in the stream and copies content in au
96     //! the cursor will point to the start of the i pic, if found
97     bool              getNextIPicture ( AccessUnit& au )
98     {
99       checkValidity();
100       return getAccessUnitFwd ( dirac_parser_get_next_i_picture, au );
101     }
103     //! retrieves the next access unit and copies content in au
104     //! the cursor will point to the start of the access unit, if found
105     bool              getNextAccessUnit ( AccessUnit& au )
106     {
107       checkValidity();
108       return getAccessUnitFwd ( dirac_parser_get_next_access_unit, au );
109     }
111     //! Retrieves I pics forward or backward in the bitstream and copies
112     //! content in au, if found
113     //! the cursor will point to the start of the requested i pic, if found
114     bool              getNextIPictureSkipN ( AccessUnit& au, int n )
115     {
116       checkValidity();
117       size_t au_size = 0;
118       int number = n;
119       while ( true ) {
120         if ( !dirac_parser_get_i_picture_skip_n ( &str_->gptr()
121                                                 , str_->sizeFwd()
122                                                 , str_->sizeBwd()
123                                                 , &number
124                                                 , &au_size ) ) {
125           if ( 0 > n ) {
126             if ( !str_->addDataBwd() ) return false;
127             else continue;
128           }
129           else {
130             if ( !str_->addDataFwd() ) return false;
131             else continue;
132           }
133         }
134         else {
135           au.setp ( str_->gptr(), au_size );
136           return true;
137         }
138       }
139     }
140     
141     //! Retrieves I pics bwd in the bitstream and copies content in au
142     //! the cursor will point to the start of the requested i pic, if found
143     bool              getPreviousIPicture ( AccessUnit& au )
144     {
145       checkValidity();
146       size_t au_size = 0;
147       while ( true ) {
148         if ( !dirac_parser_get_previous_i_picture ( &str_->gptr()
149                                                   , str_->sizeFwd()
150                                                   , str_->sizeBwd()
151                                                   , &au_size ) ) {
152           if ( !str_->addDataBwd() ) return false;
153           else continue;
154         }
155         else {
156           au.setp ( str_->gptr(), au_size );
157           return true;
158         }
159       }
160     }
161     
162     //! Determines whether the cursor is pointing to the start of a dirac AU
163     bool              isAccessUnit() const
164     {
165       checkValidity();
166       return dirac_parser_is_access_unit ( str_->gptr(), str_->sizeFwd() );
167     }
168     
169     //! Determines whether the cursor is pointing to the start of a dirac SeqHdr
170     bool              isSequenceHeader() const
171     {
172       checkValidity();
173       return dirac_parser_is_sequence_header ( str_->gptr(), str_->sizeFwd() );
174     }
175     
176     //! Determines whether the cursor is pointing to the start of a picture
177     bool              isPicture() const
178     {
179       checkValidity();
180       return dirac_parser_is_picture ( str_->gptr(), str_->sizeFwd() );
181     }
182     
183     //! Determines whether the cursor is pointing to the start of an intra pic
184     bool              isIPicture() const
185     {
186       checkValidity();
187       return dirac_parser_is_i_picture ( str_->gptr(), str_->sizeFwd() );
188     }
189     
190     //! Determines whether the cursor is pointing to the start of aux data
191     bool              isAuxiliaryData() const
192     {
193       checkValidity();
194       return dirac_parser_is_auxiliary_data ( str_->gptr(), str_->sizeFwd() );
195     }
196     
197     //! Determines whether the cursor is pointing to the start of padding data
198     bool              isPaddingData() const
199     {
200       checkValidity();
201       return dirac_parser_is_padding_data ( str_->gptr(), str_->sizeFwd() );
202     }
203     
204     //! Determines whether the cursor is pointing to the start of the end of seq
205     bool              isEndOfSequence() const
206     {
207       checkValidity();
208       return dirac_parser_is_end_of_sequence ( str_->gptr(), str_->sizeFwd() );
209     }
210     
211     //! Determines whether the cursor if pointing to the start of the last
212     //! end of sequence of the stream
213     bool              isLastEndOfSequence() const
214     {
215       checkValidity();
216       return dirac_parser_is_last_end_of_sequence ( str_->gptr(), str_->sizeFwd() );
217     }
218     
219     //! Retrieves pic number, if cursor points to start of pic
220     bool              getPictureNumber ( uint32& n ) const
221     {
222       checkValidity();
223       return dirac_parser_get_picture_number  ( str_->gptr()
224                                               , str_->sizeFwd()
225                                               , &n );
226     }
227     
228     //! Move cursor forward by one access unit - Note that the user must
229     //! ensure that the cursor points to start of AU or else undefined behaviour
230     bool              moveCursorFwd()
231     {
232       checkValidity();
233       while ( true ) {
234         if ( !dirac_parser_move_cursor_fwd ( &str_->gptr(), str_->sizeFwd() ) ) {
235           if ( !str_->addDataFwd() ) return false;
236           else continue;
237         }
238         else return true;
239       }
240     }
241     
242     //! Rewind the cursor to the beginning of the stream, if possible
243     //! otherwise it has no effect
244     bool              rewind()
245     {
246       checkValidity();
247       return str_->rewind();
248     }
249     
250     //! Allows to swap two Parser objects, guaranteed not to throw
251     void              swap ( Parser& rhs )
252     {
253       checkValidity();
254       std::auto_ptr<StreamReader> tmp ( str_.release() );
255       str_ = rhs.str_;
256       rhs.str_ = tmp;
257     }
258     
259     //! Returns the major version number of this API
260     int               getVersionMajor() const
261     {
262       return dirac_parser_get_version_major();
263     }
264     
265     //! Returns the minor version number of this API
266     int               getVersionMinor() const
267     {
268       return dirac_parser_get_version_minor();
269     }
270     
271     //! Returns the revision number of this API
272     int               getRevision() const
273     {
274       return dirac_parser_get_revision();
275     }
276     
277   private:  // helper methods
278     //! helper class used to implement getter methods
279     bool              getAccessUnitFwd ( parser_getter getter, AccessUnit& au)
280     {
281       size_t au_size = 0;
282       while ( true ) {
283         if ( !getter ( &str_->gptr(), str_->sizeFwd(), &au_size ) ) {
284           if ( !str_->addDataFwd() ) return false;
285           else continue;
286         }
287         else {
288           au.setp ( str_->gptr(), au_size );
289           return true;
290         }
291       }
292     }
293     
294     void              checkValidity() const
295     {
296       DIRAC_MESSAGE_ASSERT ( "stream reader cannot be null", 0 != str_.get() );
297     }
298     
299   private:  // members
300     //! stream buffer used to hold the dirac bitstream
301     std::auto_ptr<StreamReader>        str_;
302   };
303 } /* parser_project */
305 } /* dirac */
308 #endif /* _PARSER_HPP_ */