Compare commits

...

19 Commits

Author SHA1 Message Date
Yunqing Wang
fbad09f465 Hide global symbols for macho32/64
Added hiding global symbols for macho32 and macho64 in x86inc.asm.
This was done to fix exported symbol issue in Chrome build.

Change-Id: I08d5c559b985b82f655b537469fee125615e78c0
2013-10-30 13:12:15 -07:00
Dmitry Kovalev
300ae1b668 Correct handling of show_bit in uncompressed header.
"keyframe" variable in the current code actually means that previous
frame is a keyframe because cm->frame_type has not been initialized
in read_uncompressed_header.

Change-Id: I5645b0816c70abdef5dfc70113018d06276dac77
2013-10-29 13:59:35 -07:00
Yaowu Xu
91745bcff9 changed to comply with strict aliasing rule
The clamp operation may not affect the values of the final assigned mv
where compiler may make use of strict aliasing rule to optimize out the
clamp operation. This change made the code segments to better comply
the strict aliasing rule.

Change-Id: I24502ff18bd4f9e62507a879cc8760a91a0fd07e
2013-10-29 11:34:19 -07:00
Yaowu Xu
07b0dab5df Converted assert to error checking
Change-Id: Icb8c677f910f588cc7c97e70f024787fe6789257
2013-10-29 10:28:25 -07:00
Yaowu Xu
518904926d Added checking for invalid size
Change-Id: I9672a61e60a26e2934796f088880ce4cb49605be
2013-10-29 10:28:25 -07:00
Yaowu Xu
225aafcf9e Converted assertion to returning error
Assertion happens for invalid input data, the commit replace the
assertion with returning error.

Change-Id: I1b73ae752d64882d984cd23936efe75a757c2b41
2013-10-29 10:28:25 -07:00
Yaowu Xu
b90d51fee6 Added trap for invalid key frame
Change-Id: I698e8df9b336d38bffe01e656acba00d4003695f
2013-10-29 10:28:25 -07:00
Yaowu Xu
cd4bac3004 Prevent access to invalid pointer
The commit added check to make sure no invalid memory access even when
the decoder instance is never initialized.

Change-Id: I4da343d0b3c78c27777ac7f5ce7688562c69f0c5
2013-10-29 10:28:25 -07:00
Yaowu Xu
2f4a2a1268 Add clamp to prevent out of bound access
For bad input data, the decoder may access the array out of bounds. The
commit added clamp to prevent such out of bound access

Change-Id: I0a1cfd9b8786ea7113a998053c76605c963b077a
2013-10-29 10:28:08 -07:00
Dmitry Kovalev
e36425e637 Adding assign_mv() function to reduce code duplication.
Change-Id: I2b4e5b842c19f64749b18946ad215c0caa57e7b7
2013-10-28 16:38:28 -07:00
Dmitry Kovalev
9281f7c278 Reading diff update flag inside vp9_diff_update_prob.
Change-Id: I5ae659c1bfb132428a7272d094b5287d144ec7c8
2013-10-28 16:37:25 -07:00
Dmitry Kovalev
3680f98b1b BITSTREAM - "update_map" SEMANTICS BROKEN IN 398ddafb62
This patch reverts old commit 398ddafb62
"New way of updating last frame segmentation map.".

Change-Id: Iba730f433c30ed7f5e5449d6768049cbf9a2b2c5
2013-10-28 16:37:21 -07:00
Dmitry Kovalev
8fa0ca3b20 BITSTREAM - RESTORING BILINEAR INTERPOLATION FILTER SUPPORT
Adding appropriate test vector vp90-2-06-bilinear.webm.

Change-Id: Ia3bbf57318e0cc61a1b724fe751e3f9c7e11b337
2013-10-28 16:37:18 -07:00
Jingning Han
42f31923b0 BITSTREAM - CLARIFICATION OF MV SIZE RANGE
The codec should effectively run with motion vector of range (-2048, 2047)
in full pixels, for sequences of 1080p and below. Add assertions to clarify
this behavior.

Change-Id: Ia0cac28249f587d8f8882205228fa480263ab313
2013-10-28 16:37:14 -07:00
Dmitry Kovalev
a8a3966174 Adding read_intra_mode_{y, uv} functions for clarity.
Change-Id: I92fd32476c472e54f52b8d7602a98262b25e6eaf
2013-10-28 16:37:05 -07:00
Yaowu Xu
8ab0a2031b fix build with MSVC
near is a key word, changed to use nearmv instead.

Change-Id: Ib54438c431b2b2521a62fc7b61a9c127dd7bc01e
2013-10-28 16:36:41 -07:00
Dmitry Kovalev
16bb20631b Using array of motion vectors instead of separate variables.
Change-Id: I7380a089105f658257bbb3e30a525da168e76952
2013-10-28 16:36:06 -07:00
Dmitry Kovalev
8f83c132ff New way of updating last frame segmentation map.
Implementing more natural (and faster) way of updating last frame
segmentation map.

Change-Id: I9fefa8f78e77bd7948133b04173da45edc15a17e
2013-10-28 16:32:50 -07:00
Jingning Han
4beb889f99 Remove redundant mode update in sub8x8 decoding
The probability model used to code prediction mode is conditioned
on the immediate above and left 8x8 blocks' prediction modes. When
the above/left block is coded in sub8x8 mode, we use the prediction
mode of the bottom-right sub8x8 block as the reference to generate
the context.

This commit moves the update of mbmi.mode out of the sub8x8 decoding
loop, hence removing redundant update steps and keeping the bottom-
right block's mode for the decoding process of next blocks.

Change-Id: I1e8d749684d201c1a1151697621efa5d569218b6
2013-10-28 16:31:21 -07:00
12 changed files with 153 additions and 134 deletions

View File

@@ -524,6 +524,8 @@ b6524e4084d15b5d0caaa3d3d1368db30cbee69c vp90-2-03-deltaq.webm
65f45ec9a55537aac76104818278e0978f94a678 vp90-2-03-deltaq.webm.md5
4dbb87494c7f565ffc266c98d17d0d8c7a5c5aba vp90-2-05-resize.ivf
7f6d8879336239a43dbb6c9f13178cb11cf7ed09 vp90-2-05-resize.ivf.md5
bf61ddc1f716eba58d4c9837d4e91031d9ce4ffe vp90-2-06-bilinear.webm
f6235f937552e11d8eb331ec55da6b3aa596b9ac vp90-2-06-bilinear.webm.md5
495256cfd123fe777b2c0406862ed8468a1f4677 vp91-2-04-yv444.webm
65e3a7ffef61ab340d9140f335ecc49125970c2c vp91-2-04-yv444.webm.md5

View File

@@ -633,5 +633,7 @@ LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-03-deltaq.webm
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-03-deltaq.webm.md5
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-05-resize.ivf
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-05-resize.ivf.md5
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-06-bilinear.webm
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp90-2-06-bilinear.webm.md5
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp91-2-04-yv444.webm
LIBVPX_TEST_DATA-$(CONFIG_VP9_DECODER) += vp91-2-04-yv444.webm.md5

View File

