Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(414)

Unified Diff: remoting/protocol/client_video_dispatcher_unittest.cc

Issue 850983002: Implement video frame acknowledgements in the chromoting protocol. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « remoting/protocol/client_video_dispatcher.cc ('k') | remoting/protocol/connection_to_client.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: remoting/protocol/client_video_dispatcher_unittest.cc
diff --git a/remoting/protocol/client_video_dispatcher_unittest.cc b/remoting/protocol/client_video_dispatcher_unittest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..92087b3357a595b5afe026f00110515ce5ef2476
--- /dev/null
+++ b/remoting/protocol/client_video_dispatcher_unittest.cc
@@ -0,0 +1,180 @@
+// Copyright 2015 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 "remoting/protocol/client_video_dispatcher.h"
+
+#include "base/bind.h"
+#include "base/memory/scoped_vector.h"
+#include "base/message_loop/message_loop.h"
+#include "base/run_loop.h"
+#include "remoting/base/constants.h"
+#include "remoting/proto/video.pb.h"
+#include "remoting/protocol/fake_session.h"
+#include "remoting/protocol/fake_stream_socket.h"
+#include "remoting/protocol/message_serialization.h"
+#include "remoting/protocol/video_stub.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace remoting {
+namespace protocol {
+
+class ClientVideoDispatcherTest : public testing::Test,
+ public VideoStub,
+ public ChannelDispatcherBase::EventHandler {
+ public:
+ ClientVideoDispatcherTest();
+
+ // VideoStub interface.
+ void ProcessVideoPacket(scoped_ptr<VideoPacket> video_packet,
+ const base::Closure& done) override;
+
+ // ChannelDispatcherBase::EventHandler interface.
+ void OnChannelInitialized(ChannelDispatcherBase* channel_dispatcher) override;
+ void OnChannelError(ChannelDispatcherBase* channel_dispatcher,
+ ErrorCode error) override;
+
+ protected:
+ void OnVideoAck(scoped_ptr<VideoAck> ack, const base::Closure& done);
+
+ base::MessageLoop message_loop_;
+
+ // Set to true in OnChannelInitialized().
+ bool initialized_;
+
+ // Client side.
+ ClientVideoDispatcher dispatcher_;
+ FakeSession session_;
+
+ // Host side.
+ FakeStreamSocket host_socket_;
+ MessageReader reader_;
+ ProtobufMessageParser<VideoAck> parser_;
+ BufferedSocketWriter writer_;
+
+ ScopedVector<VideoPacket> video_packets_;
+ std::vector<base::Closure> packet_done_callbacks_;
+
+ ScopedVector<VideoAck> ack_messages_;
+};
+
+ClientVideoDispatcherTest::ClientVideoDispatcherTest()
+ : initialized_(false),
+ dispatcher_(this),
+ parser_(base::Bind(&ClientVideoDispatcherTest::OnVideoAck,
+ base::Unretained(this)),
+ &reader_) {
+ dispatcher_.Init(&session_, ChannelConfig(ChannelConfig::TRANSPORT_MUX_STREAM,
+ kDefaultStreamVersion,
+ ChannelConfig::CODEC_UNDEFINED),
+ this);
+ base::RunLoop().RunUntilIdle();
+ DCHECK(initialized_);
+ host_socket_.PairWith(
+ session_.fake_channel_factory().GetFakeChannel(kVideoChannelName));
+ reader_.StartReading(&host_socket_);
+ writer_.Init(&host_socket_, BufferedSocketWriter::WriteFailedCallback());
+}
+
+void ClientVideoDispatcherTest::ProcessVideoPacket(
+ scoped_ptr<VideoPacket> video_packet,
+ const base::Closure& done) {
+ video_packets_.push_back(video_packet.release());
+ packet_done_callbacks_.push_back(done);
+}
+
+void ClientVideoDispatcherTest::OnChannelInitialized(
+ ChannelDispatcherBase* channel_dispatcher) {
+ initialized_ = true;
+}
+
+void ClientVideoDispatcherTest::OnChannelError(
+ ChannelDispatcherBase* channel_dispatcher,
+ ErrorCode error) {
+ // Don't expect channel creation to fail.
+ FAIL();
+}
+
+void ClientVideoDispatcherTest::OnVideoAck(scoped_ptr<VideoAck> ack,
+ const base::Closure& done) {
+ ack_messages_.push_back(ack.release());
+ done.Run();
+}
+
+// Verify that the client can receive video packets and acks are not sent for
+// VideoPackets that don't have frame_id field set.
+TEST_F(ClientVideoDispatcherTest, WithoutAcks) {
+ VideoPacket packet;
+ packet.set_data(std::string());
+
+ // Send a VideoPacket and verify that the client receives it.
+ writer_.Write(SerializeAndFrameMessage(packet), base::Closure());
+ base::RunLoop().RunUntilIdle();
+ EXPECT_EQ(1U, video_packets_.size());
+
+ packet_done_callbacks_.front().Run();
+ base::RunLoop().RunUntilIdle();
+
+ // Ack should never be sent for the packet without frame_id.
+ EXPECT_TRUE(ack_messages_.empty());
+}
+
+// Verifies that the dispatcher sends Ack message with correct rendering delay.
+TEST_F(ClientVideoDispatcherTest, WithAcks) {
+ int kTestFrameId = 3;
+
+ VideoPacket packet;
+ packet.set_data(std::string());
+ packet.set_frame_id(kTestFrameId);
+
+ // Send a VideoPacket and verify that the client receives it.
+ writer_.Write(SerializeAndFrameMessage(packet), base::Closure());
+ base::RunLoop().RunUntilIdle();
+ EXPECT_EQ(1U, video_packets_.size());
+
+ // Ack should only be sent after the packet is processed.
+ EXPECT_TRUE(ack_messages_.empty());
+ base::RunLoop().RunUntilIdle();
+
+ // Fake completion of video packet decoding, to trigger the Ack.
+ packet_done_callbacks_.front().Run();
+ base::RunLoop().RunUntilIdle();
+
+ // Verify that the Ack message has been received.
+ ASSERT_EQ(1U, ack_messages_.size());
+ EXPECT_EQ(kTestFrameId, ack_messages_[0]->frame_id());
+}
+
+// Verify that Ack messages are sent in correct order.
+TEST_F(ClientVideoDispatcherTest, AcksOrder) {
+ int kTestFrameId = 3;
+
+ VideoPacket packet;
+ packet.set_data(std::string());
+ packet.set_frame_id(kTestFrameId);
+
+ // Send two VideoPackets.
+ writer_.Write(SerializeAndFrameMessage(packet), base::Closure());
+ base::RunLoop().RunUntilIdle();
+
+ packet.set_frame_id(kTestFrameId + 1);
+ writer_.Write(SerializeAndFrameMessage(packet), base::Closure());
+ base::RunLoop().RunUntilIdle();
+
+ EXPECT_EQ(2U, video_packets_.size());
+ EXPECT_TRUE(ack_messages_.empty());
+
+ // Call completion callbacks in revers order.
+ packet_done_callbacks_[1].Run();
+ packet_done_callbacks_[0].Run();
+
+ base::RunLoop().RunUntilIdle();
+
+ // Verify order of Ack messages.
+ ASSERT_EQ(2U, ack_messages_.size());
+ EXPECT_EQ(kTestFrameId, ack_messages_[0]->frame_id());
+ EXPECT_EQ(kTestFrameId + 1, ack_messages_[1]->frame_id());
+}
+
+} // namespace protocol
+} // namespace remoting
« no previous file with comments | « remoting/protocol/client_video_dispatcher.cc ('k') | remoting/protocol/connection_to_client.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698