LibVideo/VP9: Implement token parsing (6.4.24-6.4.26)
Note that this now requires a couple new syntax types to be parsed in the TreeParser, so a follow-up commit will implement that behavior.
This commit is contained in:
parent
d79c9c262f
commit
aa27ca1b16
Notes:
sideshowbarker
2024-07-18 09:23:29 +09:00
Author: https://github.com/FalseHonesty Commit: https://github.com/SerenityOS/serenity/commit/aa27ca1b160 Pull-request: https://github.com/SerenityOS/serenity/pull/8349 Reviewed-by: https://github.com/Lubrsi
5 changed files with 171 additions and 4 deletions
File diff suppressed because one or more lines are too long
|
@ -1191,10 +1191,93 @@ BlockSubsize Parser::get_plane_block_size(u32 subsize, u8 plane)
|
|||
return ss_size_lookup[subsize][sub_x][sub_y];
|
||||
}
|
||||
|
||||
bool Parser::tokens(size_t, u32, u32, TXSize, u32)
|
||||
bool Parser::tokens(size_t plane, u32 start_x, u32 start_y, TXSize tx_size, u32 block_index)
|
||||
{
|
||||
// TODO: Implement
|
||||
return true;
|
||||
m_tree_parser->set_more_coefs_variables(start_x, start_y);
|
||||
size_t segment_eob = 16 << (tx_size << 1);
|
||||
auto scan = get_scan(plane, tx_size, block_index);
|
||||
auto check_eob = true;
|
||||
size_t c = 0;
|
||||
for (; c < segment_eob; c++) {
|
||||
auto pos = scan[c];
|
||||
auto band = (tx_size == TX_4x4) ? coefband_4x4[c] : coefband_8x8plus[c];
|
||||
m_tree_parser->set_band(band);
|
||||
if (check_eob) {
|
||||
auto more_coefs = m_tree_parser->parse_tree<bool>(SyntaxElementType::MoreCoefs);
|
||||
if (!more_coefs)
|
||||
break;
|
||||
}
|
||||
auto token = m_tree_parser->parse_tree<Token>(SyntaxElementType::Token);
|
||||
m_token_cache[pos] = energy_class[token];
|
||||
if (token == ZeroToken) {
|
||||
m_tokens[pos] = 0;
|
||||
check_eob = false;
|
||||
} else {
|
||||
i32 coef = static_cast<i32>(read_coef(token));
|
||||
auto sign_bit = m_bit_stream->read_literal(1);
|
||||
m_tokens[pos] = sign_bit ? -coef : coef;
|
||||
check_eob = true;
|
||||
}
|
||||
}
|
||||
auto non_zero = c > 0;
|
||||
m_eob_total += non_zero;
|
||||
for (size_t i = c; i < segment_eob; i++)
|
||||
m_tokens[scan[i]] = 0;
|
||||
return non_zero;
|
||||
}
|
||||
|
||||
u32 const* Parser::get_scan(size_t plane, TXSize tx_size, u32 block_index)
|
||||
{
|
||||
if (plane > 0 || tx_size == TX_32x32) {
|
||||
m_tx_type = DCT_DCT;
|
||||
} else if (tx_size == TX_4x4) {
|
||||
if (m_lossless || m_is_inter)
|
||||
m_tx_type = DCT_DCT;
|
||||
else
|
||||
m_tx_type = mode_to_txfm_map[m_mi_size < Block_8x8 ? m_block_sub_modes[block_index] : m_y_mode];
|
||||
} else {
|
||||
m_tx_type = mode_to_txfm_map[m_y_mode];
|
||||
}
|
||||
if (tx_size == TX_4x4) {
|
||||
if (m_tx_type == ADST_DCT)
|
||||
return row_scan_4x4;
|
||||
if (m_tx_type == DCT_ADST)
|
||||
return col_scan_4x4;
|
||||
return default_scan_4x4;
|
||||
}
|
||||
if (tx_size == TX_8x8) {
|
||||
if (m_tx_type == ADST_DCT)
|
||||
return row_scan_8x8;
|
||||
if (m_tx_type == DCT_ADST)
|
||||
return col_scan_8x8;
|
||||
return default_scan_8x8;
|
||||
}
|
||||
if (tx_size == TX_16x16) {
|
||||
if (m_tx_type == ADST_DCT)
|
||||
return row_scan_16x16;
|
||||
if (m_tx_type == DCT_ADST)
|
||||
return col_scan_16x16;
|
||||
return default_scan_16x16;
|
||||
}
|
||||
return default_scan_32x32;
|
||||
}
|
||||
|
||||
u32 Parser::read_coef(Token token)
|
||||
{
|
||||
auto cat = extra_bits[token][0];
|
||||
auto num_extra = extra_bits[token][1];
|
||||
auto coef = extra_bits[token][2];
|
||||
if (token == DctValCat6) {
|
||||
for (size_t e = 0; e < (u8)(m_bit_depth - 8); e++) {
|
||||
auto high_bit = m_bit_stream->read_bool(255);
|
||||
coef += high_bit << (5 + m_bit_depth - e);
|
||||
}
|
||||
}
|
||||
for (size_t e = 0; e < num_extra; e++) {
|
||||
auto coef_bit = m_bit_stream->read_bool(cat_probs[cat][e]);
|
||||
coef += coef_bit << (num_extra - 1 - e);
|
||||
}
|
||||
return coef;
|
||||
}
|
||||
|
||||
bool Parser::find_mv_refs(ReferenceFrame, int)
|
||||
|
|
|
@ -116,7 +116,9 @@ private:
|
|||
bool residual();
|
||||
TXSize get_uv_tx_size();
|
||||
BlockSubsize get_plane_block_size(u32 subsize, u8 plane);
|
||||
bool tokens(size_t plane, u32 x, u32 y, TXSize size, u32 index);
|
||||
bool tokens(size_t plane, u32 x, u32 y, TXSize tx_size, u32 block_index);
|
||||
u32 const* get_scan(size_t plane, TXSize tx_size, u32 block_index);
|
||||
u32 read_coef(Token token);
|
||||
|
||||
/* (6.5) Motion Vector Prediction */
|
||||
bool find_mv_refs(ReferenceFrame, int block);
|
||||
|
@ -220,6 +222,9 @@ private:
|
|||
u32 m_ref_frame_width[NUM_REF_FRAMES];
|
||||
u32 m_ref_frame_height[NUM_REF_FRAMES];
|
||||
u32 m_eob_total { 0 };
|
||||
u8 m_tx_type { 0 };
|
||||
u8 m_token_cache[1024];
|
||||
i32 m_tokens[1024];
|
||||
|
||||
bool m_use_hp { false };
|
||||
|
||||
|
|
|
@ -36,6 +36,7 @@ template IntraMode TreeParser::parse_tree(SyntaxElementType);
|
|||
template TXSize TreeParser::parse_tree(SyntaxElementType);
|
||||
template InterpolationFilter TreeParser::parse_tree(SyntaxElementType);
|
||||
template ReferenceMode TreeParser::parse_tree(SyntaxElementType);
|
||||
template Token TreeParser::parse_tree(SyntaxElementType);
|
||||
|
||||
/*
|
||||
* Select a tree value based on the type of syntax element being parsed, as well as some parser state, as specified in section 9.3.1
|
||||
|
|
|
@ -57,6 +57,14 @@ public:
|
|||
m_idy = idy;
|
||||
}
|
||||
|
||||
void set_band(u8 band) { m_band = band; }
|
||||
|
||||
void set_more_coefs_variables(u32 start_x, u32 start_y)
|
||||
{
|
||||
m_start_x = start_x;
|
||||
m_start_y = start_y;
|
||||
}
|
||||
|
||||
private:
|
||||
u8 calculate_partition_probability(u8 node);
|
||||
u8 calculate_default_intra_mode_probability(u8 node);
|
||||
|
@ -84,6 +92,9 @@ private:
|
|||
// not stored in the Decoder itself.
|
||||
u8 m_idx { 0 };
|
||||
u8 m_idy { 0 };
|
||||
u8 m_band { 0 };
|
||||
u32 m_start_x { 0 };
|
||||
u32 m_start_y { 0 };
|
||||
};
|
||||
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue