void ReadSequenceHeader::QuantizerMatrixReader::Execute(void* state, Framework::CBitStream& stream) { while(1) { if(m_currentIndex == 0x40) return; m_table[m_currentIndex] = static_cast<uint8>(stream.GetBits_MSBF(8)); m_currentIndex++; } }
void ReadMacroblock::Execute(void* context, Framework::CBitStream& stream) { MPEG_VIDEO_STATE* state(reinterpret_cast<MPEG_VIDEO_STATE*>(context)); PICTURE_HEADER& pictureHeader(state->pictureHeader); BLOCK_DECODER_STATE& decoderState(state->blockDecoderState); PICTURE_CODING_EXTENSION& pictureCodingExtension(state->pictureCodingExtension); SEQUENCE_HEADER& sequenceHeader(state->sequenceHeader); while(1) { switch(m_programState) { case STATE_INIT: goto Label_Init; case STATE_ESCAPE: goto Label_Escape; case STATE_SKIPESCAPE: goto Label_SkipEscape; case STATE_READMBINCREMENT: goto Label_ReadMbIncrement; case STATE_READMBMODES: goto Label_ReadMbModes; case STATE_READDCTTYPE: goto Label_ReadDctType; case STATE_CHECKMBMODES: goto Label_CheckMbModes; case STATE_CHECKMBMODES_QSC: goto Label_CheckMbModes_Qsc; case STATE_CHECKMBMODES_FWM_INIT: goto Label_CheckMbModes_Fwm_Init; case STATE_CHECKMBMODES_FWM: goto Label_CheckMbModes_Fwm; case STATE_CHECKMBMODES_BKM_INIT: goto Label_CheckMbModes_Bkm_Init; case STATE_CHECKMBMODES_BKM: goto Label_CheckMbModes_Bkm; case STATE_CHECKMBMODES_CBP: goto Label_CheckMbModes_Cbp; case STATE_READBLOCKINIT: goto Label_ReadBlockInit; case STATE_READBLOCK: goto Label_ReadBlock; default: assert(0); } Label_Init: decoderState.mbIncrement = 0; m_programState = STATE_ESCAPE; continue; Label_Escape: { uint32 escapeSequence = stream.PeekBits_MSBF(11); if(escapeSequence != 0x08) { m_programState = STATE_READMBINCREMENT; } else { m_programState = STATE_SKIPESCAPE; } } continue; Label_SkipEscape: stream.Advance(11); #ifdef _DECODE_LOGGING CLog::GetInstance().Print(DECODE_LOG_NAME, "Symbol(%d, 'mb increment') = %d\r\n", g_currentVdec++, 35); #endif decoderState.mbIncrement += 33; m_programState = STATE_ESCAPE; continue; Label_ReadMbIncrement: uint32 increment = MPEG2::CMacroblockAddressIncrementTable::GetInstance()->GetSymbol(&stream); #ifdef _DECODE_LOGGING CLog::GetInstance().Print(DECODE_LOG_NAME, "Symbol(%d, 'mb increment') = %d\r\n", g_currentVdec++, increment); #endif decoderState.mbIncrement += increment; if(decoderState.mbIncrement != 1) { decoderState.currentMbAddress += (decoderState.mbIncrement - 1); decoderState.mbIncrement = 1; { int16 resetValue = 0; switch(pictureCodingExtension.intraDcPrecision) { case 0: resetValue = 128; break; case 1: resetValue = 256; break; case 2: resetValue = 512; break; default: resetValue = 0; assert(0); break; } decoderState.dcPredictor[0] = resetValue; decoderState.dcPredictor[1] = resetValue; decoderState.dcPredictor[2] = resetValue; } if((pictureHeader.pictureCodingType == PICTURE_TYPE_P)) { decoderState.forwardMotionVector[0] = 0; decoderState.forwardMotionVector[1] = 0; } } m_macroblockModesReader.Reset(); m_programState = STATE_READMBMODES; continue; Label_ReadMbModes: m_macroblockModesReader.Execute(context, stream); #ifdef _DECODE_LOGGING CLog::GetInstance().Print(DECODE_LOG_NAME, "Symbol(%d, 'mb type') = %d\r\n", g_currentVdec++, decoderState.macroblockType); #endif if( (!pictureCodingExtension.framePredFrameDct) && (decoderState.macroblockType & (MACROBLOCK_MODE_BLOCK_PATTERN | MACROBLOCK_MODE_INTRA))) { m_programState = STATE_READDCTTYPE; } else { m_programState = STATE_CHECKMBMODES; } continue; Label_ReadDctType: decoderState.dctType = static_cast<uint8>(stream.GetBits_MSBF(1)); m_programState = STATE_CHECKMBMODES; continue; Label_CheckMbModes: m_programState = STATE_CHECKMBMODES_QSC; continue; Label_CheckMbModes_Qsc: if(decoderState.macroblockType & MACROBLOCK_MODE_QUANT) { decoderState.quantizerScaleCode = static_cast<uint8>(stream.GetBits_MSBF(5)); } m_programState = STATE_CHECKMBMODES_FWM_INIT; continue; Label_CheckMbModes_Fwm_Init: if(sequenceHeader.isMpeg2) { m_motionVectorsReader.Reset(); m_motionVectorsReader.SetRSizes(pictureCodingExtension.fcode00 - 1, pictureCodingExtension.fcode01 - 1); } else { m_singleMotionVectorReader.Reset(); m_singleMotionVectorReader.SetRSizes(pictureHeader.forwardFCode - 1, pictureHeader.forwardFCode - 1); } m_programState = STATE_CHECKMBMODES_FWM; continue; Label_CheckMbModes_Fwm: if(decoderState.macroblockType & MACROBLOCK_MODE_MOTION_FORWARD) //or intra & concealment motion vectors { if(sequenceHeader.isMpeg2) { m_motionVectorsReader.SetMotionVector(decoderState.forwardMotionVector); m_motionVectorsReader.Execute(context, stream); } else { m_singleMotionVectorReader.Execute(context, stream); decoderState.forwardMotionVector[0] = ReadMotionVector::ComputeMotionVector(decoderState.forwardMotionVector[0], decoderState.motionCode[0], decoderState.motionResidual[0], pictureHeader.forwardFCode - 1); decoderState.forwardMotionVector[1] = ReadMotionVector::ComputeMotionVector(decoderState.forwardMotionVector[1], decoderState.motionCode[1], decoderState.motionResidual[1], pictureHeader.forwardFCode - 1); } } m_programState = STATE_CHECKMBMODES_BKM_INIT; continue; Label_CheckMbModes_Bkm_Init: if(sequenceHeader.isMpeg2) { m_motionVectorsReader.Reset(); m_motionVectorsReader.SetRSizes(pictureCodingExtension.fcode10 - 1, pictureCodingExtension.fcode11 - 1); } else { m_singleMotionVectorReader.Reset(); m_singleMotionVectorReader.SetRSizes(pictureHeader.backwardFCode - 1, pictureHeader.backwardFCode - 1); } m_programState = STATE_CHECKMBMODES_BKM; continue; Label_CheckMbModes_Bkm: if(decoderState.macroblockType & MACROBLOCK_MODE_MOTION_BACKWARD) { if(sequenceHeader.isMpeg2) { m_motionVectorsReader.SetMotionVector(decoderState.backwardMotionVector); m_motionVectorsReader.Execute(context, stream); } else { m_singleMotionVectorReader.Execute(context, stream); } } m_programState = STATE_CHECKMBMODES_CBP; continue; Label_CheckMbModes_Cbp: if(decoderState.macroblockType & MACROBLOCK_MODE_BLOCK_PATTERN) { //Need to verify that decoderState.codedBlockPattern = static_cast<uint8>(MPEG2::CCodedBlockPatternTable::GetInstance()->GetSymbol(&stream)); } else { if( (pictureHeader.pictureCodingType == PICTURE_TYPE_I) || (decoderState.macroblockType & MACROBLOCK_MODE_INTRA)) { decoderState.codedBlockPattern = 0x3F; } else { decoderState.codedBlockPattern = 0; } } m_programState = STATE_READBLOCKINIT; continue; Label_ReadBlockInit: m_blockReader.Reset(); #ifdef _DECODE_LOGGING if(decoderState.codedBlockPattern != 0) { static int currentMbIndex = 0; CLog::GetInstance().Print(DECODE_LOG_NAME, "Macroblock(%d, CBP: 0x%0.2X)\r\n", currentMbIndex++, decoderState.codedBlockPattern); } #endif m_programState = STATE_READBLOCK; continue; Label_ReadBlock: m_blockReader.Execute(context, stream); if(!(decoderState.macroblockType & MACROBLOCK_MODE_INTRA)) { int16 resetValue = 0; switch(pictureCodingExtension.intraDcPrecision) { case 0: resetValue = 128; break; case 1: resetValue = 256; break; case 2: resetValue = 512; break; default: resetValue = 0; assert(0); break; } decoderState.dcPredictor[0] = resetValue; decoderState.dcPredictor[1] = resetValue; decoderState.dcPredictor[2] = resetValue; } if((pictureHeader.pictureCodingType == PICTURE_TYPE_P) && !(decoderState.macroblockType & (MACROBLOCK_MODE_INTRA | MACROBLOCK_MODE_MOTION_FORWARD))) { decoderState.forwardMotionVector[0] = 0; decoderState.forwardMotionVector[1] = 0; } if((decoderState.macroblockType & MACROBLOCK_MODE_INTRA) && (pictureCodingExtension.concealmentMotionVectors == 0)) { decoderState.forwardMotionVector[0] = 0; decoderState.forwardMotionVector[1] = 0; decoderState.backwardMotionVector[0] = 0; decoderState.backwardMotionVector[1] = 0; } if(m_OnMacroblockDecodedHandler) { m_OnMacroblockDecodedHandler(state); } decoderState.currentMbAddress += decoderState.mbIncrement; return; } }
void ReadMotionVectors::Execute(void* context, Framework::CBitStream& stream) { MPEG_VIDEO_STATE* state(reinterpret_cast<MPEG_VIDEO_STATE*>(context)); PICTURE_HEADER& pictureHeader(state->pictureHeader); BLOCK_DECODER_STATE& decoderState(state->blockDecoderState); while(1) { switch(m_programState) { case STATE_INIT: goto Label_Init; case STATE_SINGLE_READVECTOR: goto Label_Single_ReadVector; case STATE_DOUBLE_FIRST_READFIELDSELECT: goto Label_Double_First_ReadFieldSelect; case STATE_DOUBLE_FIRST_READVECTOR: goto Label_Double_First_ReadVector; case STATE_DOUBLE_SECOND_READFIELDSELECT: goto Label_Double_Second_ReadFieldSelect; case STATE_DOUBLE_SECOND_READVECTOR: goto Label_Double_Second_ReadVector; case STATE_DONE: goto Label_Done; default: assert(0); } Label_Init: if(decoderState.motionVectorCount == 1) { m_motionVectorReader.Reset(); m_programState = STATE_SINGLE_READVECTOR; } else { m_programState = STATE_DOUBLE_FIRST_READFIELDSELECT; } continue; Label_Single_ReadVector: m_motionVectorReader.Execute(context, stream); m_motionVector[0] = ReadMotionVector::ComputeMotionVector(m_motionVector[0], decoderState.motionCode[0], decoderState.motionResidual[0], m_hrSize); m_motionVector[1] = ReadMotionVector::ComputeMotionVector(m_motionVector[1], decoderState.motionCode[1], decoderState.motionResidual[1], m_vrSize); m_programState = STATE_DONE; continue; Label_Double_First_ReadFieldSelect: { uint8 fieldSelect = static_cast<uint8>(stream.GetBits_MSBF(1)); m_motionVectorReader.Reset(); m_programState = STATE_DOUBLE_FIRST_READVECTOR; } continue; Label_Double_First_ReadVector: m_motionVectorReader.Execute(context, stream); m_programState = STATE_DOUBLE_SECOND_READFIELDSELECT; continue; Label_Double_Second_ReadFieldSelect: { uint8 fieldSelect = static_cast<uint8>(stream.GetBits_MSBF(1)); m_motionVectorReader.Reset(); m_programState = STATE_DOUBLE_SECOND_READVECTOR; } continue; Label_Double_Second_ReadVector: m_motionVectorReader.Execute(context, stream); m_programState = STATE_DONE; continue; Label_Done: return; } }
void ReadSequenceHeader::Execute(void* context, Framework::CBitStream& stream) { MPEG_VIDEO_STATE* state(reinterpret_cast<MPEG_VIDEO_STATE*>(context)); SEQUENCE_HEADER& sequenceHeader(state->sequenceHeader); while(1) { switch(m_programState) { case STATE_INIT: goto Label_Init; case STATE_READSTRUCT: goto Label_ReadStruct; case STATE_CHECKREADINTRAMATRIX: goto Label_CheckReadIntraMatrix; case STATE_READINTRAMATRIX: goto Label_ReadIntraMatrix; case STATE_CHECKREADNONINTRAMATRIX: goto Label_CheckReadNonIntraMatrix; case STATE_READNONINTRAMATRIX: goto Label_ReadNonIntraMatrix; case STATE_DONE: goto Label_Done; default: assert(0); } Label_Init: m_structureReader.Reset(); m_programState = STATE_READSTRUCT; continue; Label_ReadStruct: m_structureReader.Execute(state, stream); m_programState = STATE_CHECKREADINTRAMATRIX; sequenceHeader.macroblockWidth = (sequenceHeader.horizontalSize + 15) / 16; //Need to check interlaced mode, etc. sequenceHeader.macroblockHeight = (sequenceHeader.verticalSize + 15) / 16; sequenceHeader.macroblockMaxAddress = sequenceHeader.macroblockWidth * sequenceHeader.macroblockHeight; continue; Label_CheckReadIntraMatrix: sequenceHeader.loadIntraQuantiserMatrix = static_cast<uint8>(stream.GetBits_MSBF(1)); if(sequenceHeader.loadIntraQuantiserMatrix) { m_quantizerMatrixReader.Reset(); m_quantizerMatrixReader.SetTable(sequenceHeader.intraQuantiserMatrix); m_programState = STATE_READINTRAMATRIX; } else { m_programState = STATE_CHECKREADNONINTRAMATRIX; } continue; Label_ReadIntraMatrix: m_quantizerMatrixReader.Execute(state, stream); m_programState = STATE_CHECKREADNONINTRAMATRIX; continue; Label_CheckReadNonIntraMatrix: sequenceHeader.loadNonIntraQuantiserMatrix = static_cast<uint8>(stream.GetBits_MSBF(1)); if(sequenceHeader.loadNonIntraQuantiserMatrix) { m_quantizerMatrixReader.Reset(); m_quantizerMatrixReader.SetTable(sequenceHeader.nonIntraQuantiserMatrix); m_programState = STATE_READNONINTRAMATRIX; } else { m_programState = STATE_DONE; } continue; Label_ReadNonIntraMatrix: m_quantizerMatrixReader.Execute(state, stream); m_programState = STATE_DONE; continue; Label_Done: return; } }