Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
Xiph.Org
aom-rav1e
Commits
44da65fb
Commit
44da65fb
authored
Jan 14, 2016
by
Yaowu Xu
Browse files
Merge branch 'master' into nextgenv2
parents
c38fc52d
dcc0c894
Changes
23
Hide whitespace changes
Inline
Side-by-side
configure
View file @
44da65fb
...
...
@@ -263,9 +263,7 @@ ARCH_EXT_LIST="
HAVE_LIST
=
"
${
ARCH_EXT_LIST
}
vpx_ports
stdint_h
pthread_h
sys_mman_h
unistd_h
"
EXPERIMENT_LIST
=
"
...
...
@@ -559,16 +557,12 @@ process_detect() {
# Specialize windows and POSIX environments.
case
$toolchain
in
*
-win
*
-
*
)
case
$header
-
$toolchain
in
stdint
*
-gcc
)
true
;;
*
)
false
;;
esac
&&
enable_feature
$var
;;
# Don't check for any headers in Windows builds.
false
;;
*
)
case
$header
in
stdint.h
)
true
;;
pthread.h
)
true
;;
sys/mman.h
)
true
;;
unistd.h
)
true
;;
*
)
false
;;
esac
&&
enable_feature
$var
...
...
@@ -584,9 +578,7 @@ process_detect() {
int main(void) {return 0;}
EOF
# check system headers
check_header stdint.h
check_header pthread.h
check_header sys/mman.h
check_header unistd.h
# for sysconf(3) and friends.
check_header vpx/vpx_integer.h
-I
${
source_path
}
&&
enable_feature vpx_ports
...
...
examples/vp8_multi_resolution_encoder.c
View file @
44da65fb
...
...
@@ -29,13 +29,6 @@
#include
<math.h>
#include
<assert.h>
#include
<sys/time.h>
#if USE_POSIX_MMAP
#include
<sys/types.h>
#include
<sys/stat.h>
#include
<sys/mman.h>
#include
<fcntl.h>
#include
<unistd.h>
#endif
#include
"vpx_ports/vpx_timer.h"
#include
"vpx/vpx_encoder.h"
#include
"vpx/vp8cx.h"
...
...
vp10/encoder/aq_complexity.c
View file @
44da65fb
...
...
@@ -51,7 +51,7 @@ void vp10_setup_in_frame_q_adj(VP10_COMP *cpi) {
// Make SURE use of floating point in this function is safe.
vpx_clear_system_state
();
if
(
cm
->
frame_
type
==
KEY_FRAME
||
if
(
frame_
is_intra_only
(
cm
)
||
cm
->
error_resilient_mode
||
cpi
->
refresh_alt_ref_frame
||
(
cpi
->
refresh_golden_frame
&&
!
cpi
->
rc
.
is_src_frame_alt_ref
))
{
int
segment
;
...
...
vp10/encoder/aq_variance.c
View file @
44da65fb
...
...
@@ -47,7 +47,7 @@ void vp10_vaq_frame_setup(VP10_COMP *cpi) {
struct
segmentation
*
seg
=
&
cm
->
seg
;
int
i
;
if
(
cm
->
frame_
type
==
KEY_FRAME
||
if
(
frame_
is_intra_only
(
cm
)
||
cm
->
error_resilient_mode
||
cpi
->
refresh_alt_ref_frame
||
(
cpi
->
refresh_golden_frame
&&
!
cpi
->
rc
.
is_src_frame_alt_ref
))
{
vp10_enable_segmentation
(
seg
);
...
...
vp10/encoder/segmentation.c
View file @
44da65fb
...
...
@@ -250,7 +250,7 @@ void vp10_choose_segmap_coding_method(VP10_COMMON *cm, MACROBLOCKD *xd) {
no_pred_cost
=
cost_segmap
(
no_pred_segcounts
,
no_pred_tree
);
// Key frames cannot use temporal prediction
if
(
!
frame_is_intra_only
(
cm
))
{
if
(
!
frame_is_intra_only
(
cm
)
&&
!
cm
->
error_resilient_mode
)
{
// Work out probability tree for coding those segments not
// predicted using the temporal method and the cost.
calc_segtree_probs
(
t_unpred_seg_counts
,
t_pred_tree
,
segp
->
tree_probs
);
...
...
@@ -273,6 +273,7 @@ void vp10_choose_segmap_coding_method(VP10_COMMON *cm, MACROBLOCKD *xd) {
// Now choose which coding method to use.
if
(
t_pred_cost
<
no_pred_cost
)
{
assert
(
!
cm
->
error_resilient_mode
);
seg
->
temporal_update
=
1
;
}
else
{
seg
->
temporal_update
=
0
;
...
...
vp9/common/vp9_entropymv.c
View file @
44da65fb
...
...
@@ -11,9 +11,6 @@
#include
"vp9/common/vp9_onyxc_int.h"
#include
"vp9/common/vp9_entropymv.h"
// Integer pel reference mv threshold for use of high-precision 1/8 mv
#define COMPANDED_MVREF_THRESH 8
const
vpx_tree_index
vp9_mv_joint_tree
[
TREE_SIZE
(
MV_JOINTS
)]
=
{
-
MV_JOINT_ZERO
,
2
,
-
MV_JOINT_HNZVZ
,
4
,
...
...
@@ -127,11 +124,6 @@ MV_CLASS_TYPE vp9_get_mv_class(int z, int *offset) {
return
c
;
}
int
vp9_use_mv_hp
(
const
MV
*
ref
)
{
return
(
abs
(
ref
->
row
)
>>
3
)
<
COMPANDED_MVREF_THRESH
&&
(
abs
(
ref
->
col
)
>>
3
)
<
COMPANDED_MVREF_THRESH
;
}
static
void
inc_mv_component
(
int
v
,
nmv_component_counts
*
comp_counts
,
int
incr
,
int
usehp
)
{
int
s
,
z
,
c
,
o
,
d
,
e
,
f
;
...
...
vp9/common/vp9_entropymv.h
View file @
44da65fb
...
...
@@ -27,7 +27,14 @@ struct VP9Common;
void
vp9_init_mv_probs
(
struct
VP9Common
*
cm
);
void
vp9_adapt_mv_probs
(
struct
VP9Common
*
cm
,
int
usehp
);
int
vp9_use_mv_hp
(
const
MV
*
ref
);
// Integer pel reference mv threshold for use of high-precision 1/8 mv
#define COMPANDED_MVREF_THRESH 8
static
INLINE
int
use_mv_hp
(
const
MV
*
ref
)
{
return
(
abs
(
ref
->
row
)
>>
3
)
<
COMPANDED_MVREF_THRESH
&&
(
abs
(
ref
->
col
)
>>
3
)
<
COMPANDED_MVREF_THRESH
;
}
#define MV_UPDATE_PROB 252
...
...
vp9/common/vp9_mvref_common.c
View file @
44da65fb
...
...
@@ -11,20 +11,19 @@
#include
"vp9/common/vp9_mvref_common.h"
// This function searches the neighbo
u
rhood of a given MB/SB
// This function searches the neighborhood of a given MB/SB
// to try and find candidate reference vectors.
static
void
find_mv_refs_idx
(
const
VP9_COMMON
*
cm
,
const
MACROBLOCKD
*
xd
,
MODE_INFO
*
mi
,
MV_REFERENCE_FRAME
ref_frame
,
int_mv
*
mv_ref_list
,
int
block
,
int
mi_row
,
int
mi_col
,
find_mv_refs_sync
sync
,
void
*
const
data
,
uint8_t
*
mode_context
)
{
const
int
*
ref_sign_bias
=
cm
->
ref_frame_sign_bias
;
int
i
,
refmv_count
=
0
;
const
POSITION
*
const
mv_ref_search
=
mv_ref_blocks
[
mi
->
mbmi
.
sb_type
];
int
different_ref_found
=
0
;
int
context_counter
=
0
;
const
MV_REF
*
const
prev_frame_mvs
=
cm
->
use_prev_frame_mvs
?
const
MV_REF
*
const
prev_frame_mvs
=
cm
->
use_prev_frame_mvs
?
cm
->
prev_frame
->
mvs
+
mi_row
*
cm
->
mi_cols
+
mi_col
:
NULL
;
const
TileInfo
*
const
tile
=
&
xd
->
tile
;
...
...
@@ -59,8 +58,8 @@ static void find_mv_refs_idx(const VP9_COMMON *cm, const MACROBLOCKD *xd,
for
(;
i
<
MVREF_NEIGHBOURS
;
++
i
)
{
const
POSITION
*
const
mv_ref
=
&
mv_ref_search
[
i
];
if
(
is_inside
(
tile
,
mi_col
,
mi_row
,
cm
->
mi_rows
,
mv_ref
))
{
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
different_ref_found
=
1
;
if
(
candidate
->
ref_frame
[
0
]
==
ref_frame
)
...
...
@@ -70,23 +69,8 @@ static void find_mv_refs_idx(const VP9_COMMON *cm, const MACROBLOCKD *xd,
}
}
// TODO(hkuang): Remove this sync after fixing pthread_cond_broadcast
// on windows platform. The sync here is unncessary if use_perv_frame_mvs
// is 0. But after removing it, there will be hang in the unit test on windows
// due to several threads waiting for a thread's signal.
#if defined(_WIN32) && !HAVE_PTHREAD_H
if
(
cm
->
frame_parallel_decode
&&
sync
!=
NULL
)
{
sync
(
data
,
mi_row
);
}
#endif
// Check the last frame's mode and mv info.
if
(
cm
->
use_prev_frame_mvs
)
{
// Synchronize here for frame parallel decode if sync function is provided.
if
(
cm
->
frame_parallel_decode
&&
sync
!=
NULL
)
{
sync
(
data
,
mi_row
);
}
if
(
prev_frame_mvs
->
ref_frame
[
0
]
==
ref_frame
)
{
ADD_MV_REF_LIST
(
prev_frame_mvs
->
mv
[
0
],
refmv_count
,
mv_ref_list
,
Done
);
}
else
if
(
prev_frame_mvs
->
ref_frame
[
1
]
==
ref_frame
)
{
...
...
@@ -101,8 +85,8 @@ static void find_mv_refs_idx(const VP9_COMMON *cm, const MACROBLOCKD *xd,
for
(
i
=
0
;
i
<
MVREF_NEIGHBOURS
;
++
i
)
{
const
POSITION
*
mv_ref
=
&
mv_ref_search
[
i
];
if
(
is_inside
(
tile
,
mi_col
,
mi_row
,
cm
->
mi_rows
,
mv_ref
))
{
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
// If the candidate is INTRA we don't want to consider its mv.
IF_DIFF_REF_FRAME_ADD_MV
(
candidate
,
ref_frame
,
ref_sign_bias
,
...
...
@@ -150,20 +134,9 @@ void vp9_find_mv_refs(const VP9_COMMON *cm, const MACROBLOCKD *xd,
MODE_INFO
*
mi
,
MV_REFERENCE_FRAME
ref_frame
,
int_mv
*
mv_ref_list
,
int
mi_row
,
int
mi_col
,
find_mv_refs_sync
sync
,
void
*
const
data
,
uint8_t
*
mode_context
)
{
find_mv_refs_idx
(
cm
,
xd
,
mi
,
ref_frame
,
mv_ref_list
,
-
1
,
mi_row
,
mi_col
,
sync
,
data
,
mode_context
);
}
static
void
lower_mv_precision
(
MV
*
mv
,
int
allow_hp
)
{
const
int
use_hp
=
allow_hp
&&
vp9_use_mv_hp
(
mv
);
if
(
!
use_hp
)
{
if
(
mv
->
row
&
1
)
mv
->
row
+=
(
mv
->
row
>
0
?
-
1
:
1
);
if
(
mv
->
col
&
1
)
mv
->
col
+=
(
mv
->
col
>
0
?
-
1
:
1
);
}
mi_row
,
mi_col
,
mode_context
);
}
void
vp9_find_best_ref_mvs
(
MACROBLOCKD
*
xd
,
int
allow_hp
,
...
...
@@ -191,7 +164,7 @@ void vp9_append_sub8x8_mvs_for_idx(VP9_COMMON *cm, MACROBLOCKD *xd,
assert
(
MAX_MV_REF_CANDIDATES
==
2
);
find_mv_refs_idx
(
cm
,
xd
,
mi
,
mi
->
mbmi
.
ref_frame
[
ref
],
mv_list
,
block
,
mi_row
,
mi_col
,
NULL
,
NULL
,
mode_context
);
mi_row
,
mi_col
,
mode_context
);
near_mv
->
as_int
=
0
;
switch
(
block
)
{
...
...
vp9/common/vp9_mvref_common.h
View file @
44da65fb
...
...
@@ -157,7 +157,7 @@ static INLINE int_mv scale_mv(const MB_MODE_INFO *mbmi, int ref,
// This macro is used to add a motion vector mv_ref list if it isn't
// already in the list. If it's the second motion vector it will also
// skip all additional processing and jump to
d
one!
// skip all additional processing and jump to
D
one!
#define ADD_MV_REF_LIST(mv, refmv_count, mv_ref_list, Done) \
do { \
if (refmv_count) { \
...
...
@@ -207,11 +207,20 @@ static INLINE void clamp_mv2(MV *mv, const MACROBLOCKD *xd) {
xd
->
mb_to_bottom_edge
+
RIGHT_BOTTOM_MARGIN
);
}
static
INLINE
void
lower_mv_precision
(
MV
*
mv
,
int
allow_hp
)
{
const
int
use_hp
=
allow_hp
&&
use_mv_hp
(
mv
);
if
(
!
use_hp
)
{
if
(
mv
->
row
&
1
)
mv
->
row
+=
(
mv
->
row
>
0
?
-
1
:
1
);
if
(
mv
->
col
&
1
)
mv
->
col
+=
(
mv
->
col
>
0
?
-
1
:
1
);
}
}
typedef
void
(
*
find_mv_refs_sync
)(
void
*
const
data
,
int
mi_row
);
void
vp9_find_mv_refs
(
const
VP9_COMMON
*
cm
,
const
MACROBLOCKD
*
xd
,
MODE_INFO
*
mi
,
MV_REFERENCE_FRAME
ref_frame
,
int_mv
*
mv_ref_list
,
int
mi_row
,
int
mi_col
,
find_mv_refs_sync
sync
,
void
*
const
data
,
uint8_t
*
mode_context
);
// check a list of motion vectors by sad score using a number rows of pixels
...
...
vp9/decoder/vp9_decodeframe.c
View file @
44da65fb
...
...
@@ -719,6 +719,18 @@ static void dec_build_inter_predictors_sb(VP9Decoder *const pbi,
const
InterpKernel
*
kernel
=
vp9_filter_kernels
[
mi
->
mbmi
.
interp_filter
];
const
BLOCK_SIZE
sb_type
=
mi
->
mbmi
.
sb_type
;
const
int
is_compound
=
has_second_ref
(
&
mi
->
mbmi
);
int
ref
;
for
(
ref
=
0
;
ref
<
1
+
is_compound
;
++
ref
)
{
const
MV_REFERENCE_FRAME
frame
=
mi
->
mbmi
.
ref_frame
[
ref
];
RefBuffer
*
ref_buf
=
&
pbi
->
common
.
frame_refs
[
frame
-
LAST_FRAME
];
xd
->
block_refs
[
ref
]
=
ref_buf
;
if
(
!
vp9_is_valid_scale
(
&
ref_buf
->
sf
))
vpx_internal_error
(
xd
->
error_info
,
VPX_CODEC_UNSUP_BITSTREAM
,
"Reference frame has invalid dimensions"
);
vp9_setup_pre_planes
(
xd
,
ref
,
ref_buf
->
buf
,
mi_row
,
mi_col
,
&
ref_buf
->
sf
);
}
for
(
plane
=
0
;
plane
<
MAX_MB_PLANE
;
++
plane
)
{
struct
macroblockd_plane
*
const
pd
=
&
xd
->
plane
[
plane
];
...
...
vp9/decoder/vp9_decodemv.c
View file @
44da65fb
...
...
@@ -289,7 +289,7 @@ static INLINE void read_mv(vpx_reader *r, MV *mv, const MV *ref,
nmv_context_counts
*
counts
,
int
allow_hp
)
{
const
MV_JOINT_TYPE
joint_type
=
(
MV_JOINT_TYPE
)
vpx_read_tree
(
r
,
vp9_mv_joint_tree
,
ctx
->
joints
);
const
int
use_hp
=
allow_hp
&&
vp9_
use_mv_hp
(
ref
);
const
int
use_hp
=
allow_hp
&&
use_mv_hp
(
ref
);
MV
diff
=
{
0
,
0
};
if
(
mv_joint_vertical
(
joint_type
))
...
...
@@ -476,12 +476,203 @@ static int read_is_inter_block(VP9_COMMON *const cm, MACROBLOCKD *const xd,
}
}
static
void
dec_find_best_ref_mvs
(
MACROBLOCKD
*
xd
,
int
allow_hp
,
int_mv
*
mvlist
,
int_mv
*
nearest_mv
,
int_mv
*
near_mv
,
int
refmv_count
)
{
int
i
;
// Make sure all the candidates are properly clamped etc
for
(
i
=
0
;
i
<
refmv_count
;
++
i
)
{
lower_mv_precision
(
&
mvlist
[
i
].
as_mv
,
allow_hp
);
clamp_mv2
(
&
mvlist
[
i
].
as_mv
,
xd
);
}
*
nearest_mv
=
mvlist
[
0
];
*
near_mv
=
mvlist
[
1
];
}
static
void
fpm_sync
(
void
*
const
data
,
int
mi_row
)
{
VP9Decoder
*
const
pbi
=
(
VP9Decoder
*
)
data
;
vp9_frameworker_wait
(
pbi
->
frame_worker_owner
,
pbi
->
common
.
prev_frame
,
mi_row
<<
MI_BLOCK_SIZE_LOG2
);
}
// This macro is used to add a motion vector mv_ref list if it isn't
// already in the list. If it's the second motion vector or early_break
// it will also skip all additional processing and jump to Done!
#define ADD_MV_REF_LIST_EB(mv, refmv_count, mv_ref_list, Done) \
do { \
if (refmv_count) { \
if ((mv).as_int != (mv_ref_list)[0].as_int) { \
(mv_ref_list)[(refmv_count)] = (mv); \
refmv_count++; \
goto Done; \
} \
} else { \
(mv_ref_list)[(refmv_count)++] = (mv); \
if (early_break) \
goto Done; \
} \
} while (0)
// If either reference frame is different, not INTRA, and they
// are different from each other scale and add the mv to our list.
#define IF_DIFF_REF_FRAME_ADD_MV_EB(mbmi, ref_frame, ref_sign_bias, \
refmv_count, mv_ref_list, Done) \
do { \
if (is_inter_block(mbmi)) { \
if ((mbmi)->ref_frame[0] != ref_frame) \
ADD_MV_REF_LIST_EB(scale_mv((mbmi), 0, ref_frame, ref_sign_bias), \
refmv_count, mv_ref_list, Done); \
if (has_second_ref(mbmi) && \
(mbmi)->ref_frame[1] != ref_frame && \
(mbmi)->mv[1].as_int != (mbmi)->mv[0].as_int) \
ADD_MV_REF_LIST_EB(scale_mv((mbmi), 1, ref_frame, ref_sign_bias), \
refmv_count, mv_ref_list, Done); \
} \
} while (0)
// This function searches the neighborhood of a given MB/SB
// to try and find candidate reference vectors.
static
int
dec_find_mv_refs
(
const
VP9_COMMON
*
cm
,
const
MACROBLOCKD
*
xd
,
MODE_INFO
*
mi
,
MV_REFERENCE_FRAME
ref_frame
,
const
POSITION
*
const
mv_ref_search
,
int_mv
*
mv_ref_list
,
int
mi_row
,
int
mi_col
,
find_mv_refs_sync
sync
,
void
*
const
data
)
{
const
int
*
ref_sign_bias
=
cm
->
ref_frame_sign_bias
;
int
i
,
refmv_count
=
0
;
int
different_ref_found
=
0
;
const
MV_REF
*
const
prev_frame_mvs
=
cm
->
use_prev_frame_mvs
?
cm
->
prev_frame
->
mvs
+
mi_row
*
cm
->
mi_cols
+
mi_col
:
NULL
;
const
TileInfo
*
const
tile
=
&
xd
->
tile
;
// If mode is nearestmv or newmv (uses nearestmv as a reference) then stop
// searching after the first mv is found.
const
int
early_break
=
(
mi
->
mbmi
.
mode
==
NEARESTMV
)
||
(
mi
->
mbmi
.
mode
==
NEWMV
);
// Blank the reference vector list
memset
(
mv_ref_list
,
0
,
sizeof
(
*
mv_ref_list
)
*
MAX_MV_REF_CANDIDATES
);
// Check the rest of the neighbors in much the same way
// as before except we don't need to keep track of sub blocks or
// mode counts.
for
(
i
=
0
;
i
<
MVREF_NEIGHBOURS
;
++
i
)
{
const
POSITION
*
const
mv_ref
=
&
mv_ref_search
[
i
];
if
(
is_inside
(
tile
,
mi_col
,
mi_row
,
cm
->
mi_rows
,
mv_ref
))
{
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
different_ref_found
=
1
;
if
(
candidate
->
ref_frame
[
0
]
==
ref_frame
)
ADD_MV_REF_LIST_EB
(
candidate
->
mv
[
0
],
refmv_count
,
mv_ref_list
,
Done
);
else
if
(
candidate
->
ref_frame
[
1
]
==
ref_frame
)
ADD_MV_REF_LIST_EB
(
candidate
->
mv
[
1
],
refmv_count
,
mv_ref_list
,
Done
);
}
}
// TODO(hkuang): Remove this sync after fixing pthread_cond_broadcast
// on windows platform. The sync here is unnecessary if use_prev_frame_mvs
// is 0. But after removing it, there will be hang in the unit test on windows
// due to several threads waiting for a thread's signal.
#if defined(_WIN32) && !HAVE_PTHREAD_H
if
(
cm
->
frame_parallel_decode
&&
sync
!=
NULL
)
{
sync
(
data
,
mi_row
);
}
#endif
// Check the last frame's mode and mv info.
if
(
prev_frame_mvs
)
{
// Synchronize here for frame parallel decode if sync function is provided.
if
(
cm
->
frame_parallel_decode
&&
sync
!=
NULL
)
{
sync
(
data
,
mi_row
);
}
if
(
prev_frame_mvs
->
ref_frame
[
0
]
==
ref_frame
)
{
ADD_MV_REF_LIST_EB
(
prev_frame_mvs
->
mv
[
0
],
refmv_count
,
mv_ref_list
,
Done
);
}
else
if
(
prev_frame_mvs
->
ref_frame
[
1
]
==
ref_frame
)
{
ADD_MV_REF_LIST_EB
(
prev_frame_mvs
->
mv
[
1
],
refmv_count
,
mv_ref_list
,
Done
);
}
}
// Since we couldn't find 2 mvs from the same reference frame
// go back through the neighbors and find motion vectors from
// different reference frames.
if
(
different_ref_found
)
{
for
(
i
=
0
;
i
<
MVREF_NEIGHBOURS
;
++
i
)
{
const
POSITION
*
mv_ref
=
&
mv_ref_search
[
i
];
if
(
is_inside
(
tile
,
mi_col
,
mi_row
,
cm
->
mi_rows
,
mv_ref
))
{
const
MB_MODE_INFO
*
const
candidate
=
&
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
]
->
mbmi
;
// If the candidate is INTRA we don't want to consider its mv.
IF_DIFF_REF_FRAME_ADD_MV_EB
(
candidate
,
ref_frame
,
ref_sign_bias
,
refmv_count
,
mv_ref_list
,
Done
);
}
}
}
// Since we still don't have a candidate we'll try the last frame.
if
(
prev_frame_mvs
)
{
if
(
prev_frame_mvs
->
ref_frame
[
0
]
!=
ref_frame
&&
prev_frame_mvs
->
ref_frame
[
0
]
>
INTRA_FRAME
)
{
int_mv
mv
=
prev_frame_mvs
->
mv
[
0
];
if
(
ref_sign_bias
[
prev_frame_mvs
->
ref_frame
[
0
]]
!=
ref_sign_bias
[
ref_frame
])
{
mv
.
as_mv
.
row
*=
-
1
;
mv
.
as_mv
.
col
*=
-
1
;
}
ADD_MV_REF_LIST_EB
(
mv
,
refmv_count
,
mv_ref_list
,
Done
);
}
if
(
prev_frame_mvs
->
ref_frame
[
1
]
>
INTRA_FRAME
&&
prev_frame_mvs
->
ref_frame
[
1
]
!=
ref_frame
&&
prev_frame_mvs
->
mv
[
1
].
as_int
!=
prev_frame_mvs
->
mv
[
0
].
as_int
)
{
int_mv
mv
=
prev_frame_mvs
->
mv
[
1
];
if
(
ref_sign_bias
[
prev_frame_mvs
->
ref_frame
[
1
]]
!=
ref_sign_bias
[
ref_frame
])
{
mv
.
as_mv
.
row
*=
-
1
;
mv
.
as_mv
.
col
*=
-
1
;
}
ADD_MV_REF_LIST_EB
(
mv
,
refmv_count
,
mv_ref_list
,
Done
);
}
}
if
(
mi
->
mbmi
.
mode
==
NEARMV
)
refmv_count
=
MAX_MV_REF_CANDIDATES
;
else
// we only care about the nearestmv for the remaining modes
refmv_count
=
1
;
Done:
// Clamp vectors
for
(
i
=
0
;
i
<
refmv_count
;
++
i
)
clamp_mv_ref
(
&
mv_ref_list
[
i
].
as_mv
,
xd
);
return
refmv_count
;
}
static
uint8_t
get_mode_context
(
const
VP9_COMMON
*
cm
,
const
MACROBLOCKD
*
xd
,
const
POSITION
*
const
mv_ref_search
,
int
mi_row
,
int
mi_col
)
{
int
i
;
int
context_counter
=
0
;
const
TileInfo
*
const
tile
=
&
xd
->
tile
;
// Get mode count from nearest 2 blocks
for
(
i
=
0
;
i
<
2
;
++
i
)
{
const
POSITION
*
const
mv_ref
=
&
mv_ref_search
[
i
];
if
(
is_inside
(
tile
,
mi_col
,
mi_row
,
cm
->
mi_rows
,
mv_ref
))
{
const
MODE_INFO
*
const
candidate_mi
=
xd
->
mi
[
mv_ref
->
col
+
mv_ref
->
row
*
xd
->
mi_stride
];
const
MB_MODE_INFO
*
const
candidate
=
&
candidate_mi
->
mbmi
;
// Keep counts for entropy encoding.
context_counter
+=
mode_2_counter
[
candidate
->
mode
];
}
}
return
counter_to_context
[
context_counter
];
}
static
void
read_inter_block_mode_info
(
VP9Decoder
*
const
pbi
,
MACROBLOCKD
*
const
xd
,
MODE_INFO
*
const
mi
,
...
...
@@ -491,26 +682,13 @@ static void read_inter_block_mode_info(VP9Decoder *const pbi,
const
BLOCK_SIZE
bsize
=
mbmi
->
sb_type
;
const
int
allow_hp
=
cm
->
allow_high_precision_mv
;
int_mv
nearestmv
[
2
],
nearmv
[
2
];
int_mv
ref_mvs
[
MAX_REF_FRAMES
][
MAX_MV_REF_CANDIDATES
];
int
ref
,
is_compound
;
uint8_t
inter_mode_ctx
[
MAX_REF_FRAMES
];
uint8_t
inter_mode_ctx
;
const
POSITION
*
const
mv_ref_search
=
mv_ref_blocks
[
bsize
];
read_ref_frames
(
cm
,
xd
,
r
,
mbmi
->
segment_id
,
mbmi
->
ref_frame
);
is_compound
=
has_second_ref
(
mbmi
);
for
(
ref
=
0
;
ref
<
1
+
is_compound
;
++
ref
)
{
const
MV_REFERENCE_FRAME
frame
=
mbmi
->
ref_frame
[
ref
];
RefBuffer
*
ref_buf
=
&
cm
->
frame_refs
[
frame
-
LAST_FRAME
];
xd
->
block_refs
[
ref
]
=
ref_buf
;
if
((
!
vp9_is_valid_scale
(
&
ref_buf
->
sf
)))
vpx_internal_error
(
xd
->
error_info
,
VPX_CODEC_UNSUP_BITSTREAM
,
"Reference frame has invalid dimensions"
);
vp9_setup_pre_planes
(
xd
,
ref
,
ref_buf
->
buf
,
mi_row
,
mi_col
,
&
ref_buf
->
sf
);
vp9_find_mv_refs
(
cm
,
xd
,
mi
,
frame
,
ref_mvs
[
frame
],
mi_row
,
mi_col
,
fpm_sync
,
(
void
*
)
pbi
,
inter_mode_ctx
);
}
inter_mode_ctx
=
get_mode_context
(
cm
,
xd
,
mv_ref_search
,
mi_row
,
mi_col
);
if
(
segfeature_active
(
&
cm
->
seg
,
mbmi
->
segment_id
,
SEG_LVL_SKIP
))
{
mbmi
->
mode
=
ZEROMV
;
...
...
@@ -521,14 +699,27 @@ static void read_inter_block_mode_info(VP9Decoder *const pbi,
}
}
else
{
if
(
bsize
>=
BLOCK_8X8
)
mbmi
->
mode
=
read_inter_mode
(
cm
,
xd
,
r
,
inter_mode_ctx
[
mbmi
->
ref_frame
[
0
]]);
}
if
(
bsize
<
BLOCK_8X8
||
mbmi
->
mode
!=
ZEROMV
)
{
for
(
ref
=
0
;
ref
<
1
+
is_compound
;
++
ref
)
{
vp9_find_best_ref_mvs
(
xd
,
allow_hp
,
ref_mvs
[
mbmi
->
ref_frame
[
ref
]],
&
nearestmv
[
ref
],
&
nearmv
[
ref
]);
mbmi
->
mode
=
read_inter_mode
(
cm
,
xd
,
r
,
inter_mode_ctx
);
else
// Sub 8x8 blocks use the nearestmv as a ref_mv if the b_mode is NEWMV.
// Setting mode to NEARESTMV forces the search to stop after the nearestmv
// has been found. After b_modes have been read, mode will be overwritten
// by the last b_mode.
mbmi
->
mode
=
NEARESTMV
;
if
(
mbmi
->
mode
!=
ZEROMV
)
{
for
(
ref
=
0
;
ref
<
1
+
is_compound
;
++
ref
)
{
int_mv
ref_mvs
[
MAX_MV_REF_CANDIDATES
];
const
MV_REFERENCE_FRAME
frame
=
mbmi
->
ref_frame
[
ref
];
int
refmv_count
;
refmv_count
=
dec_find_mv_refs
(
cm
,
xd
,
mi
,
frame
,
mv_ref_search
,
ref_mvs
,
mi_row
,
mi_col
,
fpm_sync
,
(
void
*
)
pbi
);
dec_find_best_ref_mvs
(
xd
,
allow_hp
,
ref_mvs
,
&
nearestmv
[
ref
],
&
nearmv
[
ref
],
refmv_count
);
}
}
}
...
...
@@ -546,7 +737,7 @@ static void read_inter_block_mode_info(VP9Decoder *const pbi,
for
(
idx
=
0
;
idx
<
2
;
idx
+=
num_4x4_w
)
{
int_mv
block
[
2
];
const
int
j
=
idy
*
2
+
idx
;
b_mode
=
read_inter_mode
(
cm
,
xd
,
r
,
inter_mode_ctx
[
mbmi
->
ref_frame
[
0
]]
);
b_mode
=
read_inter_mode
(
cm
,
xd
,
r
,
inter_mode_ctx
);
if
(
b_mode
==
NEARESTMV
||
b_mode
==
NEARMV
)
{
uint8_t
dummy_mode_ctx
[
MAX_REF_FRAMES
];
...
...
vp9/encoder/vp9_aq_360.c
0 → 100644
View file @
44da65fb
/*
* Copyright (c) 2013 The WebM project authors. All Rights Reserved.
*
* Use of this source code is governed by a BSD-style license
* that can be found in the LICENSE file in the root of the source
* tree. An additional intellectual property rights grant can be found
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
#include
<math.h>
#include
"vpx_ports/mem.h"
#include
"vpx_ports/system_state.h"
#include
"vp9/encoder/vp9_aq_variance.h"
#include
"vp9/common/vp9_seg_common.h"
#include
"vp9/encoder/vp9_ratectrl.h"
#include
"vp9/encoder/vp9_rd.h"
#include
"vp9/encoder/vp9_segmentation.h"
#define ENERGY_MIN (-4)
#define ENERGY_MAX (1)
#define ENERGY_SPAN (ENERGY_MAX - ENERGY_MIN + 1)
#define ENERGY_IN_BOUNDS(energy)\
assert((energy) >= ENERGY_MIN && (energy) <= ENERGY_MAX)
static
const
double
rate_ratio
[
MAX_SEGMENTS
]
=
{
1
.
0
,
0
.
75
,
0
.
6
,
0
.
5
,
0
.
4
,
0
.
3
,
0
.
25
};
// Sets segment id 0 for the equatorial region, 1 for temperate region