@@ -160,7 +160,7 @@ const char *kVP9TestVectors[] = {
"vp90-2-03-size-226x202.webm", "vp90-2-03-size-226x208.webm",
"vp90-2-03-size-226x210.webm", "vp90-2-03-size-226x224.webm",
"vp90-2-03-size-226x226.webm", "vp90-2-03-deltaq.webm",
"vp90-2-05-resize.ivf",
"vp90-2-05-resize.ivf", "vp90-2-06-bilinear.webm",
#if CONFIG_NON420
"vp91-2-04-yv444.webm"
#endif

View File

@@ -598,6 +598,10 @@ DECLARE_ARG 7, 8, 9, 10, 11, 12, 13, 14
global %1:function hidden
%elifidn __OUTPUT_FORMAT__,elf64
global %1:function hidden
%elifidn __OUTPUT_FORMAT__,macho32
global %1:private_extern
%elifidn __OUTPUT_FORMAT__,macho64
global %1:private_extern
%else
global %1
%endif

View File

@@ -512,15 +512,15 @@ static void read_mb_modes_mv(VP8D_COMP *pbi, MODE_INFO *mi, MB_MODE_INFO *mbmi)
else
{
mbmi->mode = NEARMV;
vp8_clamp_mv2(&near_mvs[CNT_NEAR], &pbi->mb);
mbmi->mv.as_int = near_mvs[CNT_NEAR].as_int;
vp8_clamp_mv2(&mbmi->mv, &pbi->mb);
}
}
else
{
mbmi->mode = NEARESTMV;
vp8_clamp_mv2(&near_mvs[CNT_NEAREST], &pbi->mb);
mbmi->mv.as_int = near_mvs[CNT_NEAREST].as_int;
vp8_clamp_mv2(&mbmi->mv, &pbi->mb);
}
}
else

View File

@@ -73,6 +73,10 @@ extern struct vp9_token vp9_mv_class_encodings[MV_CLASSES];
#define MV_MAX ((1 << MV_MAX_BITS) - 1)
#define MV_VALS ((MV_MAX << 1) + 1)
#define MV_IN_USE_BITS 14
#define MV_UPP ((1 << MV_IN_USE_BITS) - 1)
#define MV_LOW (-(1 << MV_IN_USE_BITS))
extern const vp9_tree_index vp9_mv_class0_tree[2 * CLASS0_SIZE - 2];
extern struct vp9_token vp9_mv_class0_encodings[CLASS0_SIZE];

View File

