📄 mheaders.c
字号:
/* Time code seconds. */ Bitio_Write(bbPtr, tc_sec, 6); /* Time code pictures. */ Bitio_Write(bbPtr, tc_pict, 6); /* Closed gop flag. */ if (closed_gop) { Bitio_Write(bbPtr, 0x01, 1); } else { Bitio_Write(bbPtr, 0x00, 1); } /* Broken link flag. */ if (broken_link) { Bitio_Write(bbPtr, 0x01, 1); } else { Bitio_Write(bbPtr, 0x00, 1); } /* next start code */ Bitio_BytePad(bbPtr); /* Write ext data if present. */ if (ext_data != NULL) { Bitio_Write(bbPtr, EXT_START_CODE, 32); for (i = 0; i < ext_data_size; i++) { Bitio_Write(bbPtr, ext_data[i], 8); } Bitio_BytePad(bbPtr); } /* Write user data if present. */ if (user_data != NULL) { Bitio_Write(bbPtr, USER_START_CODE, 32); for (i = 0; i < user_data_size; i++) { Bitio_Write(bbPtr, user_data[i], 8); } Bitio_BytePad(bbPtr); }}/*===========================================================================* * * Mhead_GenSliceHeader * * generate slice header with specified attributes * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/voidMhead_GenSliceHeader(bbPtr, verticalPos, qscale, extra_info, extra_info_size) BitBucket *bbPtr; uint32 verticalPos; uint32 qscale; uint8 *extra_info; uint32 extra_info_size;{ int i; /* Write slice start code. */ Bitio_Write(bbPtr, (SLICE_BASE_CODE + verticalPos), 32); /* Quant. scale. */ Bitio_Write(bbPtr, qscale, 5); lastQSSet = qscale; /* Extra bit slice info. */ if (extra_info != NULL) { for (i = 0; i < extra_info_size; i++) { Bitio_Write(bbPtr, 0x01, 1); Bitio_Write(bbPtr, extra_info[i], 8); } } /* extra_bit_slice */ Bitio_Write(bbPtr, 0x00, 1);}/*===========================================================================* * * Mhead_GenSliceEnder * * generate slice ender * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/voidMhead_GenSliceEnder(bbPtr) BitBucket *bbPtr;{ Bitio_BytePad(bbPtr);}/*===========================================================================* * * Mhead_GenMBHeader * * generate macroblock header with given attributes * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/voidMhead_GenMBHeader(bbPtr, pict_code_type, addr_incr, q_scale, forw_f_code, back_f_code, horiz_forw_r, vert_forw_r, horiz_back_r, vert_back_r, motion_forw, m_horiz_forw, m_vert_forw, motion_back, m_horiz_back, m_vert_back, mb_pattern, mb_intra) BitBucket *bbPtr; uint32 pict_code_type; uint32 addr_incr; uint32 q_scale; uint32 forw_f_code; uint32 back_f_code; uint32 horiz_forw_r; uint32 vert_forw_r; uint32 horiz_back_r; uint32 vert_back_r; int32 motion_forw; int32 m_horiz_forw; int32 m_vert_forw; int32 motion_back; int32 m_horiz_back; int32 m_vert_back; uint32 mb_pattern; uint32 mb_intra;{ uint32 mb_quant; /* MB escape sequences if necessary. */#ifdef BLEAHif ( addr_incr != 1 ) fprintf(stdout, "Creating MB_INCR: %d\n", addr_incr);#endif while (addr_incr > 33) { Bitio_Write(bbPtr, 0x008, 11); addr_incr -= 33; } /* Generate addr incr code. */ GenMBAddrIncr(bbPtr, addr_incr); /* Determine mb_quant (true if change in q scale) */ if ((q_scale != lastQSSet) && ((mb_pattern != 0) || (mb_intra == TRUE))) { mb_quant = TRUE; lastQSSet = q_scale; } else { mb_quant = FALSE; } /* Generate mb type code. */ GenMBType(bbPtr, pict_code_type, mb_quant, motion_forw, motion_back, mb_pattern, mb_intra); /* MB quant. */ if (mb_quant) { Bitio_Write(bbPtr, q_scale, 5); } /* Forward predictive vector stuff. */ if (motion_forw) { int forw_f, forw_r_size; forw_r_size = forw_f_code - 1; forw_f = 1 << forw_r_size; /* 1 > 0 */ if ((m_horiz_forw > 16*forw_f-1) || (m_horiz_forw < -16*forw_f)) { fprintf(stderr, "Illegal motion? %d %d\n", m_horiz_forw, 16*forw_f); } if ((m_vert_forw > 16*forw_f-1) || (m_vert_forw < -16*forw_f)) { fprintf(stderr, "Illegal motion? %d %d\n", m_vert_forw, 16*forw_f); } GenMotionCode(bbPtr, m_horiz_forw); if ((forw_f != 1) && (m_horiz_forw != 0)) { Bitio_Write(bbPtr, horiz_forw_r, forw_r_size); } GenMotionCode(bbPtr, m_vert_forw); if ((forw_f != 1) && (m_vert_forw != 0)) { Bitio_Write(bbPtr, vert_forw_r, forw_r_size); } } /* Back predicted vector stuff. */ if (motion_back) { int back_f, back_r_size; back_r_size = back_f_code - 1; back_f = 1 << back_r_size; /* 1 > 0 */ if ((m_horiz_back > 16*back_f-1) || (m_horiz_back < -16*back_f)) { fprintf(stderr, "Illegal motion? %d %d\n", m_horiz_back, 16*back_f); } if ((m_vert_back > 16*back_f-1) || (m_vert_back < -16*back_f)) { fprintf(stderr, "Illegal motion? %d %d\n", m_vert_back, 16*back_f); } GenMotionCode(bbPtr, m_horiz_back); if ((back_f != 1) && (m_horiz_back != 0)) { Bitio_Write(bbPtr, horiz_back_r, back_r_size); } GenMotionCode(bbPtr, m_vert_back); if ((back_f != 1) && (m_vert_back != 0)) { Bitio_Write(bbPtr, vert_back_r, back_r_size); } } /* MB pattern. */ if (mb_pattern) { GenBlockPattern(bbPtr, mb_pattern); }}/*=====================* * INTERNAL PROCEDURES * *=====================*//*===========================================================================* * * GenMBType * * generate macroblock type with given attributes * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/static voidGenMBType(bbPtr, pict_code_type, mb_quant, motion_forw, motion_back, mb_pattern, mb_intra) BitBucket *bbPtr; uint32 pict_code_type; uint32 mb_quant; uint32 motion_forw; uint32 motion_back; uint32 mb_pattern; uint32 mb_intra;{ int code; switch (pict_code_type) { case 1: if ((motion_forw != 0) || (motion_back != 0) || (mb_pattern != 0) || (mb_intra != 1)) { perror("Illegal parameters for macroblock type."); exit(-1); } if (mb_quant) { Bitio_Write(bbPtr, 0x1, 2); } else { Bitio_Write(bbPtr, 0x1, 1); } break; case 2: code = 0; if (mb_quant) { code += 16; } if (motion_forw) { code += 8; } if (motion_back) { code += 4; } if (mb_pattern) { code += 2; } if (mb_intra) { code += 1; } switch (code) { case 1: Bitio_Write(bbPtr, 0x3, 5); break; case 2: Bitio_Write(bbPtr, 0x1, 2); break; case 8: Bitio_Write(bbPtr, 0x1, 3); break; case 10: Bitio_Write(bbPtr, 0x1, 1); break; case 17: Bitio_Write(bbPtr, 0x1, 6); break; case 18: Bitio_Write(bbPtr, 0x1, 5); break; case 26: Bitio_Write(bbPtr, 0x2, 5); break; default: perror("Illegal parameters for macroblock type."); exit(-1); break; } break; case 3: code = 0; if (mb_quant) { code += 16; } if (motion_forw) { code += 8; } if (motion_back) { code += 4; } if (mb_pattern) { code += 2; } if (mb_intra) { code += 1; } switch (code) { case 12: Bitio_Write(bbPtr, 0x2, 2); break; case 14: Bitio_Write(bbPtr, 0x3, 2); break; case 4: Bitio_Write(bbPtr, 0x2, 3); break; case 6: Bitio_Write(bbPtr, 0x3, 3); break; case 8: Bitio_Write(bbPtr, 0x2, 4); break; case 10: Bitio_Write(bbPtr, 0x3, 4); break; case 1: Bitio_Write(bbPtr, 0x3, 5); break; case 30: Bitio_Write(bbPtr, 0x2, 5); break; case 26: Bitio_Write(bbPtr, 0x3, 6); break; case 22: Bitio_Write(bbPtr, 0x2, 6); break; case 17: Bitio_Write(bbPtr, 0x1, 6); break; default: perror("Illegal parameters for macroblock type."); exit(-1); break; } break; }}/*===========================================================================* * * GenMotionCode * * generate motion vector output with given value * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/static voidGenMotionCode(bbPtr, vector) BitBucket *bbPtr; int32 vector;{ uint32 code, num; if ((vector < -16) || (vector > 16)) { perror("Motion vector out of range."); fprintf(stderr, "Motion vector out of range: vector = %d\n", vector); exit(-1); } code = mbMotionVectorTable[vector + 16][0]; num = mbMotionVectorTable[vector + 16][1]; Bitio_Write(bbPtr, code, num);}/*===========================================================================* * * GenBlockPattern * * generate macroblock pattern output * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/static voidGenBlockPattern(bbPtr, mb_pattern) BitBucket *bbPtr; uint32 mb_pattern;{ uint32 code, num; code = mbPatTable[mb_pattern][0]; num = mbPatTable[mb_pattern][1]; Bitio_Write(bbPtr, code, num);}/*===========================================================================* * * GenMBAddrIncr * * generate macroblock address increment output * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/static voidGenMBAddrIncr(bbPtr, addr_incr) BitBucket *bbPtr; uint32 addr_incr;{ uint32 code; uint32 num; code = mbAddrIncrTable[addr_incr][0]; num = mbAddrIncrTable[addr_incr][1]; Bitio_Write(bbPtr, code, num);}/*===========================================================================* * * GenPictHead * * generate picture header with given attributes * append result to the specified bitstream * * RETURNS: nothing * * SIDE EFFECTS: none * *===========================================================================*/static voidGenPictHead(bbPtr, temp_ref, code_type, vbv_delay, full_pel_forw_flag, forw_f_code, full_pel_back_flag, back_f_code, extra_info, extra_info_size, ext_data, ext_data_size, user_data, user_data_size) BitBucket *bbPtr; uint32 temp_ref; uint32 code_type; uint32 vbv_delay; int32 full_pel_forw_flag; uint32 forw_f_code; int32 full_pel_back_flag; uint32 back_f_code; uint8 *extra_info; uint32 extra_info_size; uint8 *ext_data; uint32 ext_data_size; uint8 *user_data; uint32 user_data_size;{ int i; /* Write picture start code. */ Bitio_Write(bbPtr, PICT_START_CODE, 32); /* Temp reference. */ Bitio_Write(bbPtr, temp_ref, 10); /* Code_type. */ if (code_type == 0) { code_type = 1; } Bitio_Write(bbPtr, code_type, 3); /* vbv_delay. */ vbv_delay = 0xffff; /* see page 36 (section 2.4.3.4) */ Bitio_Write(bbPtr, vbv_delay, 16); if ((code_type == 2) || (code_type == 3)) { /* Full pel forw flag. */ if (full_pel_forw_flag) { Bitio_Write(bbPtr, 0x01, 1); } else { Bitio_Write(bbPtr, 0x00, 1); } /* Forw f code. */ Bitio_Write(bbPtr, forw_f_code, 3); } if (code_type == 3) { /* Full pel back flag. */ if (full_pel_back_flag) { Bitio_Write(bbPtr, 0x01, 1); } else { Bitio_Write(bbPtr, 0x00, 1); } /* Back f code. */ Bitio_Write(bbPtr, back_f_code, 3); } /* Extra bit picture info. */ if (extra_info != NULL) { for (i = 0; i < extra_info_size; i++) { Bitio_Write(bbPtr, 0x01, 1); Bitio_Write(bbPtr, extra_info[i], 8); } } Bitio_Write(bbPtr, 0x00, 1); /* next start code */ Bitio_BytePad(bbPtr); /* Write ext data if present. */ if (ext_data != NULL) { Bitio_Write(bbPtr, EXT_START_CODE, 32); for (i = 0; i < ext_data_size; i++) { Bitio_Write(bbPtr, ext_data[i], 8); } Bitio_BytePad(bbPtr); } /* Write user data if present. */ if (user_data != NULL) { Bitio_Write(bbPtr, USER_START_CODE, 32); for (i = 0; i < user_data_size; i++) { Bitio_Write(bbPtr, user_data[i], 8); } Bitio_BytePad(bbPtr); }}#ifdef UNUSED_PROCEDURES/* GenMBEnd only used for `D` pictures. Shouldn't really ever be called. *//* - dwallach */voidGenMBEnd(bbPtr) BitBucket *bbPtr;{ Bitio_Write(bbPtr, 0x01, 1);}#endif /* UNUSED_PROCEDURES */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -