commit e0be5922916d41af37cd159bd52e3671157b6d8f parent 4ccf1cc00662b337dd193e7d96f310f8734505e8 Author: Michael Froman <mfroman@mozilla.com> Date: Thu, 9 Oct 2025 14:59:15 -0500 Bug 1993083 - Vendor libwebrtc from 9ad731ce25 Upstream commit: https://webrtc.googlesource.com/src/+/9ad731ce254f9ebb4eaa8102f153d5def054870f Replace webrtc::test::Packet with RtpPacketReceived To reduce number of classes that represent an RTP packet. Functionality of simulating payload data that is absent in an RTP dump is moved into RtpFileSource that reads from such file. Functionality to parse RED header is moved to the only user - rtp_analyze Bug: webrtc:42225366 Change-Id: I8b66cfa0df67a776d9285dcb05da9c0183d6a400 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/400760 Commit-Queue: Danil Chapovalov <danilchap@webrtc.org> Reviewed-by: Jakob Ivarsson‎ <jakobi@webrtc.org> Cr-Commit-Position: refs/heads/main@{#45169} Diffstat:
20 files changed, 191 insertions(+), 669 deletions(-)
diff --git a/third_party/libwebrtc/README.mozilla.last-vendor b/third_party/libwebrtc/README.mozilla.last-vendor @@ -1,4 +1,4 @@ # ./mach python dom/media/webrtc/third_party_build/vendor-libwebrtc.py --from-local /home/mfroman/mozilla/elm/.moz-fast-forward/moz-libwebrtc --commit mozpatches libwebrtc -libwebrtc updated from /home/mfroman/mozilla/elm/.moz-fast-forward/moz-libwebrtc commit mozpatches on 2025-10-09T19:57:58.782879+00:00. +libwebrtc updated from /home/mfroman/mozilla/elm/.moz-fast-forward/moz-libwebrtc commit mozpatches on 2025-10-09T19:59:02.041995+00:00. # base of lastest vendoring -ac59d0f6a0 +9ad731ce25 diff --git a/third_party/libwebrtc/modules/audio_coding/BUILD.gn b/third_party/libwebrtc/modules/audio_coding/BUILD.gn @@ -571,8 +571,6 @@ rtc_library("neteq_tools_minimal") { "neteq/tools/neteq_input.h", "neteq/tools/neteq_test.cc", "neteq/tools/neteq_test.h", - "neteq/tools/packet.cc", - "neteq/tools/packet.h", "neteq/tools/packet_source.cc", "neteq/tools/packet_source.h", ] @@ -632,6 +630,7 @@ rtc_library("neteq_test_tools") { ":pcm16b", "../../api:array_view", "../../api:rtp_headers", + "../../api/units:timestamp", "../../common_audio", "../../rtc_base:buffer", "../../rtc_base:checks", @@ -766,6 +765,7 @@ rtc_library("audio_coding_modules_tests_shared") { "../../system_wrappers", "../../test:fileutils", "../../test:test_support", + "../rtp_rtcp:rtp_rtcp_format", "//testing/gtest", "//third_party/abseil-cpp/absl/strings", "//third_party/abseil-cpp/absl/strings:string_view", @@ -953,6 +953,7 @@ if (rtc_include_tests) { "../../api/neteq:default_neteq_factory", "../../api/neteq:neteq_api", "../../test:test_support", + "../rtp_rtcp:rtp_rtcp_format", "//testing/gtest", ] @@ -984,6 +985,7 @@ if (rtc_include_tests) { "../../rtc_base:copy_on_write_buffer", "../../rtc_base:stringutils", "../../test:test_support", + "../rtp_rtcp:rtp_rtcp_format", "//testing/gtest", "//third_party/abseil-cpp/absl/strings", "//third_party/abseil-cpp/absl/strings:string_view", @@ -1468,7 +1470,6 @@ if (rtc_include_tests) { "neteq/time_stretch_unittest.cc", "neteq/timestamp_scaler_unittest.cc", "neteq/tools/input_audio_file_unittest.cc", - "neteq/tools/packet_unittest.cc", "neteq/underrun_optimizer_unittest.cc", ] diff --git a/third_party/libwebrtc/modules/audio_coding/acm2/acm_receive_test.cc b/third_party/libwebrtc/modules/audio_coding/acm2/acm_receive_test.cc @@ -10,13 +10,11 @@ #include "modules/audio_coding/acm2/acm_receive_test.h" -#include <cstdint> #include <cstdio> #include <memory> #include <ostream> #include <utility> -#include "api/array_view.h" #include "api/audio_codecs/audio_decoder_factory.h" #include "api/audio_codecs/builtin_audio_decoder_factory.h" #include "api/environment/environment_factory.h" @@ -25,8 +23,8 @@ #include "api/scoped_refptr.h" #include "modules/audio_coding/include/audio_coding_module.h" #include "modules/audio_coding/neteq/tools/audio_sink.h" -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/packet_source.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "test/gtest.h" namespace webrtc { @@ -89,10 +87,10 @@ void AcmReceiveTestOldApi::RegisterNetEqTestCodecs() { } void AcmReceiveTestOldApi::Run() { - for (std::unique_ptr<Packet> packet(packet_source_->NextPacket()); packet; - packet = packet_source_->NextPacket()) { + for (std::unique_ptr<RtpPacketReceived> packet = packet_source_->NextPacket(); + packet != nullptr; packet = packet_source_->NextPacket()) { // Pull audio until time to insert packet. - while (clock_.TimeInMilliseconds() < packet->time_ms()) { + while (clock_.CurrentTime() < packet->arrival_time()) { AudioFrame output_frame; bool muted; EXPECT_EQ(NetEq::kOK, neteq_->GetAudio(&output_frame, &muted)); @@ -117,16 +115,14 @@ void AcmReceiveTestOldApi::Run() { AfterGetAudio(); } - EXPECT_EQ(0, neteq_->InsertPacket( - packet->header(), - ArrayView<const uint8_t>(packet->payload(), - packet->payload_length_bytes()), - clock_.CurrentTime())) + RTPHeader rtp_header; + packet->GetHeader(&rtp_header); + EXPECT_EQ(0, neteq_->InsertPacket(rtp_header, packet->payload(), + clock_.CurrentTime())) << "Failure when inserting packet:" << std::endl - << " PT = " << static_cast<int>(packet->header().payloadType) - << std::endl - << " TS = " << packet->header().timestamp << std::endl - << " SN = " << packet->header().sequenceNumber; + << " PT = " << static_cast<int>(packet->PayloadType()) << std::endl + << " TS = " << packet->Timestamp() << std::endl + << " SN = " << packet->SequenceNumber(); } } diff --git a/third_party/libwebrtc/modules/audio_coding/acm2/acm_send_test.cc b/third_party/libwebrtc/modules/audio_coding/acm2/acm_send_test.cc @@ -26,9 +26,8 @@ #include "modules/audio_coding/include/audio_coding_module.h" #include "modules/audio_coding/include/audio_coding_module_typedefs.h" #include "modules/audio_coding/neteq/tools/input_audio_file.h" -#include "modules/audio_coding/neteq/tools/packet.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "rtc_base/checks.h" -#include "rtc_base/copy_on_write_buffer.h" namespace webrtc { namespace test { @@ -96,7 +95,7 @@ void AcmSendTestOldApi::RegisterExternalCodec( codec_registered_ = true; } -std::unique_ptr<Packet> AcmSendTestOldApi::NextPacket() { +std::unique_ptr<RtpPacketReceived> AcmSendTestOldApi::NextPacket() { RTC_DCHECK(codec_registered_); if (filter_.test(static_cast<size_t>(payload_type_))) { // This payload type should be filtered out. Since the payload type is the @@ -140,35 +139,21 @@ int32_t AcmSendTestOldApi::SendData( return 0; } -std::unique_ptr<Packet> AcmSendTestOldApi::CreatePacket() { - const size_t kRtpHeaderSize = 12; - CopyOnWriteBuffer packet_buffer(last_payload_vec_.size() + kRtpHeaderSize); - uint8_t* packet_memory = packet_buffer.MutableData(); - // Populate the header bytes. - packet_memory[0] = 0x80; - packet_memory[1] = static_cast<uint8_t>(payload_type_); - packet_memory[2] = (sequence_number_ >> 8) & 0xFF; - packet_memory[3] = (sequence_number_) & 0xFF; - packet_memory[4] = (timestamp_ >> 24) & 0xFF; - packet_memory[5] = (timestamp_ >> 16) & 0xFF; - packet_memory[6] = (timestamp_ >> 8) & 0xFF; - packet_memory[7] = timestamp_ & 0xFF; - // Set SSRC to 0x12345678. - packet_memory[8] = 0x12; - packet_memory[9] = 0x34; - packet_memory[10] = 0x56; - packet_memory[11] = 0x78; +std::unique_ptr<RtpPacketReceived> AcmSendTestOldApi::CreatePacket() { + auto rtp_packet = std::make_unique<RtpPacketReceived>(); + // Populate the header. + rtp_packet->SetPayloadType(payload_type_); + rtp_packet->SetSequenceNumber(sequence_number_); + rtp_packet->SetTimestamp(timestamp_); + rtp_packet->SetSsrc(0x12345678); ++sequence_number_; // Copy the payload data. - memcpy(packet_memory + kRtpHeaderSize, &last_payload_vec_[0], - last_payload_vec_.size()); - auto packet = std::make_unique<Packet>(std::move(packet_buffer), - clock_.TimeInMilliseconds()); - RTC_DCHECK(packet); - RTC_DCHECK(packet->valid_header()); - return packet; + memcpy(rtp_packet->AllocatePayload(last_payload_vec_.size()), + last_payload_vec_.data(), last_payload_vec_.size()); + rtp_packet->set_arrival_time(clock_.CurrentTime()); + return rtp_packet; } } // namespace test diff --git a/third_party/libwebrtc/modules/audio_coding/acm2/acm_send_test.h b/third_party/libwebrtc/modules/audio_coding/acm2/acm_send_test.h @@ -22,6 +22,7 @@ #include "modules/audio_coding/include/audio_coding_module.h" #include "modules/audio_coding/include/audio_coding_module_typedefs.h" #include "modules/audio_coding/neteq/tools/packet_source.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "system_wrappers/include/clock.h" namespace webrtc { @@ -29,7 +30,6 @@ class AudioEncoder; namespace test { class InputAudioFile; -class Packet; class AcmSendTestOldApi : public AudioPacketizationCallback, public PacketSource { @@ -54,7 +54,7 @@ class AcmSendTestOldApi : public AudioPacketizationCallback, std::unique_ptr<AudioEncoder> external_speech_encoder); // Inherited from PacketSource. - std::unique_ptr<Packet> NextPacket() override; + std::unique_ptr<RtpPacketReceived> NextPacket() override; // Inherited from AudioPacketizationCallback. int32_t SendData(AudioFrameType frame_type, @@ -71,7 +71,7 @@ class AcmSendTestOldApi : public AudioPacketizationCallback, // Creates a Packet object from the last packet produced by ACM (and received // through the SendData method as a callback). - std::unique_ptr<Packet> CreatePacket(); + std::unique_ptr<RtpPacketReceived> CreatePacket(); SimulatedClock clock_; const Environment env_; diff --git a/third_party/libwebrtc/modules/audio_coding/acm2/audio_coding_module_unittest.cc b/third_party/libwebrtc/modules/audio_coding/acm2/audio_coding_module_unittest.cc @@ -55,7 +55,7 @@ #include "modules/audio_coding/neteq/tools/input_audio_file.h" #include "modules/audio_coding/neteq/tools/output_audio_file.h" #include "modules/audio_coding/neteq/tools/output_wav_file.h" -#include "modules/audio_coding/neteq/tools/packet.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "rtc_base/buffer.h" #include "rtc_base/event.h" #include "rtc_base/message_digest.h" @@ -756,7 +756,7 @@ class AcmSenderBitExactnessOldApi : public ::testing::Test, } // Inherited from test::PacketSource. - std::unique_ptr<test::Packet> NextPacket() override { + std::unique_ptr<RtpPacketReceived> NextPacket() override { auto packet = send_test_->NextPacket(); if (!packet) return nullptr; @@ -769,24 +769,23 @@ class AcmSenderBitExactnessOldApi : public ::testing::Test, } // Verifies the packet. - void VerifyPacket(const test::Packet* packet) { - EXPECT_TRUE(packet->valid_header()); + void VerifyPacket(const RtpPacketReceived* packet) { // (We can check the header fields even if valid_header() is false.) - EXPECT_EQ(payload_type_, packet->header().payloadType); + EXPECT_EQ(payload_type_, packet->PayloadType()); if (packet_count_ > 0) { // This is not the first packet. uint16_t sequence_number_diff = - packet->header().sequenceNumber - last_sequence_number_; + packet->SequenceNumber() - last_sequence_number_; EXPECT_EQ(1, sequence_number_diff); - uint32_t timestamp_diff = packet->header().timestamp - last_timestamp_; + uint32_t timestamp_diff = packet->Timestamp() - last_timestamp_; EXPECT_EQ(frame_size_rtp_timestamps_, timestamp_diff); } ++packet_count_; - last_sequence_number_ = packet->header().sequenceNumber; - last_timestamp_ = packet->header().timestamp; + last_sequence_number_ = packet->SequenceNumber(); + last_timestamp_ = packet->Timestamp(); // Update the checksum. - payload_checksum_->Update(packet->payload(), - packet->payload_length_bytes()); + payload_checksum_->Update(packet->payload().data(), + packet->payload().size()); } void SetUpTest(absl::string_view codec_name, @@ -1077,9 +1076,9 @@ class AcmSetBitRateTest : public ::testing::Test { void RunInner(int min_expected_total_bits, int max_expected_total_bits) { int nr_bytes = 0; - while (std::unique_ptr<test::Packet> next_packet = + while (std::unique_ptr<RtpPacketReceived> next_packet = send_test_->NextPacket()) { - nr_bytes += checked_cast<int>(next_packet->payload_length_bytes()); + nr_bytes += checked_cast<int>(next_packet->payload_size()); } EXPECT_LE(min_expected_total_bits, nr_bytes * 8); EXPECT_GE(max_expected_total_bits, nr_bytes * 8); @@ -1333,7 +1332,7 @@ class AcmSwitchingOutputFrequencyOldApi : public ::testing::Test, } // Inherited from test::PacketSource. - std::unique_ptr<test::Packet> NextPacket() override { + std::unique_ptr<RtpPacketReceived> NextPacket() override { // Check if it is time to terminate the test. The packet source is of type // ConstantPcmPacketSource, which is infinite, so we must end the test // "manually". diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/test/neteq_decoding_test.cc b/third_party/libwebrtc/modules/audio_coding/neteq/test/neteq_decoding_test.cc @@ -51,14 +51,6 @@ void LoadDecoders(NetEq* neteq) { neteq->RegisterPayloadType(0, SdpAudioFormat("pcmu", 8000, 1))); ASSERT_EQ(true, neteq->RegisterPayloadType(8, SdpAudioFormat("pcma", 8000, 1))); -#if defined(WEBRTC_CODEC_ISAC) || defined(WEBRTC_CODEC_ISACFX) - ASSERT_EQ(true, - neteq->RegisterPayloadType(103, SdpAudioFormat("isac", 16000, 1))); -#endif -#ifdef WEBRTC_CODEC_ISAC - ASSERT_EQ(true, - neteq->RegisterPayloadType(104, SdpAudioFormat("isac", 32000, 1))); -#endif #ifdef WEBRTC_CODEC_OPUS ASSERT_EQ(true, neteq->RegisterPayloadType( @@ -111,17 +103,12 @@ void NetEqDecodingTest::OpenInputFile(absl::string_view rtp_file) { void NetEqDecodingTest::Process() { // Check if time to receive. - while (packet_ && clock_.TimeInMilliseconds() >= packet_->time_ms()) { - if (packet_->payload_length_bytes() > 0) { -#ifndef WEBRTC_CODEC_ISAC - // Ignore payload type 104 (iSAC-swb) if ISAC is not supported. - if (packet_->header().payloadType != 104) -#endif - ASSERT_EQ(0, neteq_->InsertPacket(packet_->header(), - ArrayView<const uint8_t>( - packet_->payload(), - packet_->payload_length_bytes()), - clock_.CurrentTime())); + while (packet_ && clock_.CurrentTime() >= packet_->arrival_time()) { + if (packet_->payload_size() > 0) { + RTPHeader rtp_header; + packet_->GetHeader(&rtp_header); + ASSERT_EQ(0, neteq_->InsertPacket(rtp_header, packet_->payload(), + clock_.CurrentTime())); } // Get next packet. packet_ = rtp_source_->NextPacket(); diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/test/neteq_decoding_test.h b/third_party/libwebrtc/modules/audio_coding/neteq/test/neteq_decoding_test.h @@ -21,8 +21,8 @@ #include "api/environment/environment.h" #include "api/neteq/neteq.h" #include "api/rtp_headers.h" -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/rtp_file_source.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "system_wrappers/include/clock.h" #include "test/gtest.h" @@ -76,7 +76,7 @@ class NetEqDecodingTest : public ::testing::Test { std::unique_ptr<NetEq> neteq_; NetEq::Config config_; std::unique_ptr<test::RtpFileSource> rtp_source_; - std::unique_ptr<test::Packet> packet_; + std::unique_ptr<RtpPacketReceived> packet_; AudioFrame out_frame_; int output_sample_rate_; int algorithmic_delay_ms_; diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/constant_pcm_packet_source.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/constant_pcm_packet_source.cc @@ -13,12 +13,11 @@ #include <cstddef> #include <cstdint> #include <memory> -#include <utility> +#include "api/units/timestamp.h" #include "modules/audio_coding/codecs/pcm16b/pcm16b.h" -#include "modules/audio_coding/neteq/tools/packet.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "rtc_base/checks.h" -#include "rtc_base/copy_on_write_buffer.h" namespace webrtc { namespace test { @@ -39,36 +38,27 @@ ConstantPcmPacketSource::ConstantPcmPacketSource(size_t payload_len_samples, RTC_CHECK_EQ(2U, encoded_len); } -std::unique_ptr<Packet> ConstantPcmPacketSource::NextPacket() { +std::unique_ptr<RtpPacketReceived> ConstantPcmPacketSource::NextPacket() { RTC_CHECK_GT(packet_len_bytes_, kHeaderLenBytes); - CopyOnWriteBuffer packet_buffer(packet_len_bytes_); - uint8_t* packet_memory = packet_buffer.MutableData(); + auto rtp_packet = std::make_unique<RtpPacketReceived>(); + rtp_packet->SetPayloadType(payload_type_); + rtp_packet->SetSequenceNumber(seq_number_); + rtp_packet->SetTimestamp(timestamp_); + rtp_packet->SetSsrc(payload_ssrc_); + ++seq_number_; + timestamp_ += static_cast<uint32_t>(payload_len_samples_); + + uint8_t* packet_memory = + rtp_packet->AllocatePayload(2 * payload_len_samples_); // Fill the payload part of the packet memory with the pre-encoded value. - for (unsigned i = 0; i < 2 * payload_len_samples_; ++i) - packet_memory[kHeaderLenBytes + i] = encoded_sample_[i % 2]; - WriteHeader(packet_memory); - // `packet` assumes ownership of `packet_memory`. - auto packet = - std::make_unique<Packet>(std::move(packet_buffer), next_arrival_time_ms_); + for (size_t i = 0; i < 2 * payload_len_samples_; ++i) { + packet_memory[i] = encoded_sample_[i % 2]; + } + + rtp_packet->set_arrival_time(Timestamp::Millis(next_arrival_time_ms_)); next_arrival_time_ms_ += payload_len_samples_ / samples_per_ms_; - return packet; -} -void ConstantPcmPacketSource::WriteHeader(uint8_t* packet_memory) { - packet_memory[0] = 0x80; - packet_memory[1] = static_cast<uint8_t>(payload_type_); - packet_memory[2] = seq_number_ >> 8; - packet_memory[3] = seq_number_ & 0xFF; - packet_memory[4] = timestamp_ >> 24; - packet_memory[5] = (timestamp_ >> 16) & 0xFF; - packet_memory[6] = (timestamp_ >> 8) & 0xFF; - packet_memory[7] = timestamp_ & 0xFF; - packet_memory[8] = payload_ssrc_ >> 24; - packet_memory[9] = (payload_ssrc_ >> 16) & 0xFF; - packet_memory[10] = (payload_ssrc_ >> 8) & 0xFF; - packet_memory[11] = payload_ssrc_ & 0xFF; - ++seq_number_; - timestamp_ += static_cast<uint32_t>(payload_len_samples_); + return rtp_packet; } } // namespace test diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/constant_pcm_packet_source.h b/third_party/libwebrtc/modules/audio_coding/neteq/tools/constant_pcm_packet_source.h @@ -16,8 +16,8 @@ #include <cstdint> #include <memory> -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/packet_source.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" namespace webrtc { namespace test { @@ -35,11 +35,9 @@ class ConstantPcmPacketSource : public PacketSource { ConstantPcmPacketSource(const ConstantPcmPacketSource&) = delete; ConstantPcmPacketSource& operator=(const ConstantPcmPacketSource&) = delete; - std::unique_ptr<Packet> NextPacket() override; + std::unique_ptr<RtpPacketReceived> NextPacket() override; private: - void WriteHeader(uint8_t* packet_memory); - const size_t kHeaderLenBytes = 12; const size_t payload_len_samples_; const size_t packet_len_bytes_; diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/neteq_rtp_dump_input.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/neteq_rtp_dump_input.cc @@ -10,7 +10,6 @@ #include "modules/audio_coding/neteq/tools/neteq_rtp_dump_input.h" -#include <algorithm> #include <cstdint> #include <map> #include <memory> @@ -19,9 +18,9 @@ #include "absl/strings/string_view.h" #include "api/rtp_headers.h" #include "modules/audio_coding/neteq/tools/neteq_input.h" -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/rtp_file_source.h" #include "modules/rtp_rtcp/include/rtp_rtcp_defines.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" namespace webrtc { namespace test { @@ -60,28 +59,17 @@ class NetEqRtpDumpInput : public NetEqInput { void AdvanceSetMinimumDelay() override {} std::optional<int64_t> NextPacketTime() const override { - return packet_ ? std::optional<int64_t>( - static_cast<int64_t>(packet_->time_ms())) - : std::nullopt; + return packet_ ? std::optional(packet_->arrival_time().ms()) : std::nullopt; } std::unique_ptr<PacketData> PopPacket() override { if (!packet_) { return std::unique_ptr<PacketData>(); } - std::unique_ptr<PacketData> packet_data(new PacketData); - packet_data->header = packet_->header(); - if (packet_->payload_length_bytes() == 0 && - packet_->virtual_payload_length_bytes() > 0) { - // This is a header-only "dummy" packet. Set the payload to all zeros, - // with length according to the virtual length. - packet_data->payload.SetSize(packet_->virtual_payload_length_bytes()); - std::fill_n(packet_data->payload.data(), packet_data->payload.size(), 0); - } else { - packet_data->payload.SetData(packet_->payload(), - packet_->payload_length_bytes()); - } - packet_data->time_ms = packet_->time_ms(); + auto packet_data = std::make_unique<PacketData>(); + packet_->GetHeader(&packet_data->header); + packet_data->payload.SetData(packet_->payload()); + packet_data->time_ms = packet_->arrival_time().ms(); LoadNextPacket(); @@ -89,7 +77,12 @@ class NetEqRtpDumpInput : public NetEqInput { } std::optional<RTPHeader> NextHeader() const override { - return packet_ ? std::optional<RTPHeader>(packet_->header()) : std::nullopt; + if (packet_ == nullptr) { + return std::nullopt; + } + RTPHeader rtp_header; + packet_->GetHeader(&rtp_header); + return rtp_header; } bool ended() const override { return !next_output_event_ms_; } @@ -101,7 +94,7 @@ class NetEqRtpDumpInput : public NetEqInput { static constexpr int64_t kOutputPeriodMs = 10; std::unique_ptr<RtpFileSource> source_; - std::unique_ptr<Packet> packet_; + std::unique_ptr<RtpPacketReceived> packet_; }; } // namespace diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet.cc @@ -1,140 +0,0 @@ -/* - * Copyright (c) 2014 The WebRTC 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 "modules/audio_coding/neteq/tools/packet.h" - -#include <cstddef> -#include <cstdint> -#include <list> -#include <utility> - -#include "api/array_view.h" -#include "api/rtp_headers.h" -#include "modules/rtp_rtcp/include/rtp_header_extension_map.h" -#include "modules/rtp_rtcp/source/rtp_packet_received.h" -#include "rtc_base/checks.h" -#include "rtc_base/copy_on_write_buffer.h" - -namespace webrtc { -namespace test { - -Packet::Packet(CopyOnWriteBuffer packet, - size_t virtual_packet_length_bytes, - double time_ms, - const RtpHeaderExtensionMap* extension_map) - : packet_(std::move(packet)), - virtual_packet_length_bytes_(virtual_packet_length_bytes), - time_ms_(time_ms), - valid_header_(ParseHeader(extension_map)) {} - -Packet::Packet(const RTPHeader& header, - size_t virtual_packet_length_bytes, - size_t virtual_payload_length_bytes, - double time_ms) - : header_(header), - virtual_packet_length_bytes_(virtual_packet_length_bytes), - virtual_payload_length_bytes_(virtual_payload_length_bytes), - time_ms_(time_ms), - valid_header_(true) {} - -Packet::~Packet() = default; - -bool Packet::ExtractRedHeaders(std::list<RTPHeader*>* headers) const { - // - // 0 1 2 3 - // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 - // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ - // |1| block PT | timestamp offset | block length | - // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ - // |1| ... | - // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ - // |0| block PT | - // +-+-+-+-+-+-+-+-+ - // - - const uint8_t* payload_ptr = payload(); - const uint8_t* payload_end_ptr = payload_ptr + payload_length_bytes(); - - // Find all RED headers with the extension bit set to 1. That is, all headers - // but the last one. - while ((payload_ptr < payload_end_ptr) && (*payload_ptr & 0x80)) { - RTPHeader* header = new RTPHeader; - CopyToHeader(header); - header->payloadType = payload_ptr[0] & 0x7F; - uint32_t offset = (payload_ptr[1] << 6) + ((payload_ptr[2] & 0xFC) >> 2); - header->timestamp -= offset; - headers->push_front(header); - payload_ptr += 4; - } - // Last header. - RTC_DCHECK_LT(payload_ptr, payload_end_ptr); - if (payload_ptr >= payload_end_ptr) { - return false; // Payload too short. - } - RTPHeader* header = new RTPHeader; - CopyToHeader(header); - header->payloadType = payload_ptr[0] & 0x7F; - headers->push_front(header); - return true; -} - -void Packet::DeleteRedHeaders(std::list<RTPHeader*>* headers) { - while (!headers->empty()) { - delete headers->front(); - headers->pop_front(); - } -} - -bool Packet::ParseHeader(const RtpHeaderExtensionMap* extension_map) { - // Use RtpPacketReceived instead of RtpPacket because former already has a - // converter into legacy RTPHeader. - RtpPacketReceived rtp_packet(extension_map); - - // Because of the special case of dummy packets that have padding marked in - // the RTP header, but do not have rtp payload with the padding size, handle - // padding manually. Regular RTP packet parser reports failure, but it is fine - // in this context. - bool padding = (packet_[0] & 0b0010'0000); - size_t padding_size = 0; - if (padding) { - // Clear the padding bit to prevent failure when rtp payload is omited. - CopyOnWriteBuffer packet(packet_); - packet.MutableData()[0] &= ~0b0010'0000; - if (!rtp_packet.Parse(std::move(packet))) { - return false; - } - if (rtp_packet.payload_size() > 0) { - padding_size = rtp_packet.data()[rtp_packet.size() - 1]; - } - if (padding_size > rtp_packet.payload_size()) { - return false; - } - } else { - if (!rtp_packet.Parse(packet_)) { - return false; - } - } - rtp_payload_ = MakeArrayView(packet_.data() + rtp_packet.headers_size(), - rtp_packet.payload_size() - padding_size); - rtp_packet.GetHeader(&header_); - - RTC_CHECK_GE(virtual_packet_length_bytes_, rtp_packet.size()); - RTC_DCHECK_GE(virtual_packet_length_bytes_, rtp_packet.headers_size()); - virtual_payload_length_bytes_ = - virtual_packet_length_bytes_ - rtp_packet.headers_size(); - return true; -} - -void Packet::CopyToHeader(RTPHeader* destination) const { - *destination = header_; -} - -} // namespace test -} // namespace webrtc diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet.h b/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet.h @@ -1,106 +0,0 @@ -/* - * Copyright (c) 2014 The WebRTC 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. - */ - -#ifndef MODULES_AUDIO_CODING_NETEQ_TOOLS_PACKET_H_ -#define MODULES_AUDIO_CODING_NETEQ_TOOLS_PACKET_H_ - -#include <cstddef> -#include <cstdint> -#include <list> - -#include "api/array_view.h" -#include "api/rtp_headers.h" -#include "modules/rtp_rtcp/include/rtp_header_extension_map.h" -#include "rtc_base/copy_on_write_buffer.h" - -namespace webrtc { -namespace test { - -// Class for handling RTP packets in test applications. -class Packet { - public: - // Creates a packet, with the packet payload (including header bytes) in - // `packet`. The `time_ms` is an extra time associated with this packet, - // typically used to denote arrival time. - // `virtual_packet_length_bytes` is typically used when reading RTP dump files - // that only contain the RTP headers, and no payload (a.k.a RTP dummy files or - // RTP light). The `virtual_packet_length_bytes` tells what size the packet - // had on wire, including the now discarded payload. - Packet(CopyOnWriteBuffer packet, - size_t virtual_packet_length_bytes, - double time_ms, - const RtpHeaderExtensionMap* extension_map = nullptr); - - Packet(CopyOnWriteBuffer packet, - double time_ms, - const RtpHeaderExtensionMap* extension_map = nullptr) - : Packet(packet, packet.size(), time_ms, extension_map) {} - - // Same as above, but creates the packet from an already parsed RTPHeader. - // This is typically used when reading RTP dump files that only contain the - // RTP headers, and no payload. The `virtual_packet_length_bytes` tells what - // size the packet had on wire, including the now discarded payload, - // The `virtual_payload_length_bytes` tells the size of the payload. - Packet(const RTPHeader& header, - size_t virtual_packet_length_bytes, - size_t virtual_payload_length_bytes, - double time_ms); - - virtual ~Packet(); - - Packet(const Packet&) = delete; - Packet& operator=(const Packet&) = delete; - - // Parses the first bytes of the RTP payload, interpreting them as RED headers - // according to RFC 2198. The headers will be inserted into `headers`. The - // caller of the method assumes ownership of the objects in the list, and - // must delete them properly. - bool ExtractRedHeaders(std::list<RTPHeader*>* headers) const; - - // Deletes all RTPHeader objects in `headers`, but does not delete `headers` - // itself. - static void DeleteRedHeaders(std::list<RTPHeader*>* headers); - - const uint8_t* payload() const { return rtp_payload_.data(); } - - size_t packet_length_bytes() const { return packet_.size(); } - - size_t payload_length_bytes() const { return rtp_payload_.size(); } - - size_t virtual_packet_length_bytes() const { - return virtual_packet_length_bytes_; - } - - size_t virtual_payload_length_bytes() const { - return virtual_payload_length_bytes_; - } - - const RTPHeader& header() const { return header_; } - - double time_ms() const { return time_ms_; } - bool valid_header() const { return valid_header_; } - - private: - bool ParseHeader(const RtpHeaderExtensionMap* extension_map); - void CopyToHeader(RTPHeader* destination) const; - - RTPHeader header_; - const CopyOnWriteBuffer packet_; - ArrayView<const uint8_t> rtp_payload_; // Empty for dummy RTP packets. - // Virtual lengths are used when parsing RTP header files (dummy RTP files). - const size_t virtual_packet_length_bytes_; - size_t virtual_payload_length_bytes_ = 0; - const double time_ms_; // Used to denote a packet's arrival time. - const bool valid_header_; -}; - -} // namespace test -} // namespace webrtc -#endif // MODULES_AUDIO_CODING_NETEQ_TOOLS_PACKET_H_ diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet_source.h b/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet_source.h @@ -15,7 +15,7 @@ #include <cstdint> #include <memory> -#include "modules/audio_coding/neteq/tools/packet.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" namespace webrtc { namespace test { @@ -31,7 +31,7 @@ class PacketSource { // Returns next packet. Returns nullptr if the source is depleted, or if an // error occurred. - virtual std::unique_ptr<Packet> NextPacket() = 0; + virtual std::unique_ptr<RtpPacketReceived> NextPacket() = 0; virtual void FilterOutPayloadType(uint8_t payload_type); diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet_unittest.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/packet_unittest.cc @@ -1,233 +0,0 @@ -/* - * Copyright (c) 2014 The WebRTC 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. - */ - -// Unit tests for test Packet class. - -#include "modules/audio_coding/neteq/tools/packet.h" - -#include <cstddef> -#include <cstdint> -#include <list> -#include <utility> - -#include "api/rtp_headers.h" -#include "rtc_base/copy_on_write_buffer.h" -#include "test/gtest.h" - -namespace webrtc { -namespace test { - -namespace { -constexpr int kHeaderLengthBytes = 12; - -void MakeRtpHeader(int payload_type, - int seq_number, - uint32_t timestamp, - uint32_t ssrc, - uint8_t* rtp_data) { - rtp_data[0] = 0x80; - rtp_data[1] = static_cast<uint8_t>(payload_type); - rtp_data[2] = (seq_number >> 8) & 0xFF; - rtp_data[3] = (seq_number) & 0xFF; - rtp_data[4] = timestamp >> 24; - rtp_data[5] = (timestamp >> 16) & 0xFF; - rtp_data[6] = (timestamp >> 8) & 0xFF; - rtp_data[7] = timestamp & 0xFF; - rtp_data[8] = ssrc >> 24; - rtp_data[9] = (ssrc >> 16) & 0xFF; - rtp_data[10] = (ssrc >> 8) & 0xFF; - rtp_data[11] = ssrc & 0xFF; -} -} // namespace - -TEST(TestPacket, RegularPacket) { - const size_t kPacketLengthBytes = 100; - CopyOnWriteBuffer packet_memory(kPacketLengthBytes); - const uint8_t kPayloadType = 17; - const uint16_t kSequenceNumber = 4711; - const uint32_t kTimestamp = 47114711; - const uint32_t kSsrc = 0x12345678; - MakeRtpHeader(kPayloadType, kSequenceNumber, kTimestamp, kSsrc, - packet_memory.MutableData()); - const double kPacketTime = 1.0; - Packet packet(std::move(packet_memory), kPacketTime); - ASSERT_TRUE(packet.valid_header()); - EXPECT_EQ(kPayloadType, packet.header().payloadType); - EXPECT_EQ(kSequenceNumber, packet.header().sequenceNumber); - EXPECT_EQ(kTimestamp, packet.header().timestamp); - EXPECT_EQ(kSsrc, packet.header().ssrc); - EXPECT_EQ(0, packet.header().numCSRCs); - EXPECT_EQ(kPacketLengthBytes, packet.packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.payload_length_bytes()); - EXPECT_EQ(kPacketLengthBytes, packet.virtual_packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.virtual_payload_length_bytes()); - EXPECT_EQ(kPacketTime, packet.time_ms()); -} - -TEST(TestPacket, DummyPacket) { - const size_t kPacketLengthBytes = kHeaderLengthBytes; // Only RTP header. - const size_t kVirtualPacketLengthBytes = 100; - CopyOnWriteBuffer packet_memory(kPacketLengthBytes); - const uint8_t kPayloadType = 17; - const uint16_t kSequenceNumber = 4711; - const uint32_t kTimestamp = 47114711; - const uint32_t kSsrc = 0x12345678; - MakeRtpHeader(kPayloadType, kSequenceNumber, kTimestamp, kSsrc, - packet_memory.MutableData()); - const double kPacketTime = 1.0; - Packet packet(std::move(packet_memory), kVirtualPacketLengthBytes, - kPacketTime); - ASSERT_TRUE(packet.valid_header()); - EXPECT_EQ(kPayloadType, packet.header().payloadType); - EXPECT_EQ(kSequenceNumber, packet.header().sequenceNumber); - EXPECT_EQ(kTimestamp, packet.header().timestamp); - EXPECT_EQ(kSsrc, packet.header().ssrc); - EXPECT_EQ(0, packet.header().numCSRCs); - EXPECT_EQ(kPacketLengthBytes, packet.packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.payload_length_bytes()); - EXPECT_EQ(kVirtualPacketLengthBytes, packet.virtual_packet_length_bytes()); - EXPECT_EQ(kVirtualPacketLengthBytes - kHeaderLengthBytes, - packet.virtual_payload_length_bytes()); - EXPECT_EQ(kPacketTime, packet.time_ms()); -} - -TEST(TestPacket, DummyPaddingPacket) { - const size_t kPacketLengthBytes = kHeaderLengthBytes; // Only RTP header. - const size_t kVirtualPacketLengthBytes = 100; - CopyOnWriteBuffer packet_memory(kPacketLengthBytes); - const uint8_t kPayloadType = 17; - const uint16_t kSequenceNumber = 4711; - const uint32_t kTimestamp = 47114711; - const uint32_t kSsrc = 0x12345678; - MakeRtpHeader(kPayloadType, kSequenceNumber, kTimestamp, kSsrc, - packet_memory.MutableData()); - packet_memory.MutableData()[0] |= 0b0010'0000; // Set the padding bit. - const double kPacketTime = 1.0; - Packet packet(std::move(packet_memory), kVirtualPacketLengthBytes, - kPacketTime); - ASSERT_TRUE(packet.valid_header()); - EXPECT_EQ(kPayloadType, packet.header().payloadType); - EXPECT_EQ(kSequenceNumber, packet.header().sequenceNumber); - EXPECT_EQ(kTimestamp, packet.header().timestamp); - EXPECT_EQ(kSsrc, packet.header().ssrc); - EXPECT_EQ(0, packet.header().numCSRCs); - EXPECT_EQ(kPacketLengthBytes, packet.packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.payload_length_bytes()); - EXPECT_EQ(kVirtualPacketLengthBytes, packet.virtual_packet_length_bytes()); - EXPECT_EQ(kVirtualPacketLengthBytes - kHeaderLengthBytes, - packet.virtual_payload_length_bytes()); - EXPECT_EQ(kPacketTime, packet.time_ms()); -} - -namespace { -// Writes one RED block header starting at `rtp_data`, according to RFC 2198. -// returns the number of bytes written (1 or 4). -// -// Format if `last_payoad` is false: -// 0 1 2 3 -// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 -// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ -// |1| block PT | timestamp offset | block length | -// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ -// -// Format if `last_payoad` is true: -// 0 1 2 3 4 5 6 7 -// +-+-+-+-+-+-+-+-+ -// |0| Block PT | -// +-+-+-+-+-+-+-+-+ - -int MakeRedHeader(int payload_type, - uint32_t timestamp_offset, - int block_length, - bool last_payload, - uint8_t* rtp_data) { - rtp_data[0] = 0x80 | (payload_type & 0x7F); // Set the first bit to 1. - if (last_payload) { - rtp_data[0] &= 0x7F; // Reset the first but to 0 to indicate last block. - return 1; - } - rtp_data[1] = timestamp_offset >> 6; - rtp_data[2] = (timestamp_offset & 0x3F) << 2; - rtp_data[2] |= block_length >> 8; - rtp_data[3] = block_length & 0xFF; - return 4; -} -} // namespace - -TEST(TestPacket, RED) { - const size_t kPacketLengthBytes = 100; - CopyOnWriteBuffer packet_memory(kPacketLengthBytes); - const uint8_t kRedPayloadType = 17; - const uint16_t kSequenceNumber = 4711; - const uint32_t kTimestamp = 47114711; - const uint32_t kSsrc = 0x12345678; - MakeRtpHeader(kRedPayloadType, kSequenceNumber, kTimestamp, kSsrc, - packet_memory.MutableData()); - // Create four RED headers. - // Payload types are just the same as the block index the offset is 100 times - // the block index. - const int kRedBlocks = 4; - uint8_t* payload_ptr = packet_memory.MutableData() + - kHeaderLengthBytes; // First byte after header. - for (int i = 0; i < kRedBlocks; ++i) { - int payload_type = i; - // Offset value is not used for the last block. - uint32_t timestamp_offset = 100 * i; - int block_length = 10 * i; - bool last_block = (i == kRedBlocks - 1) ? true : false; - payload_ptr += MakeRedHeader(payload_type, timestamp_offset, block_length, - last_block, payload_ptr); - } - const double kPacketTime = 1.0; - // Hand over ownership of `packet_memory` to `packet`. - Packet packet(packet_memory, kPacketLengthBytes, kPacketTime); - ASSERT_TRUE(packet.valid_header()); - EXPECT_EQ(kRedPayloadType, packet.header().payloadType); - EXPECT_EQ(kSequenceNumber, packet.header().sequenceNumber); - EXPECT_EQ(kTimestamp, packet.header().timestamp); - EXPECT_EQ(kSsrc, packet.header().ssrc); - EXPECT_EQ(0, packet.header().numCSRCs); - EXPECT_EQ(kPacketLengthBytes, packet.packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.payload_length_bytes()); - EXPECT_EQ(kPacketLengthBytes, packet.virtual_packet_length_bytes()); - EXPECT_EQ(kPacketLengthBytes - kHeaderLengthBytes, - packet.virtual_payload_length_bytes()); - EXPECT_EQ(kPacketTime, packet.time_ms()); - std::list<RTPHeader*> red_headers; - EXPECT_TRUE(packet.ExtractRedHeaders(&red_headers)); - EXPECT_EQ(kRedBlocks, static_cast<int>(red_headers.size())); - int block_index = 0; - for (std::list<RTPHeader*>::reverse_iterator it = red_headers.rbegin(); - it != red_headers.rend(); ++it) { - // Reading list from the back, since the extraction puts the main payload - // (which is the last one on wire) first. - RTPHeader* red_block = *it; - EXPECT_EQ(block_index, red_block->payloadType); - EXPECT_EQ(kSequenceNumber, red_block->sequenceNumber); - if (block_index == kRedBlocks - 1) { - // Last block has zero offset per definition. - EXPECT_EQ(kTimestamp, red_block->timestamp); - } else { - EXPECT_EQ(kTimestamp - 100 * block_index, red_block->timestamp); - } - EXPECT_EQ(kSsrc, red_block->ssrc); - EXPECT_EQ(0, red_block->numCSRCs); - ++block_index; - } - Packet::DeleteRedHeaders(&red_headers); -} - -} // namespace test -} // namespace webrtc diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_analyze.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_analyze.cc @@ -8,9 +8,9 @@ * be found in the AUTHORS file in the root of the source tree. */ +#include <algorithm> #include <cstdint> #include <cstdio> -#include <list> #include <memory> #include <string> #include <vector> @@ -18,9 +18,10 @@ #include "absl/flags/flag.h" #include "absl/flags/parse.h" #include "api/rtp_headers.h" -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/rtp_file_source.h" #include "modules/rtp_rtcp/include/rtp_rtcp_defines.h" +#include "modules/rtp_rtcp/source/rtp_header_extensions.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "rtc_base/checks.h" ABSL_FLAG(int, red, 117, "RTP payload type for RED"); @@ -35,6 +36,54 @@ ABSL_FLAG(int, "Extension ID for absolute sender time; " "-1 not to print absolute send time"); +namespace { + +struct RedHeader { + uint32_t rtp_timestamp; + int payload_type; +}; +std::vector<RedHeader> ExtractRedHeaders(const webrtc::RtpPacket& packet) { + // + // 0 1 2 3 + // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 + // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + // |1| block PT | timestamp offset | block length | + // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + // |1| ... | + // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + // |0| block PT | + // +-+-+-+-+-+-+-+-+ + // + const uint8_t* payload_ptr = packet.payload().data(); + const uint8_t* payload_end_ptr = + packet.payload().data() + packet.payload().size(); + + // Find all RED headers with the extension bit set to 1. That is, all headers + // but the last one. + std::vector<RedHeader> red_headers; + while ((payload_ptr < payload_end_ptr) && (*payload_ptr & 0x80)) { + RedHeader header; + header.payload_type = payload_ptr[0] & 0x7F; + uint32_t offset = (payload_ptr[1] << 6) + ((payload_ptr[2] & 0xFC) >> 2); + header.rtp_timestamp = packet.Timestamp() - offset; + red_headers.push_back(header); + payload_ptr += 4; + } + // Last header. + RTC_DCHECK_LT(payload_ptr, payload_end_ptr); + if (payload_ptr >= payload_end_ptr) { + return {}; // Payload too short. + } + RedHeader header; + header.payload_type = payload_ptr[0] & 0x7F; + header.rtp_timestamp = packet.Timestamp(); + red_headers.push_back(header); + std::reverse(red_headers.begin(), red_headers.end()); + return red_headers; +} + +} // namespace + int main(int argc, char* argv[]) { std::vector<char*> args = absl::ParseCommandLine(argc, argv); std::string usage = @@ -100,7 +149,7 @@ int main(int argc, char* argv[]) { uint32_t max_abs_send_time = 0; int cycles = -1; - std::unique_ptr<webrtc::test::Packet> packet; + std::unique_ptr<webrtc::RtpPacketReceived> packet; while (true) { packet = file_source->NextPacket(); if (!packet.get()) { @@ -109,59 +158,51 @@ int main(int argc, char* argv[]) { } // Write packet data to file. Use virtual_packet_length_bytes so that the // correct packet sizes are printed also for RTP header-only dumps. - fprintf(out_file, "%5u %10u %10u %5i %5i %2i %#08X", - packet->header().sequenceNumber, packet->header().timestamp, - static_cast<unsigned int>(packet->time_ms()), - static_cast<int>(packet->virtual_packet_length_bytes()), - packet->header().payloadType, packet->header().markerBit, - packet->header().ssrc); - if (print_audio_level && packet->header().extension.audio_level()) { - fprintf(out_file, " %5d (%1i)", - packet->header().extension.audio_level()->level(), - packet->header().extension.audio_level()->voice_activity()); + fprintf(out_file, "%5u %10u %10i %5zu %5i %2i %#08X", + packet->SequenceNumber(), packet->Timestamp(), + packet->arrival_time().ms<int>(), packet->size(), + packet->PayloadType(), packet->Marker(), packet->Ssrc()); + webrtc::AudioLevel audio_level; + if (print_audio_level && + packet->GetExtension<webrtc::AudioLevelExtension>(&audio_level)) { + fprintf(out_file, " %5d (%1i)", audio_level.level(), + audio_level.voice_activity()); } - if (print_abs_send_time && packet->header().extension.hasAbsoluteSendTime) { + uint32_t abs_sent_time; + if (print_abs_send_time && + packet->GetExtension<webrtc::AbsoluteSendTime>(&abs_sent_time)) { if (cycles == -1) { // Initialize. - max_abs_send_time = packet->header().extension.absoluteSendTime; + max_abs_send_time = abs_sent_time; cycles = 0; } // Abs sender time is 24 bit 6.18 fixed point. Shift by 8 to normalize to // 32 bits (unsigned). Calculate the difference between this packet's // send time and the maximum observed. Cast to signed 32-bit to get the // desired wrap-around behavior. - if (static_cast<int32_t>( - (packet->header().extension.absoluteSendTime << 8) - - (max_abs_send_time << 8)) >= 0) { + if (static_cast<int32_t>((abs_sent_time << 8) - + (max_abs_send_time << 8)) >= 0) { // The difference is non-negative, meaning that this packet is newer // than the previously observed maximum absolute send time. - if (packet->header().extension.absoluteSendTime < max_abs_send_time) { + if (abs_sent_time < max_abs_send_time) { // Wrap detected. cycles++; } - max_abs_send_time = packet->header().extension.absoluteSendTime; + max_abs_send_time = abs_sent_time; } // Abs sender time is 24 bit 6.18 fixed point. Divide by 2^18 to convert // to floating point representation. double send_time_seconds = - static_cast<double>(packet->header().extension.absoluteSendTime) / - 262144 + - 64.0 * cycles; + static_cast<double>(abs_sent_time) / 262144 + 64.0 * cycles; fprintf(out_file, " %11f", send_time_seconds); } fprintf(out_file, "\n"); - if (packet->header().payloadType == absl::GetFlag(FLAGS_red)) { - std::list<webrtc::RTPHeader*> red_headers; - packet->ExtractRedHeaders(&red_headers); - while (!red_headers.empty()) { - webrtc::RTPHeader* red = red_headers.front(); - RTC_DCHECK(red); - fprintf(out_file, "* %5u %10u %10u %5i\n", red->sequenceNumber, - red->timestamp, static_cast<unsigned int>(packet->time_ms()), - red->payloadType); - red_headers.pop_front(); - delete red; + if (packet->PayloadType() == absl::GetFlag(FLAGS_red)) { + for (const RedHeader& red : ExtractRedHeaders(*packet)) { + fprintf(out_file, "* %5u %10u %10i %5i\n", packet->SequenceNumber(), + red.rtp_timestamp, packet->arrival_time().ms<int>(), + red.payload_type); } } } diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_file_source.cc b/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_file_source.cc @@ -10,17 +10,18 @@ #include "modules/audio_coding/neteq/tools/rtp_file_source.h" +#include <algorithm> #include <cstdint> #include <cstring> #include <memory> #include <optional> #include "absl/strings/string_view.h" -#include "modules/audio_coding/neteq/tools/packet.h" +#include "api/units/timestamp.h" #include "modules/audio_coding/neteq/tools/packet_source.h" #include "modules/rtp_rtcp/include/rtp_rtcp_defines.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" #include "rtc_base/checks.h" -#include "rtc_base/copy_on_write_buffer.h" #include "test/rtp_file_reader.h" namespace webrtc { @@ -52,7 +53,7 @@ bool RtpFileSource::RegisterRtpHeaderExtension(RTPExtensionType type, return rtp_header_extension_map_.RegisterByType(id, type); } -std::unique_ptr<Packet> RtpFileSource::NextPacket() { +std::unique_ptr<RtpPacketReceived> RtpFileSource::NextPacket() { while (true) { RtpPacket temp_packet; if (!rtp_reader_->NextPacket(&temp_packet)) { @@ -63,19 +64,29 @@ std::unique_ptr<Packet> RtpFileSource::NextPacket() { // Read the next one. continue; } - auto packet = std::make_unique<Packet>( - CopyOnWriteBuffer(temp_packet.data, temp_packet.length), - temp_packet.original_length, temp_packet.time_ms, - &rtp_header_extension_map_); - if (!packet->valid_header()) { + auto rtp_packet = + std::make_unique<RtpPacketReceived>(&rtp_header_extension_map_); + if (!rtp_packet->Parse(temp_packet.data, temp_packet.length)) { continue; } - if (filter_.test(packet->header().payloadType) || - (ssrc_filter_ && packet->header().ssrc != *ssrc_filter_)) { + if (filter_.test(rtp_packet->PayloadType()) || + (ssrc_filter_ && rtp_packet->Ssrc() != *ssrc_filter_)) { // This payload type should be filtered out. Continue to the next packet. continue; } - return packet; + rtp_packet->set_arrival_time(Timestamp::Millis(temp_packet.time_ms)); + if (temp_packet.original_length > rtp_packet->headers_size()) { + size_t payload_size = + temp_packet.original_length - rtp_packet->headers_size(); + if (rtp_packet->has_padding()) { + // If padding bit is set in the RTP header, assume it was a pure padding + // packet. + rtp_packet->SetPadding(payload_size); + } else { + std::fill_n(rtp_packet->AllocatePayload(payload_size), payload_size, 0); + } + } + return rtp_packet; } } diff --git a/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_file_source.h b/third_party/libwebrtc/modules/audio_coding/neteq/tools/rtp_file_source.h @@ -18,10 +18,10 @@ #include <optional> #include "absl/strings/string_view.h" -#include "modules/audio_coding/neteq/tools/packet.h" #include "modules/audio_coding/neteq/tools/packet_source.h" #include "modules/rtp_rtcp/include/rtp_header_extension_map.h" #include "modules/rtp_rtcp/include/rtp_rtcp_defines.h" +#include "modules/rtp_rtcp/source/rtp_packet_received.h" namespace webrtc { @@ -49,7 +49,7 @@ class RtpFileSource : public PacketSource { // Registers an RTP header extension and binds it to `id`. virtual bool RegisterRtpHeaderExtension(RTPExtensionType type, uint8_t id); - std::unique_ptr<Packet> NextPacket() override; + std::unique_ptr<RtpPacketReceived> NextPacket() override; private: static const int kFirstLineLength = 40; diff --git a/third_party/libwebrtc/moz-patch-stack/s0027.patch b/third_party/libwebrtc/moz-patch-stack/s0027.patch @@ -724,7 +724,7 @@ index 6d4d4a2363..316408a9b3 100644 : content_hint(VideoTrackInterface::ContentHint::kNone) {} VideoOptions::~VideoOptions() = default; diff --git a/modules/audio_coding/BUILD.gn b/modules/audio_coding/BUILD.gn -index a24282bee8..f09ff0301a 100644 +index bce09e0f81..12a9566a8f 100644 --- a/modules/audio_coding/BUILD.gn +++ b/modules/audio_coding/BUILD.gn @@ -362,7 +362,7 @@ rtc_library("webrtc_opus_wrapper") { diff --git a/third_party/libwebrtc/moz-patch-stack/s0099.patch b/third_party/libwebrtc/moz-patch-stack/s0099.patch @@ -16,7 +16,7 @@ Mercurial Revision: https://hg.mozilla.org/mozilla-central/rev/bbec1b95ddb5e0096 5 files changed, 26 insertions(+), 6 deletions(-) diff --git a/modules/audio_coding/BUILD.gn b/modules/audio_coding/BUILD.gn -index f09ff0301a..6499340c5f 100644 +index 12a9566a8f..ef8c7dd339 100644 --- a/modules/audio_coding/BUILD.gn +++ b/modules/audio_coding/BUILD.gn @@ -362,7 +362,7 @@ rtc_library("webrtc_opus_wrapper") {