Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / media / filters / vp9_parser.h
blob5724ae91498b4f4a63df6d43701027a4150726b8
1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 //
5 // This file contains an implementation of a VP9 bitstream parser. The main
6 // purpose of this parser is to support hardware decode acceleration. Some
7 // accelerators, e.g. libva which implements VA-API, require the caller
8 // (chrome) to feed them parsed VP9 frame header.
9 //
10 // See content::VP9Decoder for example usage.
12 #ifndef MEDIA_FILTERS_VP9_PARSER_H_
13 #define MEDIA_FILTERS_VP9_PARSER_H_
15 #include <stddef.h>
16 #include <stdint.h>
18 #include <deque>
20 #include "base/macros.h"
21 #include "media/base/media_export.h"
22 #include "media/filters/vp9_raw_bits_reader.h"
24 namespace media {
26 const int kVp9MaxProfile = 4;
27 const int kVp9NumRefFramesLog2 = 3;
28 const size_t kVp9NumRefFrames = 1 << kVp9NumRefFramesLog2;
29 const uint8_t kVp9MaxProb = 255;
30 const size_t kVp9NumRefsPerFrame = 3;
32 enum class Vp9ColorSpace {
33 UNKNOWN = 0,
34 BT_601 = 1,
35 BT_709 = 2,
36 SMPTE_170 = 3,
37 SMPTE_240 = 4,
38 BT_2020 = 5,
39 RESERVED = 6,
40 SRGB = 7,
43 enum Vp9InterpFilter {
44 EIGHTTAP = 0,
45 EIGHTTAP_SMOOTH = 1,
46 EIGHTTAP_SHARP = 2,
47 BILINEAR = 3,
48 SWICHABLE = 4,
51 struct MEDIA_EXPORT Vp9Segmentation {
52 static const size_t kNumSegments = 8;
53 static const size_t kNumTreeProbs = kNumSegments - 1;
54 static const size_t kNumPredictionProbs = 3;
55 enum SegmentLevelFeature {
56 SEG_LVL_ALT_Q = 0,
57 SEG_LVL_ALT_LF = 1,
58 SEG_LVL_REF_FRAME = 2,
59 SEG_LVL_SKIP = 3,
60 SEG_LVL_MAX
63 bool enabled;
65 bool update_map;
66 uint8_t tree_probs[kNumTreeProbs];
67 bool temporal_update;
68 uint8_t pred_probs[kNumPredictionProbs];
70 bool update_data;
71 bool abs_delta;
72 bool feature_enabled[kNumSegments][SEG_LVL_MAX];
73 int8_t feature_data[kNumSegments][SEG_LVL_MAX];
75 int16_t y_dequant[kNumSegments][2];
76 int16_t uv_dequant[kNumSegments][2];
78 bool FeatureEnabled(size_t seg_id, SegmentLevelFeature feature) const {
79 return feature_enabled[seg_id][feature];
82 int8_t FeatureData(size_t seg_id, SegmentLevelFeature feature) const {
83 return feature_data[seg_id][feature];
87 struct MEDIA_EXPORT Vp9LoopFilter {
88 enum Vp9FrameType {
89 VP9_FRAME_INTRA = 0,
90 VP9_FRAME_LAST = 1,
91 VP9_FRAME_GOLDEN = 2,
92 VP9_FRAME_ALTREF = 3,
93 VP9_FRAME_MAX = 4,
96 static const size_t kNumModeDeltas = 2;
98 uint8_t filter_level;
99 uint8_t sharpness_level;
101 bool mode_ref_delta_enabled;
102 bool mode_ref_delta_update;
103 bool update_ref_deltas[VP9_FRAME_MAX];
104 int8_t ref_deltas[VP9_FRAME_MAX];
105 bool update_mode_deltas[kNumModeDeltas];
106 int8_t mode_deltas[kNumModeDeltas];
108 uint8_t lvl[Vp9Segmentation::kNumSegments][VP9_FRAME_MAX][kNumModeDeltas];
111 // Members of Vp9FrameHeader will be 0-initialized by Vp9Parser::ParseNextFrame.
112 struct MEDIA_EXPORT Vp9QuantizationParams {
113 bool IsLossless() const {
114 return base_qindex == 0 && y_dc_delta == 0 && uv_dc_delta == 0 &&
115 uv_ac_delta == 0;
118 uint8_t base_qindex;
119 int8_t y_dc_delta;
120 int8_t uv_dc_delta;
121 int8_t uv_ac_delta;
124 // VP9 frame header.
125 struct MEDIA_EXPORT Vp9FrameHeader {
126 enum FrameType {
127 KEYFRAME = 0,
128 INTERFRAME = 1,
131 bool IsKeyframe() const;
132 bool RefreshFlag(size_t i) const { return !!(refresh_flags & (1u << i)); }
134 uint8_t profile;
136 bool show_existing_frame;
137 uint8_t frame_to_show;
139 FrameType frame_type;
141 bool show_frame;
142 bool error_resilient_mode;
144 uint8_t bit_depth;
145 Vp9ColorSpace color_space;
146 bool yuv_range;
147 uint8_t subsampling_x;
148 uint8_t subsampling_y;
150 // The range of width and height is 1..2^16.
151 uint32_t width;
152 uint32_t height;
153 uint32_t display_width;
154 uint32_t display_height;
156 bool intra_only;
157 uint8_t reset_context;
158 uint8_t refresh_flags;
159 uint8_t frame_refs[kVp9NumRefsPerFrame];
160 bool ref_sign_biases[kVp9NumRefsPerFrame];
161 bool allow_high_precision_mv;
162 Vp9InterpFilter interp_filter;
164 bool refresh_frame_context;
165 bool frame_parallel_decoding_mode;
166 uint8_t frame_context_idx;
168 Vp9QuantizationParams quant_params;
170 uint8_t log2_tile_cols;
171 uint8_t log2_tile_rows;
173 // Pointer to the beginning of frame data. It is a responsibility of the
174 // client of the Vp9Parser to maintain validity of this data while it is
175 // being used outside of that class.
176 const uint8_t* data;
178 // Size of |data| in bytes.
179 size_t frame_size;
181 // Size of compressed header in bytes.
182 size_t first_partition_size;
184 // Size of uncompressed header in bytes.
185 size_t uncompressed_header_size;
188 // A parser for VP9 bitstream.
189 class MEDIA_EXPORT Vp9Parser {
190 public:
191 // ParseNextFrame() return values. See documentation for ParseNextFrame().
192 enum Result {
193 kOk,
194 kInvalidStream,
195 kEOStream,
198 Vp9Parser();
199 ~Vp9Parser();
201 // Set a new stream buffer to read from, starting at |stream| and of size
202 // |stream_size| in bytes. |stream| must point to the beginning of a single
203 // frame or a single superframe, is owned by caller and must remain valid
204 // until the next call to SetStream().
205 void SetStream(const uint8_t* stream, off_t stream_size);
207 // Parse the next frame in the current stream buffer, filling |fhdr| with
208 // the parsed frame header and updating current segmentation and loop filter
209 // state. Return kOk if a frame has successfully been parsed, kEOStream if
210 // there is no more data in the current stream buffer, or kInvalidStream
211 // on error.
212 Result ParseNextFrame(Vp9FrameHeader* fhdr);
214 // Return current segmentation state.
215 const Vp9Segmentation& GetSegmentation() const { return segmentation_; }
217 // Return current loop filter state.
218 const Vp9LoopFilter& GetLoopFilter() const { return loop_filter_; }
220 // Clear parser state and return to an initialized state.
221 void Reset();
223 private:
224 // The parsing context to keep track of references.
225 struct ReferenceSlot {
226 uint32_t width;
227 uint32_t height;
230 bool ParseSuperframe();
231 uint8_t ReadProfile();
232 bool VerifySyncCode();
233 bool ReadBitDepthColorSpaceSampling(Vp9FrameHeader* fhdr);
234 void ReadFrameSize(Vp9FrameHeader* fhdr);
235 bool ReadFrameSizeFromRefs(Vp9FrameHeader* fhdr);
236 void ReadDisplayFrameSize(Vp9FrameHeader* fhdr);
237 Vp9InterpFilter ReadInterpFilter();
238 void ReadLoopFilter();
239 void ReadQuantization(Vp9QuantizationParams* quants);
240 void ReadSegmentationMap();
241 void ReadSegmentationData();
242 void ReadSegmentation();
243 void ReadTiles(Vp9FrameHeader* fhdr);
244 bool ParseUncompressedHeader(const uint8_t* stream,
245 off_t frame_size,
246 Vp9FrameHeader* fhdr);
247 void UpdateSlots(const Vp9FrameHeader* fhdr);
249 void ResetLoopfilter();
250 void SetupPastIndependence();
251 size_t GetQIndex(const Vp9QuantizationParams& quant, size_t segid) const;
252 void SetupSegmentationDequant(const Vp9QuantizationParams& quant);
253 void SetupLoopFilter();
255 // Current address in the bitstream buffer.
256 const uint8_t* stream_;
258 // Remaining bytes in stream_.
259 off_t bytes_left_;
261 // Stores start pointer and size of each frame within the current superframe.
262 struct FrameInfo {
263 FrameInfo(const uint8_t* ptr, off_t size);
265 // Starting address of the frame.
266 const uint8_t* ptr;
268 // Size of the frame in bytes.
269 off_t size;
272 // FrameInfo for the remaining frames in the current superframe to be parsed.
273 std::deque<FrameInfo> frames_;
275 // Raw bits decoder for uncompressed frame header.
276 Vp9RawBitsReader reader_;
278 // Segmentation and loop filter state that persists across frames.
279 Vp9Segmentation segmentation_;
280 Vp9LoopFilter loop_filter_;
282 // The parsing context to keep track of references.
283 ReferenceSlot ref_slots_[kVp9NumRefFrames];
285 DISALLOW_COPY_AND_ASSIGN(Vp9Parser);
288 } // namespace media
290 #endif // MEDIA_FILTERS_VP9_PARSER_H_