Skip H246 scaling lists in SPS packets
This code is originally written by marc@frankensteinmotorworks.com Bug: webrtc:8275 Change-Id: I35e6d21b12e71199e0209ff91740d95c9df3bd10 Reviewed-on: https://webrtc-review.googlesource.com/36520 Commit-Queue: Erik Språng <sprang@webrtc.org> Reviewed-by: Magnus Jedvert <magjed@webrtc.org> Reviewed-by: Erik Språng <sprang@webrtc.org> Cr-Commit-Position: refs/heads/master@{#21528}
This commit is contained in:
1
AUTHORS
1
AUTHORS
@ -58,6 +58,7 @@ Xiaolei Yu <dreifachstein@gmail.com>
|
||||
Yura Yaroshevich <yura.yaroshevich@gmail.com>
|
||||
Hans Knoechel <hans@hans-knoechel.de>
|
||||
Korniltsev Anatoly <korniltsev.anatoly@gmail.com>
|
||||
Todd Wong <todd.wong.ndq@gmail.com>
|
||||
|
||||
&yet LLC <*@andyet.com>
|
||||
Agora IO <*@agora.io>
|
||||
|
@ -94,23 +94,31 @@ rtc::Optional<SpsParser::SpsState> SpsParser::ParseSpsUpToVui(
|
||||
uint32_t seq_scaling_matrix_present_flag;
|
||||
RETURN_EMPTY_ON_FAIL(buffer->ReadBits(&seq_scaling_matrix_present_flag, 1));
|
||||
if (seq_scaling_matrix_present_flag) {
|
||||
// seq_scaling_list_present_flags. Either 8 or 12, depending on
|
||||
// chroma_format_idc.
|
||||
// Process the scaling lists just enough to be able to properly
|
||||
// skip over them, so we can still read the resolution on streams
|
||||
// where this is included.
|
||||
int scaling_list_count = (chroma_format_idc == 3 ? 12 : 8);
|
||||
for (int i = 0; i < scaling_list_count; ++i) {
|
||||
// seq_scaling_list_present_flag[i] : u(1)
|
||||
uint32_t seq_scaling_list_present_flags;
|
||||
if (chroma_format_idc != 3) {
|
||||
RETURN_EMPTY_ON_FAIL(
|
||||
buffer->ReadBits(&seq_scaling_list_present_flags, 8));
|
||||
} else {
|
||||
buffer->ReadBits(&seq_scaling_list_present_flags, 1));
|
||||
if (seq_scaling_list_present_flags != 0) {
|
||||
int last_scale = 8;
|
||||
int next_scale = 8;
|
||||
int size_of_scaling_list = i < 6 ? 16 : 64;
|
||||
for (int j = 0; j < size_of_scaling_list; j++) {
|
||||
if (next_scale != 0) {
|
||||
int32_t delta_scale;
|
||||
// delta_scale: se(v)
|
||||
RETURN_EMPTY_ON_FAIL(
|
||||
buffer->ReadBits(&seq_scaling_list_present_flags, 12));
|
||||
buffer->ReadSignedExponentialGolomb(&delta_scale));
|
||||
next_scale = (last_scale + delta_scale + 256) % 256;
|
||||
}
|
||||
if (next_scale != 0)
|
||||
last_scale = next_scale;
|
||||
}
|
||||
}
|
||||
// We don't support reading the sequence scaling list, and we don't really
|
||||
// see/use them in practice, so we'll just reject the full sps if we see
|
||||
// any provided.
|
||||
if (seq_scaling_list_present_flags > 0) {
|
||||
RTC_LOG(LS_WARNING)
|
||||
<< "SPS contains scaling lists, which are unsupported.";
|
||||
return OptionalSps();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -171,4 +171,17 @@ TEST_F(H264SpsParserTest, TestSyntheticSPSWeirdResolution) {
|
||||
EXPECT_EQ(2u, sps_->id);
|
||||
}
|
||||
|
||||
TEST_F(H264SpsParserTest, TestSampleSPSWithScalingLists) {
|
||||
// SPS from a 1920x1080 video. Contains scaling lists (and veritcal cropping).
|
||||
const uint8_t buffer[] = {0x64, 0x00, 0x2a, 0xad, 0x84, 0x01, 0x0c, 0x20,
|
||||
0x08, 0x61, 0x00, 0x43, 0x08, 0x02, 0x18, 0x40,
|
||||
0x10, 0xc2, 0x00, 0x84, 0x3b, 0x50, 0x3c, 0x01,
|
||||
0x13, 0xf2, 0xcd, 0xc0, 0x40, 0x40, 0x50, 0x00,
|
||||
0x00, 0x00, 0x10, 0x00, 0x00, 0x01, 0xe8, 0x40};
|
||||
EXPECT_TRUE(
|
||||
static_cast<bool>(sps_ = SpsParser::ParseSps(buffer, arraysize(buffer))));
|
||||
EXPECT_EQ(1920u, sps_->width);
|
||||
EXPECT_EQ(1080u, sps_->height);
|
||||
}
|
||||
|
||||
} // namespace webrtc
|
||||
|
Reference in New Issue
Block a user