blob: e5c08fe60e8d0fbd3a8eec133813bf8d7b63d55e [file] [log] [blame]
// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "base/memory/scoped_ptr.h"
#include "base/rand_util.h"
#include "media/cast/net/rtp/rtp_packet_builder.h"
#include "media/cast/net/rtp/rtp_parser.h"
#include "media/cast/net/rtp/rtp_receiver_defines.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace media {
namespace cast {
static const size_t kPacketLength = 1500;
static const int kTestPayloadType = 127;
static const uint32 kTestSsrc = 1234;
static const uint32 kTestTimestamp = 111111;
static const uint16 kTestSeqNum = 4321;
static const uint8 kRefFrameId = 17;
class RtpParserTest : public ::testing::Test {
protected:
RtpParserTest() : rtp_parser_(kTestSsrc, kTestPayloadType) {
packet_builder_.SetSsrc(kTestSsrc);
packet_builder_.SetSequenceNumber(kTestSeqNum);
packet_builder_.SetTimestamp(kTestTimestamp);
packet_builder_.SetPayloadType(kTestPayloadType);
packet_builder_.SetMarkerBit(true); // Only one packet.
cast_header_.sender_ssrc = kTestSsrc;
cast_header_.sequence_number = kTestSeqNum;
cast_header_.rtp_timestamp = kTestTimestamp;
cast_header_.payload_type = kTestPayloadType;
cast_header_.marker = true;
}
virtual ~RtpParserTest() {}
void ExpectParsesPacket() {
RtpCastHeader parsed_header;
const uint8* payload = NULL;
size_t payload_size = static_cast<size_t>(-1);
EXPECT_TRUE(rtp_parser_.ParsePacket(
packet_, kPacketLength, &parsed_header, &payload, &payload_size));
EXPECT_EQ(cast_header_.marker, parsed_header.marker);
EXPECT_EQ(cast_header_.payload_type, parsed_header.payload_type);
EXPECT_EQ(cast_header_.sequence_number, parsed_header.sequence_number);
EXPECT_EQ(cast_header_.rtp_timestamp, parsed_header.rtp_timestamp);
EXPECT_EQ(cast_header_.sender_ssrc, parsed_header.sender_ssrc);
EXPECT_EQ(cast_header_.is_key_frame, parsed_header.is_key_frame);
EXPECT_EQ(cast_header_.frame_id, parsed_header.frame_id);
EXPECT_EQ(cast_header_.packet_id, parsed_header.packet_id);
EXPECT_EQ(cast_header_.max_packet_id, parsed_header.max_packet_id);
EXPECT_EQ(cast_header_.reference_frame_id,
parsed_header.reference_frame_id);
EXPECT_TRUE(!!payload);
EXPECT_NE(static_cast<size_t>(-1), payload_size);
}
void ExpectDoesNotParsePacket() {
RtpCastHeader parsed_header;
const uint8* payload = NULL;
size_t payload_size = static_cast<size_t>(-1);
EXPECT_FALSE(rtp_parser_.ParsePacket(
packet_, kPacketLength, &parsed_header, &payload, &payload_size));
}
RtpPacketBuilder packet_builder_;
uint8 packet_[kPacketLength];
RtpParser rtp_parser_;
RtpCastHeader cast_header_;
};
TEST_F(RtpParserTest, ParseDefaultCastPacket) {
packet_builder_.BuildHeader(packet_, kPacketLength);
ExpectParsesPacket();
}
TEST_F(RtpParserTest, ParseNonDefaultCastPacket) {
packet_builder_.SetKeyFrame(true);
packet_builder_.SetFrameIds(10, 10);
packet_builder_.SetPacketId(5);
packet_builder_.SetMaxPacketId(15);
packet_builder_.SetMarkerBit(false);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.is_key_frame = true;
cast_header_.frame_id = 10;
cast_header_.reference_frame_id = 10;
cast_header_.packet_id = 5;
cast_header_.max_packet_id = 15;
cast_header_.marker = false;
ExpectParsesPacket();
}
TEST_F(RtpParserTest, TooBigPacketId) {
packet_builder_.SetKeyFrame(true);
packet_builder_.SetFrameIds(10, 10);
packet_builder_.SetPacketId(15);
packet_builder_.SetMaxPacketId(5);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.is_key_frame = true;
cast_header_.frame_id = 10;
cast_header_.reference_frame_id = 10;
cast_header_.packet_id = 15;
cast_header_.max_packet_id = 5;
ExpectDoesNotParsePacket();
}
TEST_F(RtpParserTest, MaxPacketId) {
packet_builder_.SetKeyFrame(true);
packet_builder_.SetFrameIds(10, 10);
packet_builder_.SetPacketId(65535);
packet_builder_.SetMaxPacketId(65535);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.is_key_frame = true;
cast_header_.frame_id = 10;
cast_header_.reference_frame_id = 10;
cast_header_.packet_id = 65535;
cast_header_.max_packet_id = 65535;
ExpectParsesPacket();
}
TEST_F(RtpParserTest, InvalidPayloadType) {
packet_builder_.SetKeyFrame(true);
packet_builder_.SetFrameIds(10, 10);
packet_builder_.SetPacketId(65535);
packet_builder_.SetMaxPacketId(65535);
packet_builder_.SetPayloadType(kTestPayloadType - 1);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.is_key_frame = true;
cast_header_.frame_id = 10;
cast_header_.reference_frame_id = 10;
cast_header_.packet_id = 65535;
cast_header_.max_packet_id = 65535;
cast_header_.payload_type = kTestPayloadType - 1;
ExpectDoesNotParsePacket();
}
TEST_F(RtpParserTest, InvalidSsrc) {
packet_builder_.SetKeyFrame(true);
packet_builder_.SetFrameIds(10, 10);
packet_builder_.SetPacketId(65535);
packet_builder_.SetMaxPacketId(65535);
packet_builder_.SetSsrc(kTestSsrc - 1);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.is_key_frame = true;
cast_header_.frame_id = 10;
cast_header_.reference_frame_id = 10;
cast_header_.packet_id = 65535;
cast_header_.max_packet_id = 65535;
cast_header_.sender_ssrc = kTestSsrc - 1;
ExpectDoesNotParsePacket();
}
TEST_F(RtpParserTest, ParseCastPacketWithSpecificFrameReference) {
packet_builder_.SetFrameIds(kRefFrameId + 3, kRefFrameId);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.frame_id = kRefFrameId + 3;
cast_header_.reference_frame_id = kRefFrameId;
ExpectParsesPacket();
}
TEST_F(RtpParserTest, ParseExpandingFrameIdTo32Bits) {
const uint32 kMaxFrameId = 1000;
packet_builder_.SetKeyFrame(true);
cast_header_.is_key_frame = true;
for (uint32 frame_id = 0; frame_id <= kMaxFrameId; ++frame_id) {
packet_builder_.SetFrameIds(frame_id, frame_id);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.frame_id = frame_id;
cast_header_.reference_frame_id = frame_id;
ExpectParsesPacket();
}
}
TEST_F(RtpParserTest, ParseExpandingReferenceFrameIdTo32Bits) {
const uint32 kMaxFrameId = 1000;
const uint32 kMaxBackReferenceOffset = 10;
packet_builder_.SetKeyFrame(false);
cast_header_.is_key_frame = false;
for (uint32 frame_id = kMaxBackReferenceOffset;
frame_id <= kMaxFrameId; ++frame_id) {
const uint32 reference_frame_id =
frame_id - base::RandInt(1, kMaxBackReferenceOffset);
packet_builder_.SetFrameIds(frame_id, reference_frame_id);
packet_builder_.BuildHeader(packet_, kPacketLength);
cast_header_.frame_id = frame_id;
cast_header_.reference_frame_id = reference_frame_id;
ExpectParsesPacket();
}
}
} // namespace cast
} // namespace media