bit_manager.cpp

00001 /* ***** BEGIN LICENSE BLOCK *****
00002 *
00003 * $Id: bit_manager.cpp,v 1.2 2005/01/30 05:11:40 gabest Exp $ $Name:  $
00004 *
00005 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00006 *
00007 * The contents of this file are subject to the Mozilla Public License
00008 * Version 1.1 (the "License"); you may not use this file except in compliance
00009 * with the License. You may obtain a copy of the License at
00010 * http://www.mozilla.org/MPL/
00011 *
00012 * Software distributed under the License is distributed on an "AS IS" basis,
00013 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for
00014 * the specific language governing rights and limitations under the License.
00015 *
00016 * The Original Code is BBC Research and Development code.
00017 *
00018 * The Initial Developer of the Original Code is the British Broadcasting
00019 * Corporation.
00020 * Portions created by the Initial Developer are Copyright (C) 2004.
00021 * All Rights Reserved.
00022 *
00023 * Contributor(s): Thomas Davies (original author),
00024 *                 Robert Scott Ladd,
00025 *                 Tim Borer
00026 *                 Anuradha Suraparaju
00027 *
00028 * Alternatively, the contents of this file may be used under the terms of
00029 * the GNU General Public License Version 2 (the "GPL"), or the GNU Lesser
00030 * Public License Version 2.1 (the "LGPL"), in which case the provisions of
00031 * the GPL or the LGPL are applicable instead of those above. If you wish to
00032 * allow use of your version of this file only under the terms of the either
00033 * the GPL or LGPL and not to allow others to use your version of this file
00034 * under the MPL, indicate your decision by deleting the provisions above
00035 * and replace them with the notice and other provisions required by the GPL
00036 * or LGPL. If you do not delete the provisions above, a recipient may use
00037 * your version of this file under the terms of any one of the MPL, the GPL
00038 * or the LGPL.
00039 * ***** END LICENSE BLOCK ***** */
00040 
00041 #include <libdirac_common/bit_manager.h>
00042 #include <libdirac_common/common.h>
00043 using namespace dirac;
00044 
00045 using std::vector;
00046 
00048 //Output stuff//
00050 
00051 //Constructor
00052 BasicOutputManager::BasicOutputManager(std::ostream* out_data ):
00053     m_num_out_bytes(0),
00054     m_op_ptr(out_data)
00055 {
00056     InitOutputStream();
00057 }
00058 
00059 void BasicOutputManager::InitOutputStream()
00060 {
00061     // Set byte pointer to start of buffer
00062     m_current_byte = 0;   
00063     // Set output mask to MSB of byte 
00064     m_output_mask = 0x80; 
00065     // Reset the output buffer
00066     m_buffer.clear();
00067 }
00068 
00069 void BasicOutputManager::OutputSkipInterpretStartPrefixByte()
00070 {
00071     size_t buf_size = m_buffer.size();
00072     if (buf_size >=4 && 
00073         m_buffer[buf_size-1] == (char)START_CODE_PREFIX_BYTE3 &&
00074         m_buffer[buf_size-2] == (char)START_CODE_PREFIX_BYTE2 && 
00075         m_buffer[buf_size-3] == (char)START_CODE_PREFIX_BYTE1 &&
00076         m_buffer[buf_size-4] == (char)START_CODE_PREFIX_BYTE0)
00077     {
00078         m_buffer.push_back((char)NOT_START_CODE);
00079         std::cerr << "Wrote ignore code " << std::endl;
00080     }
00081 }
00082 
00083 void BasicOutputManager::OutputBit(const bool& bit )
00084 {
00085     m_current_byte |= (bit ? (m_output_mask):0);
00086 
00087     // Shift mask to next bit in the output byte
00088     m_output_mask >>= 1; 
00089 
00090     if ( m_output_mask == 0 )
00091     { 
00092         // If a whole byte has been written, write out
00093         m_output_mask = 0x80;
00094         m_buffer.push_back(m_current_byte);
00095         OutputSkipInterpretStartPrefixByte();
00096         m_current_byte = 0;
00097     }    
00098 }
00099 
00100 void BasicOutputManager::OutputBit(const bool& bit, int& count)
00101 {
00102     OutputBit(bit);
00103     count++;    
00104 }
00105 
00106 void BasicOutputManager::OutputByte(const char& byte)
00107 {
00108     FlushOutput();
00109     m_buffer.push_back( byte );
00110     OutputSkipInterpretStartPrefixByte();
00111 }
00112 
00113 void BasicOutputManager::OutputBytes( char* str_array )
00114 {
00115     FlushOutput();
00116     while ( *str_array != 0 )
00117     {
00118         m_buffer.push_back( *str_array );
00119         str_array++;
00120     }
00121 }
00122 
00123 void BasicOutputManager::OutputBytes(char* str_array,int num)
00124 {
00125     FlushOutput();
00126     for ( int i=0 ; i<num ; ++i )
00127         m_buffer.push_back( str_array[i] );
00128 }
00129 
00130 
00131 void BasicOutputManager::WriteToFile()
00132 {
00133     FlushOutput();
00134     for ( vector<char>::iterator it=m_buffer.begin() ; it!=m_buffer.end() ; ++it )
00135     {
00136         m_op_ptr->write( &( *it ) , 1 );        
00137     }
00138     m_num_out_bytes = m_buffer.size();
00139     InitOutputStream();        
00140 }
00141 
00142 void BasicOutputManager::FlushOutput()
00143 {
00144     // Flush the current byte to output buffer and reset
00145     if ( m_output_mask != 0x80 )
00146     {
00147         m_buffer.push_back( m_current_byte );    
00148         m_current_byte = 0;
00149         m_output_mask = 0x80;
00150     }
00151 }
00152 
00153 // Unit output - a subband or the MV data, for example //
00154 
00155 UnitOutputManager::UnitOutputManager(std::ostream* out_data ):
00156     m_header(out_data),
00157     m_data(out_data),
00158     m_unit_bytes(0),
00159     m_unit_data_bytes(0),
00160     m_unit_head_bytes(0)
00161     {}
00162 
00163 void UnitOutputManager::WriteToFile()
00164 {
00165     m_header.WriteToFile();
00166     m_data.WriteToFile();
00167     
00168     // after writing to file, get the number of unit bytes written
00169     m_unit_data_bytes = m_data.GetNumBytes();
00170     m_unit_head_bytes = m_header.GetNumBytes();
00171     m_unit_bytes = m_unit_data_bytes + m_unit_head_bytes;
00172 
00173 }
00174 
00175 FrameOutputManager::FrameOutputManager( std::ostream* out_data , int num_bands ) :
00176     m_data_array( 3 , num_bands ),
00177     m_comp_bytes( 3 ),
00178     m_comp_hdr_bytes( 3 ),
00179     m_out_stream( out_data )
00180 {
00181     Init( num_bands );
00182 }
00183 
00184 FrameOutputManager::~FrameOutputManager()
00185 {
00186     DeleteAll();
00187 }
00188 
00189 void FrameOutputManager::WriteToFile()
00190 {
00191 
00192     // Write out the frame header
00193     m_frame_header->WriteToFile();
00194     m_total_bytes = m_frame_header->GetNumBytes();
00195     m_header_bytes = m_frame_header->GetNumBytes();
00196 
00197     // Write out the motion vector data
00198     m_mv_data->WriteToFile();
00199 
00200     // after writing to file, get the number of bytes written
00201     m_mv_hdr_bytes = m_mv_data->GetUnitHeaderBytes();
00202     m_mv_bytes = m_mv_data->GetUnitBytes();
00203 
00204     m_total_bytes += m_mv_bytes;
00205     m_header_bytes += m_mv_hdr_bytes;
00206 
00207     // Write out the component data
00208     for ( int c=0 ; c<3 ; ++c)
00209     {
00210 
00211         m_comp_hdr_bytes[c] = 0;
00212         m_comp_bytes[c] = 0;
00213 
00214         for ( int b=m_data_array.LastX() ; b>=0 ; --b)
00215         {
00216             m_data_array[c][b]->WriteToFile();
00217             // after writing to file, get the number of bytes written
00218             m_comp_hdr_bytes[c] += m_data_array[c][b]->GetUnitHeaderBytes();
00219             m_comp_bytes[c] += m_data_array[c][b]->GetUnitBytes();
00220         }// b
00221 
00222     }// c
00223 
00224     for ( int c=0 ; c<m_data_array.LengthY() ; ++c)
00225     {
00226         m_total_bytes += m_comp_bytes[c];
00227         m_header_bytes += m_comp_hdr_bytes[c];
00228     }
00229 }
00230 
00231 UnitOutputManager& FrameOutputManager::BandOutput( const int csort , const int band_num)
00232 {
00233     return *( m_data_array[csort][band_num-1] );
00234 }
00235 
00236 const UnitOutputManager& FrameOutputManager::BandOutput( const int csort , const int band_num) const
00237 {
00238     return *( m_data_array[csort][band_num-1] );
00239 }
00240 
00241 // Frame stuff
00242 
00243 
00244 void FrameOutputManager::Init( int num_bands )
00245 {
00246     // Initialise output for the frame header
00247     m_frame_header = new BasicOutputManager( m_out_stream );
00248 
00249     // Initialise output for the MV data
00250     m_mv_data = new UnitOutputManager( m_out_stream );
00251 
00252     // Initialise subband outputs
00253     for ( int c=0 ; c<3 ; ++c)
00254         for ( int b=0 ; b<num_bands ; ++b)
00255             m_data_array[c][b] = new UnitOutputManager( m_out_stream );
00256 }
00257 
00258 void FrameOutputManager::Reset()
00259 {
00260     const int num_bands = m_data_array.LengthX();
00261     DeleteAll();
00262     Init( num_bands );
00263 }   
00264 
00265 void FrameOutputManager::DeleteAll()
00266 {
00267     // Delete subband outputs
00268     for ( int c=0 ; c<3 ; ++c)
00269         for ( int b=0 ; b<m_data_array.LengthX() ; ++b )
00270             delete m_data_array[c][b];
00271 
00272     // Delete MV data op
00273     delete m_mv_data;
00274 
00275     // Delete frame header op
00276     delete m_frame_header;
00277 }   
00278 
00279 
00280 // Sequence stuff //
00281 
00282 SequenceOutputManager::SequenceOutputManager( std::ostream* out_data ):
00283     m_frame_op_mgr( out_data ),
00284     m_seq_header( out_data ),
00285     m_seq_end( out_data ),
00286     m_comp_bytes( 3 ),
00287     m_comp_hdr_bytes( 3 ),
00288     m_mv_hdr_bytes(0),
00289     m_mv_bytes(0),
00290     m_total_bytes(0),
00291     m_header_bytes(0),
00292     m_trailer_bytes(0)
00293 
00294 {
00295     for (int c=0 ; c<3 ; ++c )
00296     {
00297         m_comp_hdr_bytes[c] = 0;
00298         m_comp_bytes[c] = 0;
00299     }
00300 }
00301 
00302 void SequenceOutputManager::WriteFrameData()
00303 {
00304     m_frame_op_mgr.WriteToFile();
00305     
00306     // Keep up with count of component bytes
00307     for (int c=0 ; c<m_comp_hdr_bytes.Length(); ++c)
00308     {
00309         m_comp_hdr_bytes[c] += m_frame_op_mgr.ComponentHeadBytes( c );
00310         m_comp_bytes[c] += m_frame_op_mgr.ComponentBytes( c );
00311     }// c
00312 
00313     // Keep up with count of MV bytes
00314     m_mv_hdr_bytes += m_frame_op_mgr.MVHeadBytes();
00315     m_mv_bytes += m_frame_op_mgr.MVBytes();
00316 
00317     // Keep up with overall totals
00318     m_header_bytes += m_frame_op_mgr.FrameHeadBytes();
00319     m_total_bytes += m_frame_op_mgr.FrameBytes();
00320 
00321 }
00322 
00323 void SequenceOutputManager::WriteSeqHeaderToFile()
00324 {
00325     m_seq_header.WriteToFile();
00326     m_header_bytes += m_seq_header.GetNumBytes();
00327     m_total_bytes += m_seq_header.GetNumBytes();
00328 }
00329 
00330 void SequenceOutputManager::WriteSeqTrailerToFile()
00331 {
00332     m_seq_end.WriteToFile();
00333     m_trailer_bytes += m_seq_end.GetNumBytes();
00334     m_total_bytes += m_seq_end.GetNumBytes();
00335 }
00336 
00338 //Input stuff//
00340 
00341 //Constructor
00342 BitInputManager::BitInputManager(std::istream* in_data ):
00343     m_ip_ptr(in_data)
00344 {
00345     InitInputStream();
00346 }
00347 
00348 
00349 void BitInputManager::InitInputStream()
00350 {
00351     m_shift = 0xffffffff;
00352     m_input_bits_left = 0;
00353 }
00354 
00355 bool BitInputManager::InputBit()
00356 {
00357     //assumes mode errors will be caught by iostream class    
00358 
00359     if (m_input_bits_left == 0)
00360     {
00361         m_ip_ptr->read(&m_current_byte,1);
00362         m_input_bits_left = 8;
00363         if (m_shift == START_CODE_PREFIX && (unsigned char)m_current_byte == NOT_START_CODE)
00364         {
00365             std::cerr << "Ignoring byte " << std::endl;
00366             m_ip_ptr->read(&m_current_byte,1);
00367             m_shift = 0xffffffff;
00368         }
00369         m_shift = (m_shift << 8) | m_current_byte;
00370     }
00371 
00372     m_input_bits_left--;
00373 
00374     return bool( ( m_current_byte >> m_input_bits_left ) & 1 );
00375 
00376 }
00377 
00378 bool BitInputManager::InputBit(int& count)
00379 {
00380     count++;
00381     return InputBit();
00382 }
00383 
00384 bool BitInputManager::InputBit(int& count, const int max_count)
00385 {
00386     if ( count<max_count )
00387     {
00388         count++;
00389         return InputBit();
00390     }
00391     else
00392         return false;
00393 }
00394 
00395 char BitInputManager::InputByte()
00396 {
00397     // Forget about what's in the current byte    
00398     FlushInput();
00399 
00400     char byte;
00401     m_ip_ptr->read(&byte,1);
00402 
00403     return byte;    
00404 }
00405 
00406 void BitInputManager::InputBytes(char* cptr, int num)
00407 {
00408     // Forget about what's in the current byte    
00409     FlushInput();
00410 
00411     m_ip_ptr->read(cptr,num);    
00412 }
00413 
00414 void BitInputManager::FlushInput()
00415 {
00416     m_input_bits_left = 0;    
00417 }
00418 
00419 bool BitInputManager::End() const 
00420 {
00421     return m_ip_ptr->eof();    
00422 }

Generated on Tue Dec 13 14:47:12 2005 for guliverkli by  doxygen 1.4.5