Skip to content
GitLab
Menu
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
6b2e4061
Commit
6b2e4061
authored
Mar 27, 2014
by
Minghai Shang
Browse files
[svc] Verify and store input two pass stats data in 2nd pass rc
Change-Id: Ib09eedc17ea0ea2eec75d78112e4786d98f382aa
parent
143b0955
Changes
6
Hide whitespace changes
Inline
Side-by-side
test/svc_test.cc
View file @
6b2e4061
...
...
@@ -31,6 +31,7 @@ class SvcTest : public ::testing::Test {
SvcTest
()
:
codec_iface_
(
0
),
test_file_name_
(
"hantro_collage_w352h288.yuv"
),
stats_file_name_
(
"hantro_collage_w352h288.stat"
),
codec_initialized_
(
false
),
decoder_
(
0
)
{
memset
(
&
svc_
,
0
,
sizeof
(
svc_
));
...
...
@@ -73,6 +74,7 @@ class SvcTest : public ::testing::Test {
struct
vpx_codec_enc_cfg
codec_enc_
;
vpx_codec_iface_t
*
codec_iface_
;
std
::
string
test_file_name_
;
std
::
string
stats_file_name_
;
bool
codec_initialized_
;
Decoder
*
decoder_
;
};
...
...
@@ -397,4 +399,31 @@ TEST_F(SvcTest, FirstPassEncode) {
EXPECT_GT
(
vpx_svc_get_rc_stats_buffer_size
(
&
svc_
),
0U
);
}
TEST_F
(
SvcTest
,
SecondPassEncode
)
{
svc_
.
spatial_layers
=
2
;
codec_enc_
.
g_pass
=
VPX_RC_LAST_PASS
;
FILE
*
const
stats_file
=
libvpx_test
::
OpenTestDataFile
(
stats_file_name_
);
ASSERT_TRUE
(
stats_file
!=
NULL
)
<<
"Stats file open failed. Filename: "
<<
stats_file
;
struct
vpx_fixed_buf
stats_buf
;
fseek
(
stats_file
,
0
,
SEEK_END
);
stats_buf
.
sz
=
static_cast
<
size_t
>
(
ftell
(
stats_file
));
fseek
(
stats_file
,
0
,
SEEK_SET
);
stats_buf
.
buf
=
malloc
(
stats_buf
.
sz
);
ASSERT_TRUE
(
stats_buf
.
buf
!=
NULL
);
const
size_t
bytes_read
=
fread
(
stats_buf
.
buf
,
1
,
stats_buf
.
sz
,
stats_file
);
ASSERT_EQ
(
bytes_read
,
stats_buf
.
sz
);
fclose
(
stats_file
);
codec_enc_
.
rc_twopass_stats_in
=
stats_buf
;
const
vpx_codec_err_t
res
=
vpx_svc_init
(
&
svc_
,
&
codec_
,
vpx_codec_vp9_cx
(),
&
codec_enc_
);
ASSERT_EQ
(
VPX_CODEC_OK
,
res
);
free
(
stats_buf
.
buf
);
}
}
// namespace
test/test-data.sha1
View file @
6b2e4061
d5dfb0151c9051f8c85999255645d7a23916d3c0 hantro_collage_w352h288.yuv
2752863aa6330a93eaeb30f883310f87aa3de87c hantro_collage_w352h288.stat
b87815bf86020c592ccc7a846ba2e28ec8043902 hantro_odd.yuv
b1f1c3ec79114b9a0651af24ce634afb44a9a419 rush_hour_444.y4m
5184c46ddca8b1fadd16742e8500115bc8f749da vp80-00-comprehensive-001.ivf
...
...
test/test.mk
View file @
6b2e4061
...
...
@@ -122,6 +122,7 @@ endif # CONFIG_SHARED
## TEST DATA
##
LIBVPX_TEST_DATA-$(CONFIG_ENCODERS)
+=
hantro_collage_w352h288.yuv
LIBVPX_TEST_DATA-$(CONFIG_ENCODERS)
+=
hantro_collage_w352h288.stat
LIBVPX_TEST_DATA-$(CONFIG_ENCODERS)
+=
hantro_odd.yuv
LIBVPX_TEST_DATA-$(CONFIG_VP9_ENCODER)
+=
rush_hour_444.y4m
...
...
vp9/encoder/vp9_onyx_if.c
View file @
6b2e4061
...
...
@@ -177,6 +177,7 @@ void vp9_initialize_enc() {
static
void
dealloc_compressor_data
(
VP9_COMP
*
cpi
)
{
VP9_COMMON
*
const
cm
=
&
cpi
->
common
;
int
i
;
// Delete sementation map
vpx_free
(
cpi
->
segmentation_map
);
...
...
@@ -210,6 +211,13 @@ static void dealloc_compressor_data(VP9_COMP *cpi) {
cpi
->
mb_activity_map
=
0
;
vpx_free
(
cpi
->
mb_norm_activity_map
);
cpi
->
mb_norm_activity_map
=
0
;
for
(
i
=
0
;
i
<
cpi
->
svc
.
number_spatial_layers
;
++
i
)
{
LAYER_CONTEXT
*
const
lc
=
&
cpi
->
svc
.
layer_context
[
i
];
vpx_free
(
lc
->
rc_twopass_stats_in
.
buf
);
lc
->
rc_twopass_stats_in
.
buf
=
NULL
;
lc
->
rc_twopass_stats_in
.
sz
=
0
;
}
}
// Computes a q delta (in "q index" terms) to get from a starting q value
...
...
@@ -1750,9 +1758,47 @@ VP9_COMP *vp9_create_compressor(VP9_CONFIG *oxcf) {
const
size_t
packet_sz
=
sizeof
(
FIRSTPASS_STATS
);
const
int
packets
=
(
int
)(
oxcf
->
two_pass_stats_in
.
sz
/
packet_sz
);
cpi
->
twopass
.
stats_in_start
=
oxcf
->
two_pass_stats_in
.
buf
;
cpi
->
twopass
.
stats_in
=
cpi
->
twopass
.
stats_in_start
;
cpi
->
twopass
.
stats_in_end
=
&
cpi
->
twopass
.
stats_in
[
packets
-
1
];
if
(
cpi
->
svc
.
number_spatial_layers
>
1
&&
cpi
->
svc
.
number_temporal_layers
==
1
)
{
FIRSTPASS_STATS
*
const
stats
=
oxcf
->
two_pass_stats_in
.
buf
;
FIRSTPASS_STATS
*
stats_copy
[
VPX_SS_MAX_LAYERS
]
=
{
0
};
int
i
;
for
(
i
=
0
;
i
<
oxcf
->
ss_number_layers
;
++
i
)
{
FIRSTPASS_STATS
*
const
last_packet_for_layer
=
&
stats
[
packets
-
oxcf
->
ss_number_layers
+
i
];
const
int
layer_id
=
last_packet_for_layer
->
spatial_layer_id
;
const
int
packets_in_layer
=
(
int
)
last_packet_for_layer
->
count
+
1
;
if
(
layer_id
>=
0
&&
layer_id
<
oxcf
->
ss_number_layers
)
{
LAYER_CONTEXT
*
const
lc
=
&
cpi
->
svc
.
layer_context
[
layer_id
];
vpx_free
(
lc
->
rc_twopass_stats_in
.
buf
);
lc
->
rc_twopass_stats_in
.
sz
=
packets_in_layer
*
packet_sz
;
CHECK_MEM_ERROR
(
cm
,
lc
->
rc_twopass_stats_in
.
buf
,
vpx_malloc
(
lc
->
rc_twopass_stats_in
.
sz
));
lc
->
twopass
.
stats_in_start
=
lc
->
rc_twopass_stats_in
.
buf
;
lc
->
twopass
.
stats_in
=
lc
->
twopass
.
stats_in_start
;
lc
->
twopass
.
stats_in_end
=
lc
->
twopass
.
stats_in_start
+
packets_in_layer
-
1
;
stats_copy
[
layer_id
]
=
lc
->
rc_twopass_stats_in
.
buf
;
}
}
for
(
i
=
0
;
i
<
packets
;
++
i
)
{
const
int
layer_id
=
stats
[
i
].
spatial_layer_id
;
if
(
layer_id
>=
0
&&
layer_id
<
oxcf
->
ss_number_layers
&&
stats_copy
[
layer_id
]
!=
NULL
)
{
*
stats_copy
[
layer_id
]
=
stats
[
i
];
++
stats_copy
[
layer_id
];
}
}
}
else
{
cpi
->
twopass
.
stats_in_start
=
oxcf
->
two_pass_stats_in
.
buf
;
cpi
->
twopass
.
stats_in
=
cpi
->
twopass
.
stats_in_start
;
cpi
->
twopass
.
stats_in_end
=
&
cpi
->
twopass
.
stats_in
[
packets
-
1
];
}
vp9_init_second_pass
(
cpi
);
}
...
...
vp9/encoder/vp9_svc_layercontext.h
View file @
6b2e4061
...
...
@@ -28,6 +28,7 @@ typedef struct {
double
framerate
;
int
avg_frame_size
;
struct
twopass_rc
twopass
;
struct
vpx_fixed_buf
rc_twopass_stats_in
;
}
LAYER_CONTEXT
;
typedef
struct
{
...
...
vp9/vp9_cx_iface.c
View file @
6b2e4061
...
...
@@ -221,14 +221,43 @@ static vpx_codec_err_t validate_config(vpx_codec_alg_priv_t *ctx,
if
(
cfg
->
rc_twopass_stats_in
.
sz
%
packet_sz
)
ERROR
(
"rc_twopass_stats_in.sz indicates truncated packet."
);
if
(
cfg
->
rc_twopass_stats_in
.
sz
<
2
*
packet_sz
)
ERROR
(
"rc_twopass_stats_in requires at least two packets."
);
if
(
cfg
->
ss_number_layers
>
1
)
{
int
i
;
unsigned
int
n_packets_per_layer
[
VPX_SS_MAX_LAYERS
]
=
{
0
};
stats
=
cfg
->
rc_twopass_stats_in
.
buf
;
for
(
i
=
0
;
i
<
n_packets
;
++
i
)
{
const
int
layer_id
=
stats
[
i
].
spatial_layer_id
;
if
(
layer_id
>=
0
&&
layer_id
<
(
int
)
cfg
->
ss_number_layers
)
{
++
n_packets_per_layer
[
layer_id
];
}
}
for
(
i
=
0
;
i
<
(
int
)
cfg
->
ss_number_layers
;
++
i
)
{
unsigned
int
layer_id
;
if
(
n_packets_per_layer
[
i
]
<
2
)
{
ERROR
(
"rc_twopass_stats_in requires at least two packets for each "
"layer."
);
}
stats
=
(
const
FIRSTPASS_STATS
*
)
cfg
->
rc_twopass_stats_in
.
buf
+
n_packets
-
1
;
stats
=
(
const
FIRSTPASS_STATS
*
)
cfg
->
rc_twopass_stats_in
.
buf
+
n_packets
-
cfg
->
ss_number_layers
+
i
;
layer_id
=
stats
->
spatial_layer_id
;
if
((
int
)(
stats
->
count
+
0
.
5
)
!=
n_packets
-
1
)
ERROR
(
"rc_twopass_stats_in missing EOS stats packet"
);
if
(
layer_id
>=
cfg
->
ss_number_layers
||
(
int
)(
stats
->
count
+
0
.
5
)
!=
n_packets_per_layer
[
layer_id
]
-
1
)
ERROR
(
"rc_twopass_stats_in missing EOS stats packet"
);
}
}
else
{
if
(
cfg
->
rc_twopass_stats_in
.
sz
<
2
*
packet_sz
)
ERROR
(
"rc_twopass_stats_in requires at least two packets."
);
stats
=
(
const
FIRSTPASS_STATS
*
)
cfg
->
rc_twopass_stats_in
.
buf
+
n_packets
-
1
;
if
((
int
)(
stats
->
count
+
0
.
5
)
!=
n_packets
-
1
)
ERROR
(
"rc_twopass_stats_in missing EOS stats packet"
);
}
}
return
VPX_CODEC_OK
;
...
...
@@ -990,9 +1019,12 @@ static vpx_codec_err_t vp9e_set_svc(vpx_codec_alg_priv_t *ctx, int ctr_id,
va_list
args
)
{
int
data
=
va_arg
(
args
,
int
);
vp9_set_svc
(
ctx
->
cpi
,
data
);
// CBR mode for SVC with both temporal and spatial layers not yet supported.
// CBR or two pass mode for SVC with both temporal and spatial layers
// not yet supported.
if
(
data
==
1
&&
ctx
->
cfg
.
rc_end_usage
==
VPX_CBR
&&
(
ctx
->
cfg
.
rc_end_usage
==
VPX_CBR
||
ctx
->
cfg
.
g_pass
==
VPX_RC_FIRST_PASS
||
ctx
->
cfg
.
g_pass
==
VPX_RC_LAST_PASS
)
&&
ctx
->
cfg
.
ss_number_layers
>
1
&&
ctx
->
cfg
.
ts_number_layers
>
1
)
{
return
VPX_CODEC_INVALID_PARAM
;
...
...
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment