videoeditorengine/h263decoder/src/sync_mpeg.cpp
branchRCL_3
changeset 3 e0b5df5c0969
parent 0 951a5db380a0
child 7 4c409de21d23
--- a/videoeditorengine/h263decoder/src/sync_mpeg.cpp	Fri Jan 29 14:08:33 2010 +0200
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,648 +0,0 @@
-/*
-* Copyright (c) 2010 Ixonos Plc.
-* All rights reserved.
-* This component and the accompanying materials are made available
-* under the terms of the "Eclipse Public License v1.0"
-* which accompanies this distribution, and is available
-* at the URL "http://www.eclipse.org/legal/epl-v10.html".
-*
-* Initial Contributors:
-* Nokia Corporation - Initial contribution
-*
-* Contributors:
-* Ixonos Plc
-*
-* Description:  
-* MPEG-4 sync code functions.
-*
-*/
-
-
-#include "h263dConfig.h"
-
-#include "sync.h"
-#include "errcodes.h"
-#include "debug.h"
-#include "mpegcons.h"
-#include "biblin.h"
-
-
-/*
- * Global functions
- */
-
-/* {{-output"sncCheckMpegVOP.txt"}} */
-/*
- *
- * sncCheckMpegVOP
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    error                      error code
- *
- * Function:
- *    This function checks if the GOV, VOP start codes
- *    are the next codes in the bit buffer.
- *    NO stuffing is allowed before the code, the routine checks from the
- *    current position in the buffer-
- *    The code is not flushed from the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if no sync code is found
- *    SNC_PSC                    if GOV or VOP start code is found
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- *    
- */
-
-int sncCheckMpegVOP(bibBuffer_t *buffer, int16 *error)
-/* {{-output"sncCheckMpegVOP.txt"}} */
-{
-   u_int32 bits;
-   int16 newError = 0;
-   int numBitsGot, bitErrorIndication = 0;
-
-   bits = bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-   
-   if ((newError == ERR_BIB_NOT_ENOUGH_DATA) && (numBitsGot > 0 )) {
-       /* Still bits in the buffer */
-       deb("sncCheckSync: bibShowReturned not enough data but there are "
-           "still bits in the buffer --> error cleared.\n");
-       return SNC_NO_SYNC;
-   } else if (newError) {
-       *error = newError;
-       return SNC_NO_SYNC;
-   }
-
-   if (bits == MP4_GROUP_START_CODE || bits == MP4_VOP_START_CODE || bits == MP4_EOB_CODE)
-        return SNC_PSC;
-   else 
-        return SNC_NO_SYNC;
-}
-
-/* {{-output"sncCheckMpegSync.txt"}} */
-/*
- *
- * sncCheckMpegSync
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    f_code                     f_code of the last P-vop
- *    error                      error code
- *
- * Function:
- *    This function checks if the GOV, VOP or Video Pcaket start codes
- *    are the next codes in the bit buffer.
- *    Stuffing is needed before the code and the number of stuffing bits
- *    is returned in numStuffBits parameter.
- *    The code is not flushed from the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if no sync code is found
- *    SNC_GOV                    if GOV start code is found
- *    SNC_VOP                    if VOP start code is found
- *    SNC_VOS                    if VOS start code is found
- *    SNC_VIDPACK                if Video Packet start code is found
- *    SNC_STUFFING               if there is a bit with the value zero 
- *                               followed by less than 7 bits with the 
- *                               value one starting from the current position 
- *                               and after them the buffer (picture segment) ends
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- *    
- *    
- *    
- *    
- */
-
-int sncCheckMpegSync(bibBuffer_t *buffer, int f_code, int16 *error)
-/* {{-output"sncCheckMpegSync.txt"}} */
-{
-   u_int32 result, bits, start_code_val;
-   int numBitsGot, i, shift_bits;
-   int16 newError = 0;
-   int bitErrorIndication = 0;
-
-   shift_bits = 32-(16+f_code);
-
-   bits = bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-   
-   if ( buffer->error )
-      {
-      // out of bits
-      *error = (int16)buffer->error;
-      return SNC_NO_SYNC;
-      }
-
-
-   for(i = 0; i <= 8; i++) {
-
-       /* if stuffing is correct */
-       if ( (i==0) || ((bits >> (32-i)) == (u_int32) ((1 << (i-1))-1)) ) {
-
-           result = bits << i;
-
-           if ((result >> 8) == 1) {
-
-               /* Stuff start code */
-               if (i != 0) {
-                   bibFlushBits(i, buffer, &numBitsGot, &bitErrorIndication, &newError);
-                   if (newError) {
-                       *error = newError;
-                       return SNC_NO_SYNC;
-                   }
-               }
-
-               /* Check start code */
-               start_code_val = 
-                   bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-               if ((newError == ERR_BIB_NOT_ENOUGH_DATA) && (numBitsGot > 0 )) {
-                       /* Still bits in the buffer */
-                       deb("sncCheckSync: bibShowReturned not enough data but there are "
-                           "still bits in the buffer --> error cleared.\n");
-                       if (i) bibRewindBits(i, buffer, &newError);
-                       return SNC_NO_SYNC;
-               } else if (newError) {
-                   *error = newError;
-                   if (i) bibRewindBits(i, buffer, &newError);
-                   return SNC_NO_SYNC;
-               }
-
-               if (start_code_val == MP4_VOP_START_CODE) {
-                   return SNC_VOP;
-               } else if (start_code_val == MP4_VOS_START_CODE) {
-                   return SNC_VOS;
-               } else if (start_code_val == MP4_GROUP_START_CODE) {
-                   return SNC_GOV;
-               } else if (start_code_val == MP4_USER_DATA_START_CODE) {
-                   return SNC_USERDATA;
-               } else if (start_code_val == MP4_EOB_CODE) {
-                   return SNC_EOB;
-               } else if (((start_code_val >> (32-MP4_VID_START_CODE_LENGTH)) == MP4_VID_START_CODE) ||
-                          ((start_code_val >> (32-MP4_VOL_START_CODE_LENGTH)) == MP4_VOL_START_CODE)) {
-                   return SNC_VID;
-               } else {
-                   if (i) bibRewindBits(i, buffer, &newError);
-                   continue;               
-               }
-
-           } else if (f_code && ((result >> shift_bits) == 1)) {
-               if (i != 0) {
-                   /* Stuff start code */
-                   bibFlushBits(i, buffer, &numBitsGot, &bitErrorIndication, &newError);
-                   if (newError) {
-                       *error = newError;
-                       return SNC_NO_SYNC;
-                   }
-               }
-               return SNC_VIDPACK;
-           }
-       }
-   }
-
-   return SNC_NO_SYNC;
-}
-
-
-/* {{-output"sncRewindAndSeekNewMPEGSync.txt"}} */
-/*
- * sncRewindAndSeekNewMPEGSync
- *    
- *
- * Parameters:
- *    numBitsToRewind            the number of bits to rewind before seeking
- *                               the synchronization code,
- *                               if negative, a default number of bits is
- *                               rewinded. It is recommended to use 
- *                               the SNC_DEFAULT_REWIND definition to represent
- *                               negative values in order to increase code 
- *                               readability.
- *    buffer                     a pointer to a bit buffer structure
- *    f_code                     f_code of the last P-vop
- *    error                      error code
- *
- * Function:
- *    This function is intended to be called after bit error detection.
- *    It rewinds some (already read) bits in order not to miss any sync code.
- *    Then, this function finds the next GOV, VOP or Video Packet start code
- *    which is not within the rewinded bits. The function discards the bits 
- *    before the synchronization code but does not remove the found code from 
- *    the buffer.
- *
- *
- * Returns:
- *    SNC_NO_SYNC                if no sync code was found and 
- *                               no more bits are available
- *    SNC_GOV                    if GOV start code is found
- *    SNC_VOP                    if VOP start code is found
- *    SNC_VIDPACK                if Video Packet start code is found
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- *    
- */
-
-int sncRewindAndSeekNewMPEGSync(int numBitsToRewind, bibBuffer_t *buffer,
-                                int f_code, int16 *error)
-/* {{-output"sncRewindAndSeekNewMPEGSync.txt"}} */
-{
-   int sncCode;                     /* found sync code */
-   u_int32 numRewindableBits;       /* number of bits which can be rewinded */
-   u_int32 bitPosBeforeRewinding;   /* initial buffer bit index */
-   u_int32 syncStartBitPos;         /* 1st bit index in found sync code */
-   u_int32 syncEndBitPos;
-    int nb = 0;
-    int bei = 0;
-
-   *error = 0;
-
-   /* If default number of rewinded bits requested */
-   if (numBitsToRewind < 0)
-      /* 32 bits is considered to be enough */
-      numBitsToRewind = 32;
-
-   numRewindableBits = bibNumberOfRewBits(buffer);
-
-   if (numRewindableBits < (u_int32) numBitsToRewind)
-      numBitsToRewind = (int) numRewindableBits;
-
-   bitPosBeforeRewinding = bibNumberOfFlushedBits(buffer);
-
-   if (numBitsToRewind) bibRewindBits(numBitsToRewind, buffer, error);
-   if (*error)
-      return SNC_NO_SYNC;
-
-   /* Loop */
-   do {
-
-      /* Seek the next synchronization code */
-      sncCode = sncSeekMPEGStartCode (buffer, f_code, 0 /* this method used with DP and VP => VP resync is relevant */, 0, error);
-      if (*error)
-         return sncCode;
-
-      syncStartBitPos = bibNumberOfFlushedBits(buffer);
-
-      syncEndBitPos = syncStartBitPos + 
-                      (u_int32) ((sncCode == SNC_VIDPACK) ? (16 + f_code) : 32);
-
-      if (syncEndBitPos <= bitPosBeforeRewinding)
-          bibFlushBits( 1, buffer, &nb, &bei, error );
-
-   /* While the found sync code has been previously read */
-   } while (syncEndBitPos <= bitPosBeforeRewinding);
-
-   return sncCode;
-}
-
-/* {{-output"sncSeekMPEGSync.txt"}} */
-/*
- * sncSeekMPEGSync
- *    
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    f_code                     f_code of the last P-vop
- *    error                      error code
- *
- * Function:
- *    Then, this function finds the next GOV, VOP or Video Packet start code
- *    from the buffer. The function discards the bits before the sync code
- *    but does not remove the found code from the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if no sync code was found and 
- *                               no more bits are available
- *    SNC_GOV                    if GOV start code is found
- *    SNC_VOP                    if VOP start code is found
- *    SNC_VOS                    if VOS start code is found
- *    SNC_VIDPACK                if Video Packet start code is found
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- */
-
-int sncSeekMPEGSync(bibBuffer_t *buffer, int f_code, int16 *error)
-/* {{-output"sncSeekMPEGSync.txt"}} */
-{
-   u_int32 result;
-   int numBitsGot, shift_bits;
-   int16 newError = 0;
-   int bitErrorIndication = 0;
-
-   shift_bits = 32-(16+f_code);
-
-   for (;;) {
-       
-       bitErrorIndication = 0;
-
-       result = bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-
-      
-       if (newError == ERR_BIB_NOT_ENOUGH_DATA && numBitsGot) {
-           /* Use the available bits */
-           result <<= (32 - numBitsGot);
-           newError = 0;
-       } else if (newError) {
-           deb("sncSeekSync: ERROR - bibShowBits failed.\n");
-           *error = newError;
-           return SNC_NO_SYNC;
-       }
-
-       if (result == MP4_GROUP_START_CODE)
-           return SNC_GOV;
-       else if (result == MP4_VOP_START_CODE)
-           return SNC_VOP;
-       else if (result == MP4_VOS_START_CODE)
-           return SNC_VOS;
-       else if (result == MP4_EOB_CODE)
-           return SNC_EOB;
-       else if (f_code && ((result >> shift_bits) == 1))
-           return SNC_VIDPACK;
-       else if ( buffer->error )
-          {
-          // out of bits
-          *error = (int16)buffer->error;
-          return SNC_NO_SYNC;
-          }
-
-       
-       bibFlushBits(1, buffer, &numBitsGot, &bitErrorIndication, error);
-   }
-}
-
-   /* {{-output"sncSeekMPEGStartCode.txt"}} */
-/*
- * sncSeekMPEGStartCode
- *    
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    f_code                     f_code of the last P-vop
- *    skipVPSync                 nonzero if Video Packet sync codes can be skipped
- *    error                      error code
- *
- * Function:
- *    This function finds the next GOV, VOP or Video Packet start code
- *    from the buffer in byte-aligned positions. The function discards the bits before the sync code
- *    but does not remove the found code from the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if no sync code was found and 
- *                               no more bits are available
- *    SNC_GOV                    if GOV start code is found
- *    SNC_VOP                    if VOP start code is found
- *    SNC_VOS                    if VOS start code is found
- *    SNC_VIDPACK                if Video Packet start code is found
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- */
-
-int sncSeekMPEGStartCode(bibBuffer_t *buffer, int f_code, int skipVPSync, int checkUD, int16 *error)
-/* {{-output"sncSeekMPEGSync.txt"}} */
-{
-  u_int32 result;
-  int numBitsGot, shift_bits;
-  int16 newError = 0;
-  int bitErrorIndication = 0;
-  int flush = 8;
-  const u_int32 MAX_MPEG4_START_CODE = 0x000001ff;
-  shift_bits = 32-(16+f_code);
-  
-  /* start codes are always byte aligned */
-  /* move to the next byte aligned position, if not already there */
-  if (buffer->bitIndex != 7)
-  {
-    bibForwardBits(buffer->bitIndex + 1, buffer); 
-  }
-  
-  for (;;) 
-  {
-    bitErrorIndication = 0;
-    result = bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-    
-
-    if ( buffer->error )
-      {
-      // out of bits
-      *error = (int16)buffer->error;
-      return SNC_NO_SYNC;
-      }
-
-    /* don't check all start codes, if it is not one of them */
-    if (result <= MAX_MPEG4_START_CODE)
-    {
-      if (result == MP4_GROUP_START_CODE)
-        return SNC_GOV;
-      else if (result == MP4_VOP_START_CODE)
-        return SNC_VOP;
-      else if (result == MP4_VOS_START_CODE)
-        return SNC_VOS;
-      else if (result == MP4_EOB_CODE)
-        return SNC_EOB;
-      else if ( checkUD && (result == MP4_USER_DATA_START_CODE) )
-      	return SNC_USERDATA;
-      
-    }
-    else if (!skipVPSync && f_code && ((result >> shift_bits) == 1))
-        {
-        return SNC_VIDPACK;
-        }
-
-    // we continue here after either if all the if-else's inside the if above are false or if the last else-if is false
-
-    // Note! the following optimization is based on MPEG-4 sync code prefix 0x000001. It doesn't work with any other prefixes.
-    if ( !skipVPSync )
-        {
-        flush = 8;
-        // a small optimization could be reached also with video packet sync markers, but is probably not worth the effort since 
-        // it seems that it could be used to shift at most 16 bits at least in cases with typical f_code values
-        // idea:
-        //  at least if fcode == 15, possible vp resync markers are in the form
-        //  00008xxx, 00009xxx, 0000axxx, 0000bxxx, 0000cxxx, 0000dxxx, 0000exxx, 0000fxxx
-        //  the shifting above already removes the 15 lowest bits => 16th bit must be 1 and 16 highest bits
-        //  should be 0
-        //  in the old way, the sync code from 00008xxx is found in the following steps
-        //  8xxxyyyy, 008xxxyy, => match
-        //  hence we can skip 16 bits (or f-code dependent nr of bits) if 
-        //    a) 32nd bit is 1
-        //  If 32nd bit is 0, we can skip the 16-(nr of successive 0-MSB bits)
-        }
-        
-    // then check for the other sync codes
-    
-    // the 1st check here is needed to optimize the checking: in hopeless cases only a single check is needed
-    else if ( (result & 0x000000ff) <= 1 )
-        {
-        // the 1st check is needed to optimize the checking: in hopeless cases only a single check is needed
-        if ( ((result & 0x000000ff ) == 1) && ((result & 0x00ffff00 ) > 0))
-            {
-            // yyxxxx01, where one of the x != 0 => hopeless
-            flush = 32;
-            }
-        else if ( (result & 0x0000ffff ) == 0 )
-            {
-            // xxxx0000 => could be the 1st 2 bytes of sync code
-            flush = 16;
-            }
-        else if ( (result & 0x000000ff) == 0 )
-            {
-            // yyyyxx00, where xx != 00 (checked above), could be the 1st byte of sync code
-            flush = 24;
-            }
-        else if ( (result & 0x00ffffff) == 1 )
-            {
-            // xx000001 => shift 1 byte
-            flush = 8;
-            }
-        else
-            {
-            // this looks duplicate to the 1st one, but is kept here for simplicity. The 1st one is there since it is the most probable and
-            // hence most cases fall under it. If it was not there, then in most cases all the if's were evaluated and that means extra processing
-            flush = 32;
-            }
-        }
-    else
-        {
-        // hopeless
-        flush = 32;
-        }
-
-    // flush bits
-    bibFlushBits(flush, buffer, &numBitsGot, &bitErrorIndication, error);
-    }
-}
-
-
-/* {{-output"sncSeekBitPattern.txt"}} */
-/*
- * sncSeekBitPattern
- *    
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    error                      error code
- *    BitPattern                 to bit pattern to be found
- *    BitPatternLength           length of the bit pattern to be found
- *
- * Function:
- *    This function finds the next occurance of the given BitPattern 
- *    from the buffer. The function discards the bits before the BitPattern
- *    but does not remove the found code from the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if the bit pattern was not found and 
- *                               no more bits are available
- *    SNC_PATTERN                if the BitPattern is found
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- */
-
-int sncSeekBitPattern(bibBuffer_t *buffer, u_int32 BitPattern, int BitPatternLength, int16 *error)
-/* {{-output"sncSeekBitPattern.txt"}} */
-{
-   u_int32 result;
-   int numBitsGot;
-   int16 newError = 0;
-   int bitErrorIndication = 0;
-
-   for (;;) {
-       
-       bitErrorIndication = 0;
-
-       result = bibShowBits(32, buffer, &numBitsGot, &bitErrorIndication, &newError);
-
-       if (newError == ERR_BIB_NOT_ENOUGH_DATA && numBitsGot >= BitPatternLength) {
-           /* Use the available bits */
-           result <<= (32 - numBitsGot);
-           newError = 0;
-       } else if (newError) {
-           deb("sncSeekBitPattern: ERROR - bibShowBits failed.\n");
-           *error = newError;
-           return SNC_NO_SYNC;
-       }
-
-       if ((result >> (32 - BitPatternLength)) == BitPattern)
-           return SNC_PATTERN;
-       else if (result == MP4_GROUP_START_CODE)
-           return SNC_GOV;
-       else if (result == MP4_VOP_START_CODE)
-           return SNC_VOP;
-       else if (result == MP4_EOB_CODE)
-           return SNC_EOB;
-       else if ( buffer->error )
-          {
-          // out of bits
-          *error = (int16)buffer->error;
-          return SNC_NO_SYNC;
-          }
-       
-       bibFlushBits(1, buffer, &numBitsGot, &bitErrorIndication, error);
-   }
-}
-
-/* {{-output"sncRewindStuffing.txt"}} */
-/*
- * sncRewindStuffing
- *    
- *
- * Parameters:
- *    buffer                     a pointer to a bit buffer structure
- *    error                      error code
- *
- * Function:
- *    This function recognizes and rewinds the stuffing bits (1..8) from
- *    the current position of the buffer.
- *
- * Returns:
- *    SNC_NO_SYNC                if the stuffing was not found
- *    SNC_PATTERN                if the stuffing has been rewinded successfully
- *
- * Error codes:
- *    Error codes returned by bibFlushBits/bibGetBits/bibShowBits.
- *
- *    
- */
-
-int sncRewindStuffing(bibBuffer_t *buffer, int16 *error)
-/* {{-output"sncRewindStuffing.txt"}} */
-{
-   u_int32 result;
-   int numBitsGot, i;
-   int16 newError = 0;
-   int bitErrorIndication = 0;
-
-   bibRewindBits(8, buffer, &newError);
-   result = bibGetBits(8, buffer, &numBitsGot, &bitErrorIndication, &newError);
-   if (newError) {
-       deb("sncRewindStuffing: ERROR - bibShowBits failed.\n");
-       *error = newError;
-       return SNC_NO_SYNC;
-   }
-
-   for(i = 1; i <= 8; i++) {       
-       /* if stuffing is correct */
-       if ((result & (1 << (i-1))) == 0) {
-           bibRewindBits(i, buffer, &newError);
-           return SNC_PATTERN;
-       }
-   }
-
-   return SNC_NO_SYNC;
-}
-// End of File