1 // Copyright 2012 The Chromium Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef NET_SOCKET_UDP_SOCKET_POSIX_H_ 6 #define NET_SOCKET_UDP_SOCKET_POSIX_H_ 7 8 #include <stdint.h> 9 #include <sys/socket.h> 10 #include <sys/types.h> 11 12 #include <memory> 13 14 #include "base/logging.h" 15 #include "base/memory/raw_ptr.h" 16 #include "base/memory/scoped_refptr.h" 17 #include "base/message_loop/message_pump_for_io.h" 18 #include "base/threading/thread_checker.h" 19 #include "net/base/address_family.h" 20 #include "net/base/completion_once_callback.h" 21 #include "net/base/io_buffer.h" 22 #include "net/base/ip_endpoint.h" 23 #include "net/base/net_export.h" 24 #include "net/base/network_handle.h" 25 #include "net/log/net_log_with_source.h" 26 #include "net/socket/datagram_socket.h" 27 #include "net/socket/diff_serv_code_point.h" 28 #include "net/socket/socket_descriptor.h" 29 #include "net/socket/socket_tag.h" 30 #include "net/socket/udp_socket_global_limits.h" 31 #include "net/traffic_annotation/network_traffic_annotation.h" 32 33 namespace net { 34 35 class IPAddress; 36 class NetLog; 37 struct NetLogSource; 38 class SocketTag; 39 40 class NET_EXPORT UDPSocketPosix { 41 public: 42 UDPSocketPosix(DatagramSocket::BindType bind_type, 43 net::NetLog* net_log, 44 const net::NetLogSource& source); 45 46 UDPSocketPosix(DatagramSocket::BindType bind_type, 47 NetLogWithSource source_net_log); 48 49 UDPSocketPosix(const UDPSocketPosix&) = delete; 50 UDPSocketPosix& operator=(const UDPSocketPosix&) = delete; 51 52 virtual ~UDPSocketPosix(); 53 54 // Opens the socket. 55 // Returns a net error code. 56 int Open(AddressFamily address_family); 57 58 // Binds this socket to |network|. All data traffic on the socket will be sent 59 // and received via |network|. Must be called before Connect(). This call will 60 // fail if |network| has disconnected. Communication using this socket will 61 // fail if |network| disconnects. 62 // Returns a net error code. 63 int BindToNetwork(handles::NetworkHandle network); 64 65 // Connects the socket to connect with a certain |address|. 66 // Should be called after Open(). 67 // Returns a net error code. 68 int Connect(const IPEndPoint& address); 69 70 // Binds the address/port for this socket to |address|. This is generally 71 // only used on a server. Should be called after Open(). 72 // Returns a net error code. 73 int Bind(const IPEndPoint& address); 74 75 // Closes the socket. 76 void Close(); 77 78 // Copies the remote udp address into |address| and returns a net error code. 79 int GetPeerAddress(IPEndPoint* address) const; 80 81 // Copies the local udp address into |address| and returns a net error code. 82 // (similar to getsockname) 83 int GetLocalAddress(IPEndPoint* address) const; 84 85 // IO: 86 // Multiple outstanding read requests are not supported. 87 // Full duplex mode (reading and writing at the same time) is supported 88 89 // Reads from the socket. 90 // Only usable from the client-side of a UDP socket, after the socket 91 // has been connected. 92 int Read(IOBuffer* buf, int buf_len, CompletionOnceCallback callback); 93 94 // Writes to the socket. 95 // Only usable from the client-side of a UDP socket, after the socket 96 // has been connected. 97 int Write(IOBuffer* buf, 98 int buf_len, 99 CompletionOnceCallback callback, 100 const NetworkTrafficAnnotationTag& traffic_annotation); 101 102 // Reads from a socket and receive sender address information. 103 // |buf| is the buffer to read data into. 104 // |buf_len| is the maximum amount of data to read. 105 // |address| is a buffer provided by the caller for receiving the sender 106 // address information about the received data. This buffer must be kept 107 // alive by the caller until the callback is placed. 108 // |callback| is the callback on completion of the RecvFrom. 109 // Returns a net error code, or ERR_IO_PENDING if the IO is in progress. 110 // If ERR_IO_PENDING is returned, this socket takes a ref to |buf| to keep 111 // it alive until the data is received. However, the caller must keep 112 // |address| alive until the callback is called. 113 int RecvFrom(IOBuffer* buf, 114 int buf_len, 115 IPEndPoint* address, 116 CompletionOnceCallback callback); 117 118 // Sends to a socket with a particular destination. 119 // |buf| is the buffer to send. 120 // |buf_len| is the number of bytes to send. 121 // |address| is the recipient address. 122 // |callback| is the user callback function to call on complete. 123 // Returns a net error code, or ERR_IO_PENDING if the IO is in progress. 124 // If ERR_IO_PENDING is returned, this socket copies |address| for 125 // asynchronous sending, and takes a ref to |buf| to keep it alive until the 126 // data is sent. 127 int SendTo(IOBuffer* buf, 128 int buf_len, 129 const IPEndPoint& address, 130 CompletionOnceCallback callback); 131 132 // Sets the receive buffer size (in bytes) for the socket. 133 // Returns a net error code. 134 int SetReceiveBufferSize(int32_t size); 135 136 // Sets the send buffer size (in bytes) for the socket. 137 // Returns a net error code. 138 int SetSendBufferSize(int32_t size); 139 140 // Requests that packets sent by this socket not be fragment, either locally 141 // by the host, or by routers (via the DF bit in the IPv4 packet header). 142 // May not be supported by all platforms. Returns a network error code if 143 // there was a problem, but the socket will still be usable. Can not 144 // return ERR_IO_PENDING. 145 int SetDoNotFragment(); 146 147 // Requests that packets received by this socket have the ECN bit set. Returns 148 // a network error code if there was a problem. 149 int SetRecvTos(); 150 151 // If |confirm| is true, then the MSG_CONFIRM flag will be passed to 152 // subsequent writes if it's supported by the platform. 153 void SetMsgConfirm(bool confirm); 154 155 // Returns true if the socket is already connected or bound. is_connected()156 bool is_connected() const { return is_connected_; } 157 NetLog()158 const NetLogWithSource& NetLog() const { return net_log_; } 159 160 // Call this to enable SO_REUSEADDR on the underlying socket. 161 // Should be called between Open() and Bind(). 162 // Returns a net error code. 163 int AllowAddressReuse(); 164 165 // Call this to allow or disallow sending and receiving packets to and from 166 // broadcast addresses. 167 // Returns a net error code. 168 int SetBroadcast(bool broadcast); 169 170 // Sets socket options to allow the socket to share the local address to which 171 // the socket will be bound with other processes and attempt to allow all such 172 // sockets to receive the same multicast messages. Returns a net error code. 173 // 174 // Ability and requirements for different sockets to receive the same messages 175 // varies between POSIX platforms. For best results in allowing the messages 176 // to be shared, all sockets sharing the same address should join the same 177 // multicast group and interface. Also, the socket should listen to the 178 // specific multicast address rather than a wildcard address (e.g. 0.0.0.0). 179 // 180 // Should be called between Open() and Bind(). 181 int AllowAddressSharingForMulticast(); 182 183 // Joins the multicast group. 184 // |group_address| is the group address to join, could be either 185 // an IPv4 or IPv6 address. 186 // Returns a net error code. 187 int JoinGroup(const IPAddress& group_address) const; 188 189 // Leaves the multicast group. 190 // |group_address| is the group address to leave, could be either 191 // an IPv4 or IPv6 address. If the socket hasn't joined the group, 192 // it will be ignored. 193 // It's optional to leave the multicast group before destroying 194 // the socket. It will be done by the OS. 195 // Returns a net error code. 196 int LeaveGroup(const IPAddress& group_address) const; 197 198 // Sets interface to use for multicast. If |interface_index| set to 0, 199 // default interface is used. 200 // Should be called before Bind(). 201 // Returns a net error code. 202 int SetMulticastInterface(uint32_t interface_index); 203 204 // Sets the time-to-live option for UDP packets sent to the multicast 205 // group address. The default value of this option is 1. 206 // Cannot be negative or more than 255. 207 // Should be called before Bind(). 208 // Returns a net error code. 209 int SetMulticastTimeToLive(int time_to_live); 210 211 // Sets the loopback flag for UDP socket. If this flag is true, the host 212 // will receive packets sent to the joined group from itself. 213 // The default value of this option is true. 214 // Should be called before Bind(). 215 // Returns a net error code. 216 // 217 // Note: the behavior of |SetMulticastLoopbackMode| is slightly 218 // different between Windows and Unix-like systems. The inconsistency only 219 // happens when there are more than one applications on the same host 220 // joined to the same multicast group while having different settings on 221 // multicast loopback mode. On Windows, the applications with loopback off 222 // will not RECEIVE the loopback packets; while on Unix-like systems, the 223 // applications with loopback off will not SEND the loopback packets to 224 // other applications on the same host. See MSDN: http://goo.gl/6vqbj 225 int SetMulticastLoopbackMode(bool loopback); 226 227 // Sets the differentiated services flags on outgoing packets. May not 228 // do anything on some platforms. 229 // Returns a net error code. 230 int SetDiffServCodePoint(DiffServCodePoint dscp); 231 232 // Requests that packets sent by this socket have the DSCP and/or ECN 233 // bits set. Returns a network error code if there was a problem. If 234 // DSCP_NO_CHANGE or ECN_NO_CHANGE are set, will preserve those parts of 235 // the original setting. 236 // ECN values other than ECN_DEFAULT must not be used outside of tests, 237 // without appropriate congestion control. 238 int SetTos(DiffServCodePoint dscp, EcnCodePoint ecn); 239 240 // Sets IPV6_V6ONLY on the socket. If this flag is true, the socket will be 241 // restricted to only IPv6; false allows both IPv4 and IPv6 traffic. 242 int SetIPv6Only(bool ipv6_only); 243 244 // Exposes the underlying socket descriptor for testing its state. Does not 245 // release ownership of the descriptor. SocketDescriptorForTesting()246 SocketDescriptor SocketDescriptorForTesting() const { return socket_; } 247 248 // Resets the thread to be used for thread-safety checks. 249 void DetachFromThread(); 250 251 // Apply |tag| to this socket. 252 void ApplySocketTag(const SocketTag& tag); 253 254 // Enables experimental optimization. This method should be called 255 // before the socket is used to read data for the first time. enable_experimental_recv_optimization()256 void enable_experimental_recv_optimization() { 257 DCHECK_EQ(kInvalidSocket, socket_); 258 experimental_recv_optimization_enabled_ = true; 259 } 260 261 // Sets iOS Network Service Type for option SO_NET_SERVICE_TYPE. 262 int SetIOSNetworkServiceType(int ios_network_service_type); 263 264 // Takes ownership of `socket`, which should be a socket descriptor opened 265 // with the specified address family. The socket should only be created but 266 // not bound or connected to an address. 267 int AdoptOpenedSocket(AddressFamily address_family, int socket); 268 get_multicast_interface_for_testing()269 uint32_t get_multicast_interface_for_testing() { 270 return multicast_interface_; 271 } get_msg_confirm_for_testing()272 bool get_msg_confirm_for_testing() { return sendto_flags_; } get_experimental_recv_optimization_enabled_for_testing()273 bool get_experimental_recv_optimization_enabled_for_testing() { 274 return experimental_recv_optimization_enabled_; 275 } 276 GetLastTos()277 DscpAndEcn GetLastTos() const { return TosToDscpAndEcn(last_tos_); } 278 279 private: 280 enum SocketOptions { 281 SOCKET_OPTION_MULTICAST_LOOP = 1 << 0 282 }; 283 284 class ReadWatcher : public base::MessagePumpForIO::FdWatcher { 285 public: ReadWatcher(UDPSocketPosix * socket)286 explicit ReadWatcher(UDPSocketPosix* socket) : socket_(socket) {} 287 288 ReadWatcher(const ReadWatcher&) = delete; 289 ReadWatcher& operator=(const ReadWatcher&) = delete; 290 291 // MessagePumpForIO::FdWatcher methods 292 293 void OnFileCanReadWithoutBlocking(int /* fd */) override; 294 OnFileCanWriteWithoutBlocking(int)295 void OnFileCanWriteWithoutBlocking(int /* fd */) override {} 296 297 private: 298 const raw_ptr<UDPSocketPosix> socket_; 299 }; 300 301 class WriteWatcher : public base::MessagePumpForIO::FdWatcher { 302 public: WriteWatcher(UDPSocketPosix * socket)303 explicit WriteWatcher(UDPSocketPosix* socket) : socket_(socket) {} 304 305 WriteWatcher(const WriteWatcher&) = delete; 306 WriteWatcher& operator=(const WriteWatcher&) = delete; 307 308 // MessagePumpForIO::FdWatcher methods 309 OnFileCanReadWithoutBlocking(int)310 void OnFileCanReadWithoutBlocking(int /* fd */) override {} 311 312 void OnFileCanWriteWithoutBlocking(int /* fd */) override; 313 314 private: 315 const raw_ptr<UDPSocketPosix> socket_; 316 }; 317 318 void DoReadCallback(int rv); 319 void DoWriteCallback(int rv); 320 void DidCompleteRead(); 321 void DidCompleteWrite(); 322 323 // Handles stats and logging. |result| is the number of bytes transferred, on 324 // success, or the net error code on failure. On success, LogRead takes in a 325 // sockaddr and its length, which are mandatory, while LogWrite takes in an 326 // optional IPEndPoint. 327 void LogRead(int result, 328 const char* bytes, 329 socklen_t addr_len, 330 const sockaddr* addr); 331 void LogWrite(int result, const char* bytes, const IPEndPoint* address); 332 333 // Same as SendTo(), except that address is passed by pointer 334 // instead of by reference. It is called from Write() with |address| 335 // set to nullptr. 336 int SendToOrWrite(IOBuffer* buf, 337 int buf_len, 338 const IPEndPoint* address, 339 CompletionOnceCallback callback); 340 341 int InternalConnect(const IPEndPoint& address); 342 343 // Reads data from a UDP socket. Depending whether the socket is connected or 344 // not, the method delegates the call to InternalRecvFromConnectedSocket() 345 // or InternalRecvFromNonConnectedSocket() respectively. 346 // For proper detection of truncated reads, the |buf_len| should always be 347 // one byte longer than the expected maximum packet length. 348 int InternalRecvFrom(IOBuffer* buf, int buf_len, IPEndPoint* address); 349 350 // A more efficient implementation of the InternalRecvFrom() method for 351 // reading data from connected sockets. Internally the method uses the read() 352 // system call. 353 int InternalRecvFromConnectedSocket(IOBuffer* buf, 354 int buf_len, 355 IPEndPoint* address); 356 357 // An implementation of the InternalRecvFrom() method for reading data 358 // from non-connected sockets. Internally the method uses the recvmsg() 359 // system call. 360 int InternalRecvFromNonConnectedSocket(IOBuffer* buf, 361 int buf_len, 362 IPEndPoint* address); 363 int InternalSendTo(IOBuffer* buf, int buf_len, const IPEndPoint* address); 364 365 // Applies |socket_options_| to |socket_|. Should be called before 366 // Bind(). 367 int SetMulticastOptions(); 368 int DoBind(const IPEndPoint& address); 369 // Binds to a random port on |address|. 370 int RandomBind(const IPAddress& address); 371 372 // Sets `socket_hash_` and `tag_` on opened `socket_`. 373 int ConfigureOpenedSocket(); 374 375 int socket_; 376 377 // Hash of |socket_| to verify that it is not corrupted when calling close(). 378 // Used to debug https://crbug.com/906005. 379 // TODO(crbug.com/41426706): Remove this once the bug is fixed. 380 int socket_hash_ = 0; 381 382 int addr_family_ = 0; 383 bool is_connected_ = false; 384 385 // Bitwise-or'd combination of SocketOptions. Specifies the set of 386 // options that should be applied to |socket_| before Bind(). 387 int socket_options_ = SOCKET_OPTION_MULTICAST_LOOP; 388 389 // Flags passed to sendto(). 390 int sendto_flags_ = 0; 391 392 // Multicast interface. 393 uint32_t multicast_interface_ = 0; 394 395 // Multicast socket options cached for SetMulticastOption. 396 // Cannot be used after Bind(). 397 int multicast_time_to_live_ = 1; 398 399 // How to do source port binding, used only when UDPSocket is part of 400 // UDPClientSocket, since UDPServerSocket provides Bind. 401 DatagramSocket::BindType bind_type_; 402 403 // These are mutable since they're just cached copies to make 404 // GetPeerAddress/GetLocalAddress smarter. 405 mutable std::unique_ptr<IPEndPoint> local_address_; 406 mutable std::unique_ptr<IPEndPoint> remote_address_; 407 408 // The socket's posix wrappers 409 base::MessagePumpForIO::FdWatchController read_socket_watcher_; 410 base::MessagePumpForIO::FdWatchController write_socket_watcher_; 411 412 // The corresponding watchers for reads and writes. 413 ReadWatcher read_watcher_; 414 WriteWatcher write_watcher_; 415 416 // The buffer used by InternalRead() to retry Read requests 417 scoped_refptr<IOBuffer> read_buf_; 418 int read_buf_len_ = 0; 419 raw_ptr<IPEndPoint> recv_from_address_ = nullptr; 420 421 // The buffer used by InternalWrite() to retry Write requests 422 scoped_refptr<IOBuffer> write_buf_; 423 int write_buf_len_ = 0; 424 std::unique_ptr<IPEndPoint> send_to_address_; 425 426 // External callback; called when read is complete. 427 CompletionOnceCallback read_callback_; 428 429 // External callback; called when write is complete. 430 CompletionOnceCallback write_callback_; 431 432 NetLogWithSource net_log_; 433 434 // Network that this socket is bound to via BindToNetwork(). 435 handles::NetworkHandle bound_network_; 436 437 // Current socket tag if |socket_| is valid, otherwise the tag to apply when 438 // |socket_| is opened. 439 SocketTag tag_; 440 441 // If set to true, the socket will use an optimized experimental code path. 442 // By default, the value is set to false. To use the optimization, the 443 // client of the socket has to opt-in by calling the 444 // enable_experimental_recv_optimization() method. 445 bool experimental_recv_optimization_enabled_ = false; 446 447 // Manages decrementing the global open UDP socket counter when this 448 // UDPSocket is destroyed. 449 OwnedUDPSocketCount owned_socket_count_; 450 451 // The last TOS byte received on the socket. 452 uint8_t last_tos_ = 0; 453 454 THREAD_CHECKER(thread_checker_); 455 }; 456 457 } // namespace net 458 459 #endif // NET_SOCKET_UDP_SOCKET_POSIX_H_ 460