@@ -30,10 +30,26 @@ static MB_PREDICTION_MODE read_intra_mode(vp9_reader *r, const vp9_prob *p) {
return (MB_PREDICTION_MODE)treed_read(r, vp9_intra_mode_tree, p);
}
static MB_PREDICTION_MODE read_intra_mode_y(VP9_COMMON *cm, vp9_reader *r,
int size_group) {
const MB_PREDICTION_MODE y_mode = read_intra_mode(r,
cm->fc.y_mode_prob[size_group]);
++cm->counts.y_mode[size_group][y_mode];
return y_mode;
}
static MB_PREDICTION_MODE read_intra_mode_uv(VP9_COMMON *cm, vp9_reader *r,
MB_PREDICTION_MODE y_mode) {
const MB_PREDICTION_MODE uv_mode = read_intra_mode(r,
cm->fc.uv_mode_prob[y_mode]);
++cm->counts.uv_mode[y_mode][uv_mode];
return uv_mode;
}
static MB_PREDICTION_MODE read_inter_mode(VP9_COMMON *cm, vp9_reader *r,
uint8_t context) {
MB_PREDICTION_MODE mode = treed_read(r, vp9_inter_mode_tree,
cm->fc.inter_mode_probs[context]);
const MB_PREDICTION_MODE mode = treed_read(r, vp9_inter_mode_tree,
cm->fc.inter_mode_probs[context]);
++cm->counts.inter_mode[context][inter_mode_offset(mode)];
return mode;
}
@@ -348,16 +364,15 @@ static void read_switchable_interp_probs(FRAME_CONTEXT *fc, vp9_reader *r) {
int i, j;
for (j = 0; j < SWITCHABLE_FILTERS + 1; ++j)
for (i = 0; i < SWITCHABLE_FILTERS - 1; ++i)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &fc->switchable_interp_prob[j][i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB,
&fc->switchable_interp_prob[j][i]);
}
static void read_inter_mode_probs(FRAME_CONTEXT *fc, vp9_reader *r) {
int i, j;
for (i = 0; i < INTER_MODE_CONTEXTS; ++i)
for (j = 0; j < INTER_MODES - 1; ++j)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &fc->inter_mode_probs[i][j]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &fc->inter_mode_probs[i][j]);
}
static INLINE COMPPREDMODE_TYPE read_comp_pred_mode(vp9_reader *r) {
@@ -388,9 +403,7 @@ static void read_intra_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
mbmi->ref_frame[1] = NONE;
if (bsize >= BLOCK_8X8) {
const int size_group = size_group_lookup[bsize];
mbmi->mode = read_intra_mode(r, cm->fc.y_mode_prob[size_group]);
cm->counts.y_mode[size_group][mbmi->mode]++;
mbmi->mode = read_intra_mode_y(cm, r, size_group_lookup[bsize]);
} else {
// Only 4x4, 4x8, 8x4 blocks
const int num_4x4_w = num_4x4_blocks_wide_lookup[bsize]; // 1 or 2
@@ -400,10 +413,8 @@ static void read_intra_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
for (idy = 0; idy < 2; idy += num_4x4_h) {
for (idx = 0; idx < 2; idx += num_4x4_w) {
const int ib = idy * 2 + idx;
const int b_mode = read_intra_mode(r, cm->fc.y_mode_prob[0]);
const int b_mode = read_intra_mode_y(cm, r, 0);
mi->bmi[ib].as_mode = b_mode;
cm->counts.y_mode[0][b_mode]++;
if (num_4x4_h == 2)
mi->bmi[ib + 2].as_mode = b_mode;
if (num_4x4_w == 2)
@@ -413,8 +424,47 @@ static void read_intra_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
mbmi->mode = mi->bmi[3].as_mode;
}
mbmi->uv_mode = read_intra_mode(r, cm->fc.uv_mode_prob[mbmi->mode]);
cm->counts.uv_mode[mbmi->mode][mbmi->uv_mode]++;
mbmi->uv_mode = read_intra_mode_uv(cm, r, mbmi->mode);
}
static INLINE int assign_mv(VP9_COMMON *cm, MB_PREDICTION_MODE mode,
int_mv mv[2], int_mv best_mv[2],
int_mv nearest_mv[2], int_mv near_mv[2],
int is_compound, int allow_hp, vp9_reader *r) {
int i;
int ret = 1;
switch (mode) {
case NEWMV:
read_mv(r, &mv[0].as_mv, &best_mv[0].as_mv,
&cm->fc.nmvc, &cm->counts.mv, allow_hp);
if (is_compound)
read_mv(r, &mv[1].as_mv, &best_mv[1].as_mv,
&cm->fc.nmvc, &cm->counts.mv, allow_hp);
for (i = 0; i < 1 + is_compound; ++i) {
ret = ret && mv[i].as_mv.row < MV_UPP && mv[i].as_mv.row > MV_LOW;
ret = ret && mv[i].as_mv.col < MV_UPP && mv[i].as_mv.col > MV_LOW;
}
break;
case NEARESTMV:
mv[0].as_int = nearest_mv[0].as_int;
if (is_compound)
mv[1].as_int = nearest_mv[1].as_int;
break;
case NEARMV:
mv[0].as_int = near_mv[0].as_int;
if (is_compound)
mv[1].as_int = near_mv[1].as_int;
break;
case ZEROMV:
mv[0].as_int = 0;
if (is_compound)
mv[1].as_int = 0;
break;
default:
return 0;
}
return ret;
}
static int read_is_inter_block(VP9D_COMP *pbi, int segment_id, vp9_reader *r) {
@@ -436,15 +486,11 @@ static void read_inter_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
int mi_row, int mi_col, vp9_reader *r) {
VP9_COMMON *const cm = &pbi->common;
MACROBLOCKD *const xd = &pbi->mb;
nmv_context *const nmvc = &cm->fc.nmvc;
MB_MODE_INFO *const mbmi = &mi->mbmi;
int_mv *const mv0 = &mbmi->mv[0];
int_mv *const mv1 = &mbmi->mv[1];
const BLOCK_SIZE bsize = mbmi->sb_type;
const int allow_hp = xd->allow_high_precision_mv;
int_mv nearest, nearby, best_mv;
int_mv nearest_second, nearby_second, best_mv_second;
int_mv nearest[2], nearmv[2], best[2];
uint8_t inter_mode_ctx;
MV_REFERENCE_FRAME ref0;
int is_compound;
@@ -461,7 +507,11 @@ static void read_inter_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
if (vp9_segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) {
mbmi->mode = ZEROMV;
assert(bsize >= BLOCK_8X8);
if (bsize < BLOCK_8X8) {
vpx_internal_error(&cm->error, VPX_CODEC_UNSUP_BITSTREAM,
"Invalid usage of segement feature on small blocks");
return;
}
} else {
if (bsize >= BLOCK_8X8)
mbmi->mode = read_inter_mode(cm, r, inter_mode_ctx);
@@ -469,8 +519,8 @@ static void read_inter_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
// nearest, nearby
if (bsize < BLOCK_8X8 || mbmi->mode != ZEROMV) {
vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref0], &nearest, &nearby);
best_mv.as_int = mbmi->ref_mvs[ref0][0].as_int;
vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref0], &nearest[0], &nearmv[0]);
best[0].as_int = nearest[0].as_int;
}
if (is_compound) {
@@ -479,9 +529,8 @@ static void read_inter_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
ref1, mbmi->ref_mvs[ref1], mi_row, mi_col);
if (bsize < BLOCK_8X8 || mbmi->mode != ZEROMV) {
vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref1],
&nearest_second, &nearby_second);
best_mv_second.as_int = mbmi->ref_mvs[ref1][0].as_int;
vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref1], &nearest[1], &nearmv[1]);
best[1].as_int = nearest[1].as_int;
}
}
@@ -493,92 +542,50 @@ static void read_inter_block_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
const int num_4x4_w = num_4x4_blocks_wide_lookup[bsize]; // 1 or 2
const int num_4x4_h = num_4x4_blocks_high_lookup[bsize]; // 1 or 2
int idx, idy;
int b_mode;
for (idy = 0; idy < 2; idy += num_4x4_h) {
for (idx = 0; idx < 2; idx += num_4x4_w) {
int_mv blockmv, secondmv;
int_mv block[2];
const int j = idy * 2 + idx;
const int b_mode = read_inter_mode(cm, r, inter_mode_ctx);
b_mode = read_inter_mode(cm, r, inter_mode_ctx);
if (b_mode == NEARESTMV || b_mode == NEARMV) {
vp9_append_sub8x8_mvs_for_idx(cm, xd, &nearest, &nearby, j, 0,
vp9_append_sub8x8_mvs_for_idx(cm, xd, &nearest[0],
&nearmv[0], j, 0,
mi_row, mi_col);
if (is_compound)
vp9_append_sub8x8_mvs_for_idx(cm, xd, &nearest_second,
&nearby_second, j, 1,
mi_row, mi_col);
vp9_append_sub8x8_mvs_for_idx(cm, xd, &nearest[1],
&nearmv[1], j, 1,
mi_row, mi_col);
}
switch (b_mode) {
case NEWMV:
read_mv(r, &blockmv.as_mv, &best_mv.as_mv, nmvc,
&cm->counts.mv, allow_hp);
if (!assign_mv(cm, b_mode, block, best, nearest, nearmv,
is_compound, allow_hp, r)) {
xd->corrupted |= 1;
break;
};
if (is_compound)
read_mv(r, &secondmv.as_mv, &best_mv_second.as_mv, nmvc,
&cm->counts.mv, allow_hp);
break;
case NEARESTMV:
blockmv.as_int = nearest.as_int;
if (is_compound)
secondmv.as_int = nearest_second.as_int;
break;
case NEARMV:
blockmv.as_int = nearby.as_int;
if (is_compound)
secondmv.as_int = nearby_second.as_int;
break;
case ZEROMV:
blockmv.as_int = 0;
if (is_compound)
secondmv.as_int = 0;
break;
default:
assert(!"Invalid inter mode value");
}
mi->bmi[j].as_mv[0].as_int = blockmv.as_int;
mi->bmi[j].as_mv[0].as_int = block[0].as_int;
if (is_compound)
mi->bmi[j].as_mv[1].as_int = secondmv.as_int;
mi->bmi[j].as_mv[1].as_int = block[1].as_int;
if (num_4x4_h == 2)
mi->bmi[j + 2] = mi->bmi[j];
if (num_4x4_w == 2)
mi->bmi[j + 1] = mi->bmi[j];
mi->mbmi.mode = b_mode;
}
}
mv0->as_int = mi->bmi[3].as_mv[0].as_int;
mv1->as_int = mi->bmi[3].as_mv[1].as_int;
mi->mbmi.mode = b_mode;
mbmi->mv[0].as_int = mi->bmi[3].as_mv[0].as_int;
mbmi->mv[1].as_int = mi->bmi[3].as_mv[1].as_int;
} else {
switch (mbmi->mode) {
case NEARMV:
mv0->as_int = nearby.as_int;
if (is_compound)
mv1->as_int = nearby_second.as_int;
break;
case NEARESTMV:
mv0->as_int = nearest.as_int;
if (is_compound)
mv1->as_int = nearest_second.as_int;
break;
case ZEROMV:
mv0->as_int = 0;
if (is_compound)
mv1->as_int = 0;
break;
case NEWMV:
read_mv(r, &mv0->as_mv, &best_mv.as_mv, nmvc, &cm->counts.mv, allow_hp);
if (is_compound)
read_mv(r, &mv1->as_mv, &best_mv_second.as_mv, nmvc, &cm->counts.mv,
allow_hp);
break;
default:
assert(!"Invalid inter mode value");
}
xd->corrupted |= !assign_mv(cm, mbmi->mode, mbmi->mv,
best, nearest, nearmv,
is_compound, allow_hp, r);
}
}
@@ -610,21 +617,17 @@ static void read_comp_pred(VP9_COMMON *cm, vp9_reader *r) {
if (cm->comp_pred_mode == HYBRID_PREDICTION)
for (i = 0; i < COMP_INTER_CONTEXTS; i++)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.comp_inter_prob[i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.comp_inter_prob[i]);
if (cm->comp_pred_mode != COMP_PREDICTION_ONLY)
for (i = 0; i < REF_CONTEXTS; i++) {
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.single_ref_prob[i][0]);
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.single_ref_prob[i][1]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.single_ref_prob[i][0]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.single_ref_prob[i][1]);
}
if (cm->comp_pred_mode != SINGLE_PREDICTION_ONLY)
for (i = 0; i < REF_CONTEXTS; i++)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.comp_ref_prob[i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.comp_ref_prob[i]);
}
void vp9_prepare_read_mode_info(VP9D_COMP* pbi, vp9_reader *r) {
@@ -634,8 +637,7 @@ void vp9_prepare_read_mode_info(VP9D_COMP* pbi, vp9_reader *r) {
// TODO(jkoleszar): does this clear more than MBSKIP_CONTEXTS? Maybe remove.
// vpx_memset(cm->fc.mbskip_probs, 0, sizeof(cm->fc.mbskip_probs));
for (k = 0; k < MBSKIP_CONTEXTS; ++k)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.mbskip_probs[k]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.mbskip_probs[k]);
if (cm->frame_type != KEY_FRAME && !cm->intra_only) {
nmv_context *const nmvc = &pbi->common.fc.nmvc;
@@ -648,20 +650,18 @@ void vp9_prepare_read_mode_info(VP9D_COMP* pbi, vp9_reader *r) {
read_switchable_interp_probs(&cm->fc, r);
for (i = 0; i < INTRA_INTER_CONTEXTS; i++)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.intra_inter_prob[i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.intra_inter_prob[i]);
read_comp_pred(cm, r);
for (j = 0; j < BLOCK_SIZE_GROUPS; j++)
for (i = 0; i < INTRA_MODES - 1; ++i)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.y_mode_prob[j][i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &cm->fc.y_mode_prob[j][i]);
for (j = 0; j < NUM_PARTITION_CONTEXTS; ++j)
for (i = 0; i < PARTITION_TYPES - 1; ++i)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &cm->fc.partition_prob[INTER_FRAME][j][i]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB,
&cm->fc.partition_prob[INTER_FRAME][j][i]);
read_mv_probs(r, nmvc, xd->allow_high_precision_mv);
}

View File

@@ -63,18 +63,15 @@ static void read_tx_probs(struct tx_probs *tx_probs, vp9_reader *r) {
for (i = 0; i < TX_SIZE_CONTEXTS; ++i)
for (j = 0; j < TX_SIZES - 3; ++j)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &tx_probs->p8x8[i][j]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &tx_probs->p8x8[i][j]);
for (i = 0; i < TX_SIZE_CONTEXTS; ++i)
for (j = 0; j < TX_SIZES - 2; ++j)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &tx_probs->p16x16[i][j]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &tx_probs->p16x16[i][j]);
for (i = 0; i < TX_SIZE_CONTEXTS; ++i)
for (j = 0; j < TX_SIZES - 1; ++j)
if (vp9_read(r, MODE_UPDATE_PROB))
vp9_diff_update_prob(r, &tx_probs->p32x32[i][j]);
vp9_diff_update_prob(r, MODE_UPDATE_PROB, &tx_probs->p32x32[i][j]);
}
static void setup_plane_dequants(VP9_COMMON *cm, MACROBLOCKD *xd, int q_index) {
@@ -364,8 +361,8 @@ static void read_coef_probs_common(vp9_coeff_probs_model *coef_probs,
for (l = 0; l < PREV_COEF_CONTEXTS; l++)
if (k > 0 || l < 3)
for (m = 0; m < UNCONSTRAINED_NODES; m++)
if (vp9_read(r, VP9_COEF_UPDATE_PROB))
vp9_diff_update_prob(r, &coef_probs[i][j][k][l][m]);
vp9_diff_update_prob(r, VP9_COEF_UPDATE_PROB,
&coef_probs[i][j][k][l][m]);
}
static void read_coef_probs(FRAME_CONTEXT *fc, TX_MODE tx_mode,
@@ -492,7 +489,8 @@ static INTERPOLATIONFILTERTYPE read_interp_filter_type(
struct vp9_read_bit_buffer *rb) {
const INTERPOLATIONFILTERTYPE literal_to_type[] = { EIGHTTAP_SMOOTH,
EIGHTTAP,
EIGHTTAP_SHARP };
EIGHTTAP_SHARP,
BILINEAR };
return vp9_rb_read_bit(rb) ? SWITCHABLE
: literal_to_type[vp9_rb_read_literal(rb, 2)];
}
@@ -794,6 +792,7 @@ static size_t read_uncompressed_header(VP9D_COMP *pbi,
struct vp9_read_bit_buffer *rb) {
VP9_COMMON *const cm = &pbi->common;
MACROBLOCKD *const xd = &pbi->mb;
size_t sz;
int i;
cm->last_frame_type = cm->frame_type;
@@ -899,8 +898,13 @@ static size_t read_uncompressed_header(VP9D_COMP *pbi,
setup_segmentation(&cm->seg, rb);
setup_tile_info(cm, rb);
sz = vp9_rb_read_literal(rb, 16);
return vp9_rb_read_literal(rb, 16);
if (sz == 0)
vpx_internal_error(&cm->error, VPX_CODEC_CORRUPT_FRAME,
"Invalid header size");
return sz;
}
static int read_compressed_header(VP9D_COMP *pbi, const uint8_t *data,
@@ -950,9 +954,9 @@ int vp9_decode_frame(VP9D_COMP *pbi, const uint8_t **p_data_end) {
YV12_BUFFER_CONFIG *new_fb = &cm->yv12_fb[cm->new_fb_idx];
if (!first_partition_size) {
// showing a frame directly
*p_data_end = data + 1;
return 0;
// showing a frame directly
*p_data_end = data + 1;
return 0;
}
data += vp9_rb_bytes_read(&rb);
xd->corrupted = 0;

View File

@@ -48,8 +48,6 @@ static int merge_index(int v, int n, int modulus) {
static int inv_remap_prob(int v, int m) {
static int inv_map_table[MAX_PROB - 1] = {
// generated by:
// inv_map_table[j] = merge_index(j, MAX_PROB - 1, MODULUS_PARAM);
6, 19, 32, 45, 58, 71, 84, 97, 110, 123, 136, 149, 162, 175, 188,
201, 214, 227, 240, 253, 0, 1, 2, 3, 4, 5, 7, 8, 9, 10,
11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22, 23, 24, 25, 26,
@@ -66,10 +64,11 @@ static int inv_remap_prob(int v, int m) {
190, 191, 192, 193, 194, 195, 196, 197, 198, 199, 200, 202, 203, 204, 205,
206, 207, 208, 209, 210, 211, 212, 213, 215, 216, 217, 218, 219, 220, 221,
222, 223, 224, 225, 226, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237,
238, 239, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252,
238, 239, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252
};
// v = merge_index(v, MAX_PROBS - 1, MODULUS_PARAM);
// The clamp is not necessary for conforming VP9 stream, it is added to
// prevent out of bound access for bad input data
v = clamp(v, 0, 253);
v = inv_map_table[v];
m--;
if ((m << 1) <= MAX_PROB) {
@@ -100,7 +99,9 @@ static int decode_term_subexp(vp9_reader *r, int k, int num_syms) {
return word;
}
void vp9_diff_update_prob(vp9_reader *r, vp9_prob* p) {
int delp = decode_term_subexp(r, SUBEXP_PARAM, 255);
*p = (vp9_prob)inv_remap_prob(delp, *p);
void vp9_diff_update_prob(vp9_reader *r, int update_prob, vp9_prob* p) {
if (vp9_read(r, update_prob)) {
const int delp = decode_term_subexp(r, SUBEXP_PARAM, 255);
*p = (vp9_prob)inv_remap_prob(delp, *p);
}
}

View File

@@ -14,6 +14,6 @@
#include "vp9/decoder/vp9_dboolhuff.h"
void vp9_diff_update_prob(vp9_reader *r, vp9_prob* p);
void vp9_diff_update_prob(vp9_reader *r, int update_prob, vp9_prob* p);
#endif // VP9_DECODER_VP9_DSUBEXP_H_

View File

@@ -1162,7 +1162,7 @@ static void encode_txfm_probs(VP9_COMP *cpi, vp9_writer *w) {
static void write_interp_filter_type(INTERPOLATIONFILTERTYPE type,
struct vp9_write_bit_buffer *wb) {
const int type_to_literal[] = { 1, 0, 2 };
const int type_to_literal[] = { 1, 0, 2, 3 };
vp9_wb_write_bit(wb, type == SWITCHABLE);
if (type != SWITCHABLE)

View File

@@ -655,8 +655,10 @@ static vpx_codec_err_t get_frame_corrupted(vpx_codec_alg_priv_t *ctx,
if (corrupted) {
VP9D_COMP *pbi = (VP9D_COMP *)ctx->pbi;
*corrupted = pbi->common.frame_to_show->corrupted;
if (pbi)
*corrupted = pbi->common.frame_to_show->corrupted;
else
return VPX_CODEC_ERROR;
return VPX_CODEC_OK;
} else
return VPX_CODEC_INVALID_PARAM;