⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 h263mb.c

📁 Linux下的基于intel的ipp库的h.263解码源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
//  [SAMPLE_STATUS_NOERR]:            Succeeds
//  [SAMPLE_STATUS_BITSTREAM_ERR]:    Stream parsing error occurs
//  [SAMPLE_STATUS_ERR]:              Error occurs during decoding
//
// Notes:   None
******************************************************************************/
sample_status decode_mb_ppic_h263(sample_bitstream    *stream, 
                                  h263_dec_state      *state)
{
    sample_status   ret;
    short           idct_buf[72], *a_idct_buf;
    IppMotionVector chroma_mv;
    int             cbp, predict_type, i;
    int             ref_y_step = state->ref_picture->pic_plane_step[0];
    int             ref_cb_step= state->ref_picture->pic_plane_step[1];
    int             ref_cr_step= state->ref_picture->pic_plane_step[2];
    int             cur_y_step = state->cur_picture->pic_plane_step[0];
    int             cur_cb_step= state->cur_picture->pic_plane_step[1];
    int             cur_cr_step= state->cur_picture->pic_plane_step[2];

    /***********************************************************
    // Parse MB header 
    ***********************************************************/
    ret = parse_mb_header_h263(stream, state);
    if(SAMPLE_STATUS_NOERR != ret) {
        return ret;
    }

    /***********************************************************
    // If MB type is INTER_Q, 
    // update quantization param according to GQUANT and DQUANT 
    ***********************************************************/
    if(H263_INTER_Q == state->mb_type || H263_INTRA_Q == state->mb_type) {
        state->quant = QUANT_CLIP(state->quant+state->dquant);
    }

    /***********************************************************
    // Initialize block pointers 
    ***********************************************************/
    state->cur_block.y_ptr  = state->cur_mb.y_ptr;
    state->cur_block.cb_ptr = state->cur_mb.cb_ptr;
    state->cur_block.cr_ptr = state->cur_mb.cr_ptr;

    state->ref_block.y_ptr  = state->ref_mb.y_ptr;
    state->ref_block.cb_ptr = state->ref_mb.cb_ptr;
    state->ref_block.cr_ptr = state->ref_mb.cr_ptr;

    a_idct_buf = (short*)SAMPLE_ALIGN8(idct_buf);

    /***********************************************************
    // Decode blocks
    ***********************************************************/
    if(state->cod) {
        /* Not Coded, copy from reference blocks */
		ippiCopyMB_H263_8u(state->ref_block.y_ptr, state->cur_block.y_ptr, cur_y_step);
		ippiCopyBlock_H263_8u(state->ref_block.cb_ptr, state->cur_block.cb_ptr, cur_cb_step);
		ippiCopyBlock_H263_8u(state->ref_block.cr_ptr, state->cur_block.cr_ptr, cur_cr_step);

        /* Zero motion vector */
        state->cur_mv[1].dx = 0;
        state->cur_mv[1].dy = 0;

        return SAMPLE_STATUS_NOERR;
    }

    /* Coded */
    if(H263_INTRA == state->mb_type || H263_INTRA_Q == state->mb_type) {
        /* INTRA block */
        state->cur_mv[1].dx = 0;
        state->cur_mv[1].dy = 0;

        return decode_intra_mb_h263(stream, state);

    } else { 
        /* INTER */

        /* Decode MV */
        /* First line of GOB or when GOB header is present, 
        // ippiDecodeMV_TopBorder_H263 is used to decode MV,
        // the rest uses ippiDecodeMV_H263.
        */
        if(state->mb_index < state->mb_per_row || 1 == state->gob_has_header) {
            if(ippStsNoErr != ippiDecodeMV_TopBorder_H263(
                                           &stream->bs_cur_byte, 
                                           &stream->bs_cur_bitoffset, 
                                           state->cur_mv)) {
                return SAMPLE_STATUS_ERR;
            }
        } else {
            if(ippStsNoErr != ippiDecodeMV_H263(
                                           &stream->bs_cur_byte, 
                                           &stream->bs_cur_bitoffset, 
                                           state->cur_mv)) {
                return SAMPLE_STATUS_ERR;
            }
        }

        /* MV for Chominance Blocks */
        chroma_mv.dx = (Ipp16s)(((state->cur_mv[1].dx) >> 1) 
                        + mv_quarter_round_h263[(state->cur_mv[1].dx)&3]);
        chroma_mv.dy = (Ipp16s)(((state->cur_mv[1].dy) >> 1) 
                        + mv_quarter_round_h263[(state->cur_mv[1].dy)&3]);

        /* Prediction */
        state->ref_block.y_ptr  += ((state->cur_mv[1].dx) >> 1);
        state->ref_block.cb_ptr += ((chroma_mv.dx) >> 1);
        state->ref_block.cr_ptr += ((chroma_mv.dx) >> 1);

        if(state->cur_mv[1].dy) {
            state->ref_block.y_ptr += ((state->cur_mv[1].dy) >> 1) * ref_y_step;
            state->ref_block.cb_ptr+= ((chroma_mv.dy) >> 1) * ref_cb_step;
            state->ref_block.cr_ptr+= ((chroma_mv.dy) >> 1) * ref_cr_step;
        }
    
        /* Decode MB */
        /***********************************
        // Luminance Block 
        ***********************************/
        predict_type = (state->cur_mv[1].dx & 0x1) |
                       ((state->cur_mv[1].dy & 0x1) << 1);

        cbp = state->cbpy;

        /* 4 Y blocks */
        for(i=0;i<4;i++) {
            if(cbp & 0x8) {
                if(ippStsNoErr != ippiDecodeBlockCoef_Inter_H263_1u16s(
                                              &stream->bs_cur_byte, 
                                              &stream->bs_cur_bitoffset, 
                                              a_idct_buf,
                                              state->quant) ) {
                    return SAMPLE_STATUS_ERR;
                }
                if(1 == state->rounding_type) {
                    ippiMCReconBlock_RoundOn (state->ref_block.y_ptr, 
                                              ref_y_step,
                                              a_idct_buf,
                                              state->cur_block.y_ptr,
                                              cur_y_step,
                                              predict_type);
                } else {
                    ippiMCReconBlock_RoundOff(state->ref_block.y_ptr, 
                                              ref_y_step,
                                              a_idct_buf,
                                              state->cur_block.y_ptr,
                                              cur_y_step,
                                              predict_type);
                }
            } else {
                if(1 == state->rounding_type) {
                    ippiMCBlock_RoundOn_8u (state->ref_block.y_ptr, 
                                            ref_y_step,
                                            state->cur_block.y_ptr,
                                            cur_y_step,
                                            predict_type);
                } else {
                    ippiMCBlock_RoundOff_8u(state->ref_block.y_ptr, 
                                            ref_y_step,
                                            state->cur_block.y_ptr,
                                            cur_y_step,
                                            predict_type);
                }
            }
            state->cur_block.y_ptr += SAMPLE_VIDEO_BLOCK_SIZE;
            state->ref_block.y_ptr += SAMPLE_VIDEO_BLOCK_SIZE;
            if(i&1) {
                state->cur_block.y_ptr += SAMPLE_VIDEO_BLOCK_SIZE * cur_y_step 
                                          - 2*SAMPLE_VIDEO_BLOCK_SIZE;
                state->ref_block.y_ptr += SAMPLE_VIDEO_BLOCK_SIZE * ref_y_step 
                                          - 2*SAMPLE_VIDEO_BLOCK_SIZE;
            }
            cbp <<= 1;
        }

        /***********************************
        // Chrominance Block 
        ***********************************/
        predict_type = (chroma_mv.dx & 0x1) |((chroma_mv.dy & 0x1) << 1);
        cbp = state->cbpc;

        /* Cb block */
        if(cbp & 0x2) { /* Non-DC coeff exists  */
            if(ippStsNoErr != ippiDecodeBlockCoef_Inter_H263_1u16s(
                                            &stream->bs_cur_byte, 
                                            &stream->bs_cur_bitoffset,
                                            a_idct_buf,
                                            state->quant)) {
                return SAMPLE_STATUS_ERR;
            }
            if(1 == state->rounding_type) {
                ippiMCReconBlock_RoundOn (state->ref_block.cb_ptr, 
                                          ref_cb_step,
                                          a_idct_buf,
                                          state->cur_block.cb_ptr,
                                          cur_cb_step,
                                          predict_type);
            } else {
                ippiMCReconBlock_RoundOff(state->ref_block.cb_ptr, 
                                          ref_cb_step,
                                          a_idct_buf,
                                          state->cur_block.cb_ptr,
                                          cur_cb_step,
                                          predict_type);
            }
        } else {  /* Only DC exists */
            if(1 == state->rounding_type) {
                ippiMCBlock_RoundOn_8u (state->ref_block.cb_ptr, 
                                        ref_cb_step,
                                        state->cur_block.cb_ptr,
                                        cur_cb_step,
                                        predict_type);
            } else {
                ippiMCBlock_RoundOff_8u(state->ref_block.cb_ptr, 
                                        ref_cb_step,
                                        state->cur_block.cb_ptr,
                                        cur_cb_step,
                                        predict_type);
            }
        } /* Cb Block end */

        /* Cr Block */
        if(cbp & 0x1) { /* Non-DC coeff exists  */
            if(ippStsNoErr != ippiDecodeBlockCoef_Inter_H263_1u16s(
                                        &stream->bs_cur_byte, 
                                        &stream->bs_cur_bitoffset,
                                        a_idct_buf,
                                        state->quant)) {
                return SAMPLE_STATUS_ERR;
            }
            if(1 == state->rounding_type) {
                ippiMCReconBlock_RoundOn (state->ref_block.cr_ptr, 
                                          ref_cr_step,
                                          a_idct_buf,
                                          state->cur_block.cr_ptr,
                                          cur_cr_step,
                                          predict_type);
            } else {
                ippiMCReconBlock_RoundOff(state->ref_block.cr_ptr, 
                                          ref_cr_step,
                                          a_idct_buf,
                                          state->cur_block.cr_ptr,
                                          cur_cr_step,
                                          predict_type);
            }
        } else {  /* Only DC exists */
            if(1 == state->rounding_type) {
                ippiMCBlock_RoundOn_8u (state->ref_block.cr_ptr, 
                                        ref_cr_step,
                                        state->cur_block.cr_ptr,
                                        cur_cr_step,
                                        predict_type);
            } else {
                ippiMCBlock_RoundOff_8u(state->ref_block.cr_ptr, 
                                        ref_cr_step,
                                        state->cur_block.cr_ptr,
                                        cur_cr_step,
                                        predict_type);
            }
        } /* Cr block end */
    } /* INTER */

    return SAMPLE_STATUS_NOERR;
}


/* EOF */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -