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

📄 slice.c

📁 mpeg2 decoder filter过滤服务端
💻 C
📖 第 1 页 / 共 5 页
字号:
#undef bit_ptr#define MOTION_CALL(routine,direction)				\do {								\    if ((direction) & MACROBLOCK_MOTION_FORWARD)		\	routine (decoder, &(decoder->f_motion), mpeg2_mc.put);	\    if ((direction) & MACROBLOCK_MOTION_BACKWARD)		\	routine (decoder, &(decoder->b_motion),			\		 ((direction) & MACROBLOCK_MOTION_FORWARD ?	\		  mpeg2_mc.avg : mpeg2_mc.put));		\} while (0)#define NEXT_MACROBLOCK							\do {									\    decoder->offset += 16;						\    if (decoder->offset == decoder->width) {				\	do { /* just so we can use the break statement */		\	    if (decoder->convert) {					\		decoder->convert (decoder->convert_id, decoder->dest,	\				  decoder->v_offset);			\		if (decoder->coding_type == B_TYPE)			\		    break;						\	    }								\	    decoder->dest[0] += decoder->slice_stride;			\	    decoder->dest[1] += decoder->slice_uv_stride;		\	    decoder->dest[2] += decoder->slice_uv_stride;		\	} while (0);							\	decoder->v_offset += 16;					\	if (decoder->v_offset > decoder->limit_y) {			\	    if (mpeg2_cpu_state_restore)				\		mpeg2_cpu_state_restore (&cpu_state);			\	    return;							\	}								\	decoder->offset = 0;						\    }									\} while (0)void mpeg2_init_fbuf (mpeg2_decoder_t * decoder, uint8_t * current_fbuf[3],		      uint8_t * forward_fbuf[3], uint8_t * backward_fbuf[3]){    int offset, stride, height, bottom_field;    stride = decoder->stride_frame;    bottom_field = (decoder->picture_structure == BOTTOM_FIELD);    offset = bottom_field ? stride : 0;    height = decoder->height;    decoder->picture_dest[0] = current_fbuf[0] + offset;    decoder->picture_dest[1] = current_fbuf[1] + (offset >> 1);    decoder->picture_dest[2] = current_fbuf[2] + (offset >> 1);    decoder->f_motion.ref[0][0] = forward_fbuf[0] + offset;    decoder->f_motion.ref[0][1] = forward_fbuf[1] + (offset >> 1);    decoder->f_motion.ref[0][2] = forward_fbuf[2] + (offset >> 1);    decoder->b_motion.ref[0][0] = backward_fbuf[0] + offset;    decoder->b_motion.ref[0][1] = backward_fbuf[1] + (offset >> 1);    decoder->b_motion.ref[0][2] = backward_fbuf[2] + (offset >> 1);    if (decoder->picture_structure != FRAME_PICTURE) {	decoder->dmv_offset = bottom_field ? 1 : -1;	decoder->f_motion.ref2[0] = decoder->f_motion.ref[bottom_field];	decoder->f_motion.ref2[1] = decoder->f_motion.ref[!bottom_field];	decoder->b_motion.ref2[0] = decoder->b_motion.ref[bottom_field];	decoder->b_motion.ref2[1] = decoder->b_motion.ref[!bottom_field];	offset = stride - offset;	if (decoder->second_field && (decoder->coding_type != B_TYPE))	    forward_fbuf = current_fbuf;	decoder->f_motion.ref[1][0] = forward_fbuf[0] + offset;	decoder->f_motion.ref[1][1] = forward_fbuf[1] + (offset >> 1);	decoder->f_motion.ref[1][2] = forward_fbuf[2] + (offset >> 1);	decoder->b_motion.ref[1][0] = backward_fbuf[0] + offset;	decoder->b_motion.ref[1][1] = backward_fbuf[1] + (offset >> 1);	decoder->b_motion.ref[1][2] = backward_fbuf[2] + (offset >> 1);	stride <<= 1;	height >>= 1;    }    decoder->stride = stride;    decoder->uv_stride = stride >> 1;    decoder->slice_stride = 16 * stride;    decoder->slice_uv_stride =	decoder->slice_stride >> (2 - decoder->chroma_format);    decoder->limit_x = 2 * decoder->width - 32;    decoder->limit_y_16 = 2 * height - 32;    decoder->limit_y_8 = 2 * height - 16;    decoder->limit_y = height - 16;    if (decoder->mpeg1) {	decoder->motion_parser[0] = motion_zero_420;	decoder->motion_parser[MC_FRAME] = motion_mp1;	decoder->motion_parser[4] = motion_reuse_420;    } else if (decoder->picture_structure == FRAME_PICTURE) {	if (decoder->chroma_format == 0) {	    decoder->motion_parser[0] = motion_zero_420;	    decoder->motion_parser[MC_FIELD] = motion_fr_field_420;	    decoder->motion_parser[MC_FRAME] = motion_fr_frame_420;	    decoder->motion_parser[MC_DMV] = motion_fr_dmv_420;	    decoder->motion_parser[4] = motion_reuse_420;	} else if (decoder->chroma_format == 1) {	    decoder->motion_parser[0] = motion_zero_422;	    decoder->motion_parser[MC_FIELD] = motion_fr_field_422;	    decoder->motion_parser[MC_FRAME] = motion_fr_frame_422;	    decoder->motion_parser[MC_DMV] = motion_fr_dmv_422;	    decoder->motion_parser[4] = motion_reuse_422;	} else {	    decoder->motion_parser[0] = motion_zero_444;	    decoder->motion_parser[MC_FIELD] = motion_fr_field_444;	    decoder->motion_parser[MC_FRAME] = motion_fr_frame_444;	    decoder->motion_parser[MC_DMV] = motion_fr_dmv_444;	    decoder->motion_parser[4] = motion_reuse_444;	}    } else {	if (decoder->chroma_format == 0) {	    decoder->motion_parser[0] = motion_zero_420;	    decoder->motion_parser[MC_FIELD] = motion_fi_field_420;	    decoder->motion_parser[MC_16X8] = motion_fi_16x8_420;	    decoder->motion_parser[MC_DMV] = motion_fi_dmv_420;	    decoder->motion_parser[4] = motion_reuse_420;	} else if (decoder->chroma_format == 1) {	    decoder->motion_parser[0] = motion_zero_422;	    decoder->motion_parser[MC_FIELD] = motion_fi_field_422;	    decoder->motion_parser[MC_16X8] = motion_fi_16x8_422;	    decoder->motion_parser[MC_DMV] = motion_fi_dmv_422;	    decoder->motion_parser[4] = motion_reuse_422;	} else {	    decoder->motion_parser[0] = motion_zero_444;	    decoder->motion_parser[MC_FIELD] = motion_fi_field_444;	    decoder->motion_parser[MC_16X8] = motion_fi_16x8_444;	    decoder->motion_parser[MC_DMV] = motion_fi_dmv_444;	    decoder->motion_parser[4] = motion_reuse_444;	}    }}static inline int slice_init (mpeg2_decoder_t * const decoder, int code){#define bit_buf (decoder->bitstream_buf)#define bits (decoder->bitstream_bits)#define bit_ptr (decoder->bitstream_ptr)    int offset;    const MBAtab * mba;    decoder->dc_dct_pred[0] = decoder->dc_dct_pred[1] =	decoder->dc_dct_pred[2] = 16384;    decoder->f_motion.pmv[0][0] = decoder->f_motion.pmv[0][1] = 0;    decoder->f_motion.pmv[1][0] = decoder->f_motion.pmv[1][1] = 0;    decoder->b_motion.pmv[0][0] = decoder->b_motion.pmv[0][1] = 0;    decoder->b_motion.pmv[1][0] = decoder->b_motion.pmv[1][1] = 0;    if (decoder->vertical_position_extension) {	code += UBITS (bit_buf, 3) << 7;	DUMPBITS (bit_buf, bits, 3);    }    decoder->v_offset = (code - 1) * 16;    offset = 0;    if (!(decoder->convert) || decoder->coding_type != B_TYPE)	offset = (code - 1) * decoder->slice_stride;    decoder->dest[0] = decoder->picture_dest[0] + offset;    offset >>= (2 - decoder->chroma_format);    decoder->dest[1] = decoder->picture_dest[1] + offset;    decoder->dest[2] = decoder->picture_dest[2] + offset;    get_quantizer_scale (decoder);    /* ignore intra_slice and all the extra data */    while (bit_buf & 0x80000000) {	DUMPBITS (bit_buf, bits, 9);	NEEDBITS (bit_buf, bits, bit_ptr);    }    /* decode initial macroblock address increment */    offset = 0;    while (1) {	if (bit_buf >= 0x08000000) {	    mba = MBA_5 + (UBITS (bit_buf, 6) - 2);	    break;	} else if (bit_buf >= 0x01800000) {	    mba = MBA_11 + (UBITS (bit_buf, 12) - 24);	    break;	} else switch (UBITS (bit_buf, 12)) {	case 8:		/* macroblock_escape */	    offset += 33;	    DUMPBITS (bit_buf, bits, 11);	    NEEDBITS (bit_buf, bits, bit_ptr);	    continue;	case 15:	/* macroblock_stuffing (MPEG1 only) */	    bit_buf &= 0xfffff;	    DUMPBITS (bit_buf, bits, 11);	    NEEDBITS (bit_buf, bits, bit_ptr);	    continue;	default:	/* error */	    return 1;	}    }    DUMPBITS (bit_buf, bits, mba->len + 1);    decoder->offset = (offset + mba->mba) << 4;    while (decoder->offset - decoder->width >= 0) {	decoder->offset -= decoder->width;	if (!(decoder->convert) || decoder->coding_type != B_TYPE) {	    decoder->dest[0] += decoder->slice_stride;	    decoder->dest[1] += decoder->slice_uv_stride;	    decoder->dest[2] += decoder->slice_uv_stride;	}	decoder->v_offset += 16;    }    if (decoder->v_offset > decoder->limit_y)	return 1;    return 0;#undef bit_buf#undef bits#undef bit_ptr}void mpeg2_slice (mpeg2_decoder_t * const decoder, const int code,		  const uint8_t * const buffer){#define bit_buf (decoder->bitstream_buf)#define bits (decoder->bitstream_bits)#define bit_ptr (decoder->bitstream_ptr)    cpu_state_t cpu_state;    bitstream_init (decoder, buffer);    if (slice_init (decoder, code))	return;    if (mpeg2_cpu_state_save)	mpeg2_cpu_state_save (&cpu_state);    while (1) {	int macroblock_modes;	int mba_inc;	const MBAtab * mba;	NEEDBITS (bit_buf, bits, bit_ptr);	macroblock_modes = get_macroblock_modes (decoder);	/* maybe integrate MACROBLOCK_QUANT test into get_macroblock_modes ? */	if (macroblock_modes & MACROBLOCK_QUANT)	    get_quantizer_scale (decoder);	if (macroblock_modes & MACROBLOCK_INTRA) {	    int DCT_offset, DCT_stride;	    int offset;	    uint8_t * dest_y;	    if (decoder->concealment_motion_vectors) {		if (decoder->picture_structure == FRAME_PICTURE)		    motion_fr_conceal (decoder);		else		    motion_fi_conceal (decoder);	    } else {		decoder->f_motion.pmv[0][0] = decoder->f_motion.pmv[0][1] = 0;		decoder->f_motion.pmv[1][0] = decoder->f_motion.pmv[1][1] = 0;		decoder->b_motion.pmv[0][0] = decoder->b_motion.pmv[0][1] = 0;		decoder->b_motion.pmv[1][0] = decoder->b_motion.pmv[1][1] = 0;	    }	    if (macroblock_modes & DCT_TYPE_INTERLACED) {		DCT_offset = decoder->stride;		DCT_stride = decoder->stride * 2;	    } else {		DCT_offset = decoder->stride * 8;		DCT_stride = decoder->stride;	    }	    offset = decoder->offset;	    dest_y = decoder->dest[0] + offset;	    slice_intra_DCT (decoder, 0, dest_y, DCT_stride);	    slice_intra_DCT (decoder, 0, dest_y + 8, DCT_stride);	    slice_intra_DCT (decoder, 0, dest_y + DCT_offset, DCT_stride);	    slice_intra_DCT (decoder, 0, dest_y + DCT_offset + 8, DCT_stride);	    if (likely (decoder->chroma_format == 0)) {		slice_intra_DCT (decoder, 1, decoder->dest[1] + (offset >> 1),				 decoder->uv_stride);		slice_intra_DCT (decoder, 2, decoder->dest[2] + (offset >> 1),				 decoder->uv_stride);		if (decoder->coding_type == D_TYPE) {		    NEEDBITS (bit_buf, bits, bit_ptr);		    DUMPBITS (bit_buf, bits, 1);		}	    } else if (likely (decoder->chroma_format == 1)) {		uint8_t * dest_u = decoder->dest[1] + (offset >> 1);		uint8_t * dest_v = decoder->dest[2] + (offset >> 1);		DCT_stride >>= 1;		DCT_offset >>= 1;		slice_intra_DCT (decoder, 1, dest_u, DCT_stride);		slice_intra_DCT (decoder, 2, dest_v, DCT_stride);		slice_intra_DCT (decoder, 1, dest_u + DCT_offset, DCT_stride);		slice_intra_DCT (decoder, 2, dest_v + DCT_offset, DCT_stride);	    } else {		uint8_t * dest_u = decoder->dest[1] + offset;		uint8_t * dest_v = decoder->dest[2] + offset;		slice_intra_DCT (decoder, 1, dest_u, DCT_stride);		slice_intra_DCT (decoder, 2, dest_v, DCT_stride);		slice_intra_DCT (decoder, 1, dest_u + DCT_offset, DCT_stride);		slice_intra_DCT (decoder, 2, dest_v + DCT_offset, DCT_stride);		slice_intra_DCT (decoder, 1, dest_u + 8, DCT_stride);		slice_intra_DCT (decoder, 2, dest_v + 8, DCT_stride);		slice_intra_DCT (decoder, 1, dest_u + DCT_offset + 8,				 DCT_stride);		slice_intra_DCT (decoder, 2, dest_v + DCT_offset + 8,				 DCT_stride);	    }	} else {	    motion_parser_t * parser;	    parser =		decoder->motion_parser[macroblock_modes >> MOTION_TYPE_SHIFT];	    MOTION_CALL (parser, macroblock_modes);	    if (macroblock_modes & MACROBLOCK_PATTERN) {		int coded_block_pattern;		int DCT_offset, DCT_stride;		if (macroblock_modes & DCT_TYPE_INTERLACED) {		    DCT_offset = decoder->stride;		    DCT_stride = decoder->stride * 2;		} else {		    DCT_offset = decoder->stride * 8;		    DCT_stride = decoder->stride;		}		coded_block_pattern = get_coded_block_pattern (decoder);		if (likely (decoder->chroma_format == 0)) {		    int offset = decoder->offset;		    uint8_t * dest_y = decoder->dest[0] + offset;		    if (coded_block_pattern & 1)			slice_non_intra_DCT (decoder, 0, dest_y, DCT_stride);		    if (coded_block_pattern & 2)			slice_non_intra_DCT (decoder, 0, dest_y + 8,					     DCT_stride);		    if (coded_block_pattern & 4)			slice_non_intra_DCT (decoder, 0, dest_y + DCT_offset,					     DCT_stride);		    if (coded_block_pattern & 8)			slice_non_intra_DCT (decoder, 0,					     dest_y + DCT_offset + 8,					     DCT_stride);		    if (coded_block_pattern & 16)			slice_non_intra_DCT (decoder, 1,					     decoder->dest[1] + (offset >> 1),					     decoder->uv_stride);		    if (coded_block_pattern & 32)			slice_non_intra_DCT (decoder, 2,					     decoder->dest[2] + (offset >> 1),					     decoder->uv_stride);		} else if (likely (decoder->chroma_format == 1)) {		    int offset;		    uint8_t * dest_y;		    coded_block_pattern |= bit_buf & (3 << 30);		    DUMPBITS (bit_buf, bits, 2);		    offset = decoder->offset;		    dest_y = decoder->dest[0] + offset;		    if (coded_block_pattern & 1)			slice_non_intra_DCT (decoder, 0, dest_y, DCT_stride);		    if (coded_block_pattern & 2)			slice_non_intra_DCT (decoder, 0, dest_y + 8,					     DCT_stride);		    if (coded_block_pattern & 4)			slice_non_intra_DCT (decoder, 0, dest_y + DCT_offset,					     DCT_stride);		    if (coded_block_pattern & 8)			slice_non_intra_DCT (decoder, 0,					     dest_y + DCT_offset + 8,					     DCT_stride);		    DCT_stride >>= 1;		    DCT_offset = (DCT_offset + offset) >> 1;		    if

⌨️ 快捷键说明

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