Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1583)

Unified Diff: content/common/gpu/media/h264_parser.h

Issue 9814001: Add VAVDA, the VAAPI Video Decode Accelerator for Intel CPUs. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 8 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: content/common/gpu/media/h264_parser.h
diff --git a/content/common/gpu/media/h264_parser.h b/content/common/gpu/media/h264_parser.h
new file mode 100644
index 0000000000000000000000000000000000000000..9d1090e3b8f5a977e981892884b26b56310c8cda
--- /dev/null
+++ b/content/common/gpu/media/h264_parser.h
@@ -0,0 +1,378 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
Ami GONE FROM CHROMIUM 2012/03/21 13:16:24 Not part of this CL?
Pawel Osciak 2012/03/21 18:40:35 Yeah, looks like I was misunderstanding how rietve
Ami GONE FROM CHROMIUM 2012/03/22 17:01:36 Addressed this elsewhere, but FWIW it's always a g
+// found in the LICENSE file.
+//
+// This file contains an implementation of a H264 Annex-B video stream parser.
+
+#ifndef CONTENT_COMMON_GPU_MEDIA_H264_PARSER_H_
+#define CONTENT_COMMON_GPU_MEDIA_H264_PARSER_H_
+
+#include <map>
+
+#include "base/basictypes.h"
+#include "base/memory/scoped_ptr.h"
+
+// For explanations of each struct and its members, see H.264 specification
+enum H264NaluType {
+ kH264NaluUnspecified = 0,
+ kH264NaluNonIDRSlice = 1,
+ kH264NaluIDRSlice = 5,
+ kH264SEIMessage = 6,
+ kH264NaluSPS = 7,
+ kH264NaluPPS = 8,
+ kH264NaluEOSeq = 9,
+ kH264NaluEOStream = 11,
+};
+
+struct H264NALU {
+ uint8* data; // After/without start code
+ size_t size; // From after start code to start code of next NALU (or EOS)
+
+ uint8 nal_ref_idc;
+ uint8 nal_unit_type;
+};
+
+struct H264SPS {
+ uint8 profile_idc;
+ uint8 level_idc;
+ uint32 seq_parameter_set_id;
+
+ uint8 chroma_format_idc;
+ bool separate_colour_plane_flag;
+ uint8 bit_depth_luma_minus8;
+ uint8 bit_depth_chroma_minus8;
+ bool qpprime_y_zero_transform_bypass_flag;
+
+ bool seq_scaling_matrix_present_flag;
+ // Changing uint8s below to larger types will break assumptions
+ // in code that fills default scaling lists
+ uint8 scaling_list4x4[6][16];
+ uint8 scaling_list8x8[6][64];
+
+ uint8 log2_max_frame_num_minus4;
+ uint8 pic_order_cnt_type;
+ uint8 log2_max_pic_order_cnt_lsb_minus4;
+ bool delta_pic_order_always_zero_flag;
+ int32 offset_for_non_ref_pic;
+ int32 offset_for_top_to_bottom_field;
+ uint8 num_ref_frames_in_pic_order_cnt_cycle;
+ int32 offset_for_ref_frame[255];
+ uint32 max_num_ref_frames;
+ bool gaps_in_frame_num_value_allowed_flag;
+ uint32 pic_width_in_mbs_minus1;
+ uint32 pic_height_in_map_units_minus1;
+ bool frame_mbs_only_flag;
+ bool mb_adaptive_frame_field_flag;
+ bool direct_8x8_inference_flag;
+ bool frame_cropping_flag;
+ uint32 frame_crop_left_offset;
+ uint32 frame_crop_right_offset;
+ uint32 frame_crop_top_offset;
+ uint32 frame_crop_bottom_offset;
+ bool vui_parameters_present_flag;
+
+ uint8 chroma_array_type;
+};
+
+struct H264PPS {
+ uint8 pic_parameter_set_id;
+ uint8 seq_parameter_set_id;
+ bool entropy_coding_mode_flag;
+ bool bottom_field_pic_order_in_frame_present_flag;
+ uint32 num_slice_groups_minus1;
+ // TODO slice groups not implemented
+ uint8 num_ref_idx_l0_default_active_minus1;
+ uint8 num_ref_idx_l1_default_active_minus1;
+ bool weighted_pred_flag;
+ uint8 weighted_bipred_idc;
+ int8 pic_init_qp_minus26;
+ int8 pic_init_qs_minus26;
+ int8 chroma_qp_index_offset;
+ bool deblocking_filter_control_present_flag;
+ bool constrained_intra_pred_flag;
+ bool redundant_pic_cnt_present_flag;
+
+ bool transform_8x8_mode_flag;
+
+ bool pic_scaling_matrix_present_flag;
+ uint8 scaling_list4x4[6][16];
+ uint8 scaling_list8x8[6][64];
+
+ int32 second_chroma_qp_index_offset;
+};
+
+enum H264SliceType {
+ kH264PSlice = 0,
+ kH264BSlice = 1,
+ kH264ISlice = 2,
+ kH264SPSlice = 3,
+ kH264SISlice = 4,
+};
+
+struct H264ModificationOfPicNum {
+ uint8 modification_of_pic_nums_idc;
+ union {
+ uint32 abs_diff_pic_num_minus1;
+ uint32 long_term_pic_num;
+ };
+};
+
+struct H264WeightingFactors {
+ bool luma_weight_flag;
+ bool chroma_weight_flag;
+
+ int16 luma_weight[32];
+ int16 luma_offset[32];
+ int16 chroma_weight[32][2];
+ int16 chroma_offset[32][2];
+};
+
+struct H264DecRefPicMarking {
+ uint8 memory_mgmnt_control_operation;
+ uint32 difference_of_pic_nums_minus1;
+ uint32 long_term_pic_num;
+ uint32 long_term_frame_idx;
+ uint32 max_long_term_frame_idx_plus1;
+};
+
+struct H264SliceHeader {
+ enum { kRefListSize = 32 };
+ enum { kRefListModSize = kRefListSize };
+
+ bool idr_pic_flag; // from NAL header
+ uint8 nal_ref_idc; // from NAL header
+ uint8* nalu_data; // from NAL header
+ size_t nalu_size; // from NAL header
+ size_t header_bit_size; // calculated
+
+ uint32 first_mb_in_slice;
+ uint8 slice_type;
+ uint8 pic_parameter_set_id;
+ uint8 colour_plane_id;
+ uint32 frame_num;
+ bool field_pic_flag;
+ bool bottom_field_flag;
+ uint16 idr_pic_id;
+ uint32 pic_order_cnt_lsb;
+ int32 delta_pic_order_cnt_bottom;
+ int32 delta_pic_order_cnt[2];
+ uint8 redundant_pic_cnt;
+ bool direct_spatial_mv_pred_flag;
+
+ bool num_ref_idx_active_override_flag;
+ uint8 num_ref_idx_l0_active_minus1;
+ uint8 num_ref_idx_l1_active_minus1;
+ bool ref_pic_list_modification_flag_l0;
+ bool ref_pic_list_modification_flag_l1;
+ H264ModificationOfPicNum ref_list_l0_modifications[kRefListModSize];
+ H264ModificationOfPicNum ref_list_l1_modifications[kRefListModSize];
+
+ uint8 luma_log2_weight_denom;
+ uint8 chroma_log2_weight_denom;
+
+ bool luma_weight_l0_flag;
+ bool chroma_weight_l0_flag;
+ H264WeightingFactors pred_weight_table_l0;
+
+ bool luma_weight_l1_flag;
+ bool chroma_weight_l1_flag;
+ H264WeightingFactors pred_weight_table_l1;
+
+ bool no_output_of_prior_pics_flag;
+ bool long_term_reference_flag;
+
+ bool adaptive_ref_pic_marking_mode_flag;
+ H264DecRefPicMarking ref_pic_marking[kRefListSize];
+
+ uint8 cabac_init_idc;
+ int32 slice_qp_delta;
+ bool sp_for_switch_flag;
+ int32 slice_qs_delta;
+ uint8 disable_deblocking_filter_idc;
+ int8 slice_alpha_c0_offset_div2;
+ int8 slice_beta_offset_div2;
+};
+
+enum H264SEIType {
+ kH264SEIRecoveryPoint = 6,
+};
+
+struct H264SEIRecoveryPoint {
+ uint32 recovery_frame_cnt;
+ bool exact_match_flag;
+ bool broken_link_flag;
+ uint8 changing_slice_group_idc;
+};
+
+struct H264SEIMessage {
+ int32 type;
+ uint32 payload_size;
+ union {
+ H264SEIRecoveryPoint recovery_point;
+ };
+};
+
+static inline bool IsH264PSlice(H264SliceHeader* shdr) {
+ if (shdr)
+ return (shdr->slice_type % 5 == kH264PSlice);
+ return false;
+}
+
+static inline bool IsH264BSlice(H264SliceHeader* shdr) {
+ if (shdr)
+ return (shdr->slice_type % 5 == kH264BSlice);
+ return false;
+}
+
+static inline bool IsH264ISlice(H264SliceHeader* shdr) {
+ if (shdr)
+ return (shdr->slice_type % 5 == kH264ISlice);
+ return false;
+}
+
+static inline bool IsH264SPSlice(H264SliceHeader* shdr) {
+ if (shdr)
+ return (shdr->slice_type % 5 == kH264SPSlice);
+ return false;
+}
+
+static inline bool IsH264SISlice(H264SliceHeader* shdr) {
+ if (shdr)
+ return (shdr->slice_type % 5 == kH264SISlice);
+ return false;
+}
+
+// Class to provide bit-granularity reading of H.264 streams
+// This is not a generic bit reader class, as it takes into account
+// H.264 stream-specific constraints, such as skipping emulation-prevention
+// bytes and stop bits. See spec for more details.
+class H264BitReader {
+ public:
+
+ H264BitReader();
+ ~H264BitReader();
+
+ bool Initialize(uint8* data, size_t size);
+
+ // Read num_bits next bits in stream and return in out
+ bool ReadBits(int num_bits, uint32 *out);
+
+ // True if any bits left in the stream
+ size_t NumBitsLeft() { return (bits_in_curr_byte_ + bytes_left_ * 8); }
+
+ // See the definition of more_rbsp_data() in spec.
+ bool MoreRBSPData();
+
+ private:
+
+ // Advance to the next byte if we are out of bits in the current byte
+ bool UpdateCurrByte();
+
+ // Pointer to the next unread byte in the stream
+ uint8* data_;
+
+ // Bytes left in the stream (without the current byte)
+ size_t bytes_left_;
+
+ // Contents of the current byte
+ uint8 curr_byte_;
+
+ // for emulation prevention three byte detection
+ uint16 prev_two_bytes_;
+ int bits_in_curr_byte_;
+
+ DISALLOW_COPY_AND_ASSIGN(H264BitReader);
+};
+
+// Class to parse an Annex-B H.264 stream,
+// as specified in chapters 7 and Annex B of the H.264 spec.
+class H264Parser {
+ public:
+
+ enum Result {
+ kOk,
+ kInvalidStream, // error in stream
+ kUnsupportedStream, // stream not supported by the parser
+ kEOStream, // end of stream
+ };
+
+ H264Parser();
+ ~H264Parser();
+
+ void Reset();
+ // stream_size in bytes
+ void SetStream(uint8* stream, size_t stream_size);
+
+ // Read the next stream to find the next NALU, identify it and return
+ // that information in nalu. This advances the stream to the beginning
+ // of this NALU, but not past it, so subsequent calls to NALU-specific
+ // parsing functions (ParseSPS, etc.) will parse this NALU.
+ // If the caller wishes to skip the current NALU, it can call this function
+ // again, instead of any NALU-type specific parse functions below.
+ Result ParseNextNalu(H264NALU* nalu);
+
+ // Nalu-specific parsing functions.
+ // These should be called after ParseNextNalu().
+
+ // SPS and PPS are stored in the Parser and the memory for their structures
+ // is managed by the parser, as they can be reused across NALUs.
+ // To access any of them, use GetSPS()/GetPPS() using the returned id.
+ Result ParseSPS(int* sps_id);
+ Result ParsePPS(int* pps_id);
+
+ // Slice header is not used across NALUs and can be discarded after current
+ // NALU, so the parser does not store them, nor does it manage their memory.
+ // Caller has to provide and manage it instead.
+ Result ParseSliceHeader(H264SliceHeader* shdr, H264NALU* nalu);
+
+ // Return pointer to SPS/PPS with given id or NULL if not present.
+ // Caller should not attempt to modify/free this memory.
+ H264SPS* GetSPS(uint8 sps_id);
+ H264PPS* GetPPS(uint8 pps_id);
+
+ Result ParseSEI(H264SEIMessage* sei_msg);
+
+ private:
+
+ // Exp-Golomb code parsing as specified in chapter 9.1 of the spec.
+ // Read one unsigned exp-Golomb code from the stream,
+ Result ReadUE(uint32* val);
+
+ // Read one signed exp-Golomb code from the stream.
+ Result ReadSE(int32* val);
+
+ Result ScalingList(uint8* scaling_list, int size, bool* use_default);
+ Result ParseSPSScalingLists(H264SPS* sps);
+ Result ParsePPSScalingLists(H264SPS* sps, H264PPS* pps);
+
+ Result RefPicListModification(H264SliceHeader* shdr);
+ Result ParseRefPicListModification(uint8 num_ref_idx_active_minus1,
+ H264ModificationOfPicNum* ref_list_mods);
+
+ Result ParsePredWeightTable(H264SliceHeader *shdr, H264SPS* sps);
+
+ Result ParseWeightingFactors(H264WeightingFactors* w_facts,
+ int num_ref_idx_active_minus1,
+ uint8 chroma_array_type,
+ uint8 luma_log2_weight_denom,
+ uint8 chroma_log2_weight_denom);
+ Result ParseDecRefPicMarking(H264SliceHeader *shdr);
+
+ // Pointer to the current NALU in the stream
+ uint8* stream_;
+
+ // Bytes left in the stream after the current NALU.
+ size_t bytes_left_;
+
+ H264BitReader br_;
+
+ typedef std::map<uint8, H264SPS*> SPSById;
+ typedef std::map<uint8, H264PPS*> PPSById;
+ SPSById active_SPSes_;
+ PPSById active_PPSes_;
+
+ DISALLOW_COPY_AND_ASSIGN(H264Parser);
+};
+
+#endif // CONTENT_COMMON_GPU_MEDIA_H264_PARSER_H_
+

Powered by Google App Engine
This is Rietveld 408576698