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

Side by Side Diff: media/cast/net/udp_transport.cc

Issue 967723002: Cast: Fix crash in udp_transport (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: typ0 Created 5 years, 7 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 unified diff | Download patch
« no previous file with comments | « media/cast/net/udp_transport.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/cast/net/udp_transport.h" 5 #include "media/cast/net/udp_transport.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <string> 8 #include <string>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
59 weak_factory_(this) { 59 weak_factory_(this) {
60 DCHECK(!IsEmpty(local_end_point) || !IsEmpty(remote_end_point)); 60 DCHECK(!IsEmpty(local_end_point) || !IsEmpty(remote_end_point));
61 } 61 }
62 62
63 UdpTransport::~UdpTransport() {} 63 UdpTransport::~UdpTransport() {}
64 64
65 void UdpTransport::StartReceiving( 65 void UdpTransport::StartReceiving(
66 const PacketReceiverCallbackWithStatus& packet_receiver) { 66 const PacketReceiverCallbackWithStatus& packet_receiver) {
67 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 67 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
68 68
69 if (!udp_socket_) {
70 status_callback_.Run(TRANSPORT_SOCKET_ERROR);
71 return;
72 }
73
69 packet_receiver_ = packet_receiver; 74 packet_receiver_ = packet_receiver;
70 udp_socket_->SetMulticastLoopbackMode(true); 75 udp_socket_->SetMulticastLoopbackMode(true);
71 if (!IsEmpty(local_addr_)) { 76 if (!IsEmpty(local_addr_)) {
72 if (udp_socket_->Open(local_addr_.GetFamily()) < 0 || 77 if (udp_socket_->Open(local_addr_.GetFamily()) < 0 ||
73 udp_socket_->AllowAddressReuse() < 0 || 78 udp_socket_->AllowAddressReuse() < 0 ||
74 udp_socket_->Bind(local_addr_) < 0) { 79 udp_socket_->Bind(local_addr_) < 0) {
75 udp_socket_->Close(); 80 udp_socket_->Close();
81 udp_socket_.reset();
76 status_callback_.Run(TRANSPORT_SOCKET_ERROR); 82 status_callback_.Run(TRANSPORT_SOCKET_ERROR);
77 LOG(ERROR) << "Failed to bind local address."; 83 LOG(ERROR) << "Failed to bind local address.";
78 return; 84 return;
79 } 85 }
80 } else if (!IsEmpty(remote_addr_)) { 86 } else if (!IsEmpty(remote_addr_)) {
81 if (udp_socket_->Open(remote_addr_.GetFamily()) < 0 || 87 if (udp_socket_->Open(remote_addr_.GetFamily()) < 0 ||
82 udp_socket_->AllowAddressReuse() < 0 || 88 udp_socket_->AllowAddressReuse() < 0 ||
83 udp_socket_->Connect(remote_addr_) < 0) { 89 udp_socket_->Connect(remote_addr_) < 0) {
84 udp_socket_->Close(); 90 udp_socket_->Close();
91 udp_socket_.reset();
85 status_callback_.Run(TRANSPORT_SOCKET_ERROR); 92 status_callback_.Run(TRANSPORT_SOCKET_ERROR);
86 LOG(ERROR) << "Failed to connect to remote address."; 93 LOG(ERROR) << "Failed to connect to remote address.";
87 return; 94 return;
88 } 95 }
89 client_connected_ = true; 96 client_connected_ = true;
90 } else { 97 } else {
91 NOTREACHED() << "Either local or remote address has to be defined."; 98 NOTREACHED() << "Either local or remote address has to be defined.";
92 } 99 }
93 if (udp_socket_->SetSendBufferSize(send_buffer_size_) != net::OK) { 100 if (udp_socket_->SetSendBufferSize(send_buffer_size_) != net::OK) {
94 LOG(WARNING) << "Failed to set socket send buffer size."; 101 LOG(WARNING) << "Failed to set socket send buffer size.";
95 } 102 }
96 103
97 ScheduleReceiveNextPacket(); 104 ScheduleReceiveNextPacket();
98 } 105 }
99 106
100 void UdpTransport::StopReceiving() { 107 void UdpTransport::StopReceiving() {
101 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 108 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
102 packet_receiver_ = PacketReceiverCallbackWithStatus(); 109 packet_receiver_ = PacketReceiverCallbackWithStatus();
103 } 110 }
104 111
105 112
106 void UdpTransport::SetDscp(net::DiffServCodePoint dscp) { 113 void UdpTransport::SetDscp(net::DiffServCodePoint dscp) {
107 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 114 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
108 next_dscp_value_ = dscp; 115 next_dscp_value_ = dscp;
109 } 116 }
110 117
111 #if defined(OS_WIN) 118 #if defined(OS_WIN)
112 void UdpTransport::UseNonBlockingIO() { 119 void UdpTransport::UseNonBlockingIO() {
113 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 120 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
121 if (!udp_socket_)
122 return;
114 udp_socket_->UseNonBlockingIO(); 123 udp_socket_->UseNonBlockingIO();
115 } 124 }
116 #endif 125 #endif
117 126
118 void UdpTransport::ScheduleReceiveNextPacket() { 127 void UdpTransport::ScheduleReceiveNextPacket() {
119 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 128 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
120 if (!packet_receiver_.is_null() && !receive_pending_) { 129 if (!packet_receiver_.is_null() && !receive_pending_) {
121 receive_pending_ = true; 130 receive_pending_ = true;
122 io_thread_proxy_->PostTask(FROM_HERE, 131 io_thread_proxy_->PostTask(FROM_HERE,
123 base::Bind(&UdpTransport::ReceiveNextPacket, 132 base::Bind(&UdpTransport::ReceiveNextPacket,
124 weak_factory_.GetWeakPtr(), 133 weak_factory_.GetWeakPtr(),
125 net::ERR_IO_PENDING)); 134 net::ERR_IO_PENDING));
126 } 135 }
127 } 136 }
128 137
129 void UdpTransport::ReceiveNextPacket(int length_or_status) { 138 void UdpTransport::ReceiveNextPacket(int length_or_status) {
130 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 139 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
131 140
132 if (packet_receiver_.is_null()) 141 if (packet_receiver_.is_null())
133 return; 142 return;
143 if (!udp_socket_)
144 return;
134 145
135 // Loop while UdpSocket is delivering data synchronously. When it responds 146 // Loop while UdpSocket is delivering data synchronously. When it responds
136 // with a "pending" status, break and expect this method to be called back in 147 // with a "pending" status, break and expect this method to be called back in
137 // the future when a packet is ready. 148 // the future when a packet is ready.
138 while (true) { 149 while (true) {
139 if (length_or_status == net::ERR_IO_PENDING) { 150 if (length_or_status == net::ERR_IO_PENDING) {
140 next_packet_.reset(new Packet(kMaxPacketSize)); 151 next_packet_.reset(new Packet(kMaxPacketSize));
141 recv_buf_ = new net::WrappedIOBuffer( 152 recv_buf_ = new net::WrappedIOBuffer(
142 reinterpret_cast<char*>(&next_packet_->front())); 153 reinterpret_cast<char*>(&next_packet_->front()));
143 length_or_status = 154 length_or_status =
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
180 } else { 191 } else {
181 next_packet_->resize(length_or_status); 192 next_packet_->resize(length_or_status);
182 packet_receiver_.Run(next_packet_.Pass()); 193 packet_receiver_.Run(next_packet_.Pass());
183 } 194 }
184 length_or_status = net::ERR_IO_PENDING; 195 length_or_status = net::ERR_IO_PENDING;
185 } 196 }
186 } 197 }
187 198
188 bool UdpTransport::SendPacket(PacketRef packet, const base::Closure& cb) { 199 bool UdpTransport::SendPacket(PacketRef packet, const base::Closure& cb) {
189 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread()); 200 DCHECK(io_thread_proxy_->RunsTasksOnCurrentThread());
201 if (!udp_socket_)
202 return true;
190 203
191 // Increase byte count no matter the packet was sent or dropped. 204 // Increase byte count no matter the packet was sent or dropped.
192 bytes_sent_ += packet->data.size(); 205 bytes_sent_ += packet->data.size();
193 206
194 DCHECK(!send_pending_); 207 DCHECK(!send_pending_);
195 if (send_pending_) { 208 if (send_pending_) {
196 VLOG(1) << "Cannot send because of pending IO."; 209 VLOG(1) << "Cannot send because of pending IO.";
197 return true; 210 return true;
198 } 211 }
199 212
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
260 } 273 }
261 ScheduleReceiveNextPacket(); 274 ScheduleReceiveNextPacket();
262 275
263 if (!cb.is_null()) { 276 if (!cb.is_null()) {
264 cb.Run(); 277 cb.Run();
265 } 278 }
266 } 279 }
267 280
268 } // namespace cast 281 } // namespace cast
269 } // namespace media 282 } // namespace media
OLDNEW
« no previous file with comments | « media/cast/net/udp_transport.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698