Commit 482d3eb1 authored by hclam's avatar hclam Committed by Commit bot

Cast: set UDP socket send buffer size via options

On Windows the default UDP send buffer size is 8192. OSX default is
9216. On Linux default is 212992. The values are too small on Windows
and OSX. This cannot make good use of the A-MPDU of 802.11n (64KB),
which is the most common network for Cast Streaming.

We have also seen strong evidence that the default buffer size is
limiting, e.g. long packet queuing delay on Windows, p2p socket seeing
a lot of EWOULDBLOCKs.

This code uses pacer maximum burst size (in bytes) as the send buffer
size. Also added an option "send_buffer_min_size" to allow application
to choose an even larger value for send buffer size.

BUG=423545

Review URL: https://codereview.chromium.org/654843007

Cr-Commit-Position: refs/heads/master@{#300183}
parent 1509b222
......@@ -9,12 +9,22 @@
#include "media/cast/net/cast_transport_config.h"
#include "media/cast/net/cast_transport_defines.h"
#include "media/cast/net/udp_transport.h"
#include "net/base/net_errors.h"
#include "net/base/net_util.h"
namespace media {
namespace cast {
namespace {
// See header file for what these mean.
const char kOptionPacerTargetBurstSize[] = "pacer_target_burst_size";
const char kOptionPacerMaxBurstSize[] = "pacer_max_burst_size";
const char kOptionSendBufferMinSize[] = "send_buffer_min_size";
const char kOptionDscp[] = "DSCP";
const char kOptionWifiDisableScan[] = "disable_wifi_scan";
const char kOptionWifiMediaStreamingMode[] = "media_streaming_mode";
int LookupOptionWithDefault(const base::DictionaryValue& options,
const std::string& path,
int default_value) {
......@@ -26,6 +36,17 @@ int LookupOptionWithDefault(const base::DictionaryValue& options,
}
};
int32 GetTransportSendBufferSize(const base::DictionaryValue& options) {
// Socket send buffer size needs to be at least greater than one burst
// size.
int32 max_burst_size =
LookupOptionWithDefault(options, kOptionPacerMaxBurstSize,
kMaxBurstSize) * kMaxIpPacketSize;
int32 min_send_buffer_size =
LookupOptionWithDefault(options, kOptionSendBufferMinSize, 0);
return std::max(max_burst_size, min_send_buffer_size);
}
} // namespace
scoped_ptr<CastTransportSender> CastTransportSender::Create(
......@@ -66,17 +87,20 @@ CastTransportSenderImpl::CastTransportSenderImpl(
: clock_(clock),
status_callback_(status_callback),
transport_task_runner_(transport_task_runner),
transport_(external_transport ? NULL
: new UdpTransport(net_log,
transport_task_runner,
net::IPEndPoint(),
remote_end_point,
status_callback)),
pacer_(LookupOptionWithDefault(*options.get(),
"pacer_target_burst_size",
transport_(
external_transport ?
NULL :
new UdpTransport(net_log,
transport_task_runner,
net::IPEndPoint(),
remote_end_point,
GetTransportSendBufferSize(*options),
status_callback)),
pacer_(LookupOptionWithDefault(*options,
kOptionPacerTargetBurstSize,
kTargetBurstSize),
LookupOptionWithDefault(*options.get(),
"pacer_max_burst_size",
LookupOptionWithDefault(*options,
kOptionPacerMaxBurstSize,
kMaxBurstSize),
clock,
&logging_,
......@@ -98,7 +122,7 @@ CastTransportSenderImpl::CastTransportSenderImpl(
raw_events_callback_interval);
}
if (transport_) {
if (options->HasKey("DSCP")) {
if (options->HasKey(kOptionDscp)) {
// The default DSCP value for cast is AF41. Which gives it a higher
// priority over other traffic.
transport_->SetDscp(net::DSCP_AF41);
......@@ -107,10 +131,10 @@ CastTransportSenderImpl::CastTransportSenderImpl(
base::Bind(&CastTransportSenderImpl::OnReceivedPacket,
weak_factory_.GetWeakPtr()));
int wifi_options = 0;
if (options->HasKey("disable_wifi_scan")) {
if (options->HasKey(kOptionWifiDisableScan)) {
wifi_options |= net::WIFI_OPTIONS_DISABLE_SCAN;
}
if (options->HasKey("media_streaming_mode")) {
if (options->HasKey(kOptionWifiMediaStreamingMode)) {
wifi_options |= net::WIFI_OPTIONS_MEDIA_STREAMING_MODE;
}
if (wifi_options) {
......
......@@ -61,6 +61,8 @@ class CastTransportSenderImpl : public CastTransportSender {
// per 10 ms ideally.
// "pacer_max_burst_size": int - specifies how many pakcets to send
// per 10 ms, max
// "send_buffer_min_size": int - specifies the minimum socket send buffer
// size
// "disable_wifi_scan" (value ignored) - disable wifi scans while streaming
// "media_streaming_mode" (value ignored) - turn media streaming mode on
// Note, these options may be ignored on some platforms.
......
......@@ -42,6 +42,7 @@ UdpTransport::UdpTransport(
const scoped_refptr<base::SingleThreadTaskRunner>& io_thread_proxy,
const net::IPEndPoint& local_end_point,
const net::IPEndPoint& remote_end_point,
int32 send_buffer_size,
const CastTransportStatusCallback& status_callback)
: io_thread_proxy_(io_thread_proxy),
local_addr_(local_end_point),
......@@ -54,6 +55,7 @@ UdpTransport::UdpTransport(
receive_pending_(false),
client_connected_(false),
next_dscp_value_(net::DSCP_NO_CHANGE),
send_buffer_size_(send_buffer_size),
status_callback_(status_callback),
bytes_sent_(0),
weak_factory_(this) {
......@@ -85,6 +87,9 @@ void UdpTransport::StartReceiving(
} else {
NOTREACHED() << "Either local or remote address has to be defined.";
}
if (udp_socket_->SetSendBufferSize(send_buffer_size_) != net::OK) {
LOG(WARNING) << "Failed to set socket send buffer size.";
}
ScheduleReceiveNextPacket();
}
......
......@@ -35,11 +35,13 @@ class UdpTransport : public PacketSender {
// |remote_end_point| specifies the address and port to send packets
// to. If the value is 0.0.0.0:0 the the end point is set to the source
// address of the first packet received.
// |send_buffer_size| specifies the size of the socket send buffer.
UdpTransport(
net::NetLog* net_log,
const scoped_refptr<base::SingleThreadTaskRunner>& io_thread_proxy,
const net::IPEndPoint& local_end_point,
const net::IPEndPoint& remote_end_point,
int32 send_buffer_size,
const CastTransportStatusCallback& status_callback);
virtual ~UdpTransport();
......@@ -82,6 +84,7 @@ class UdpTransport : public PacketSender {
scoped_refptr<net::WrappedIOBuffer> recv_buf_;
net::IPEndPoint recv_addr_;
PacketReceiverCallback packet_receiver_;
int32 send_buffer_size_;
const CastTransportStatusCallback status_callback_;
int bytes_sent_;
......
......@@ -65,11 +65,13 @@ TEST(UdpTransport, SendAndReceive) {
message_loop.message_loop_proxy(),
free_local_port1,
free_local_port2,
65536,
base::Bind(&UpdateCastTransportStatus));
UdpTransport recv_transport(NULL,
message_loop.message_loop_proxy(),
free_local_port2,
net::IPEndPoint(empty_addr_number, 0),
65536,
base::Bind(&UpdateCastTransportStatus));
Packet packet;
......
......@@ -81,6 +81,7 @@ void InProcessReceiver::StartOnMainThread() {
cast_environment_->GetTaskRunner(CastEnvironment::MAIN),
local_end_point_,
remote_end_point_,
65536,
base::Bind(&InProcessReceiver::UpdateCastTransportStatus,
base::Unretained(this))));
cast_receiver_ = CastReceiver::Create(
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment