| // Copyright 2018 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. |
| |
| module network.mojom; |
| |
| import "mojo/public/mojom/base/read_only_buffer.mojom"; |
| import "services/network/public/mojom/ip_address.mojom"; |
| import "services/network/public/mojom/ip_endpoint.mojom"; |
| import "services/network/public/mojom/mutable_network_traffic_annotation_tag.mojom"; |
| |
| // Represents options that consumers can set when requesting a UDPSocket |
| // interface pointer. |
| struct UDPSocketOptions { |
| // If true, this enables SO_REUSEADDR on the underlying socket. |
| bool allow_address_reuse = false; |
| |
| // If true, allows sending and receiving packets to and from broadcast |
| // addresses. It's recommended this be used instead of SetBroadcast(), as |
| // Bind() may fail on some platforms when reusing a UDP port and broadcast |
| // is not enabled when the socket is created. |
| bool allow_broadcast = false; |
| |
| // If true, allows the socket to share the local address to which the socket |
| // will be bound with other processes and attempts to allow all such sockets |
| // to receive the same multicast messages. |
| // |
| // For best cross-platform results in allowing the messages to be shared, all |
| // sockets sharing the same address should join the same multicast group (via |
| // UDPSocket::JoinGroup()) and set the same |multicast_interface|. Also, the |
| // socket should bind to the specific multicast group address rather than a |
| // wildcard address (e.g. 0.0.0.0) on platforms where doing so is allowed. |
| bool allow_address_sharing_for_multicast = false; |
| |
| // Sets interface to use for multicast. Default value is 0, in which case the |
| // default interface is used. |
| uint32 multicast_interface = 0; |
| |
| // Sets the time-to-live option for UDP packets sent to the multicast |
| // group address. The default value of this option is 1. Cannot be more than |
| // 255. |
| uint32 multicast_time_to_live = 1; |
| |
| // Sets the loopback flag for UDP socket. If this flag is true and the socket |
| // joins a group through JoinGroup(), the socket will receive packets sent to |
| // the joined group from itself. The default value of this option is true. |
| // |
| // Note: the behavior of |SetMulticastLoopbackMode| is slightly |
| // different between Windows and Unix-like systems. The inconsistency only |
| // happens when there are more than one applications on the same host |
| // joined to the same multicast group while having different settings on |
| // multicast loopback mode. On Windows, the applications with loopback off |
| // will not RECEIVE the loopback packets; while on Unix-like systems, the |
| // applications with loopback off will not SEND the loopback packets to |
| // other applications on the same host. See MSDN: http://goo.gl/6vqbj |
| bool multicast_loopback_mode = true; |
| |
| // Sets the OS send buffer size (in bytes) for the socket. This is the |
| // SO_SNDBUF socket option. This socket option matters less for UDP socket (as |
| // compared to TCP), because in theory all UDP data written to the kernel |
| // should directly go out to the network. The kernel usually doesn't need to |
| // buffer send data. Default value is 0, in which case, OS's default value |
| // will be used. |
| int32 send_buffer_size = 0; |
| |
| // Sets the OS receive buffer size (in bytes) for the socket. This is the |
| // SO_RCVBUF socket option. The kernel allocates this much to hold the data |
| // arriving into this socket between the time when data arrives over the |
| // network and when it is read by UDPSocketReceiver. If buffer is full, |
| // new packets will be discarded. Default value is 0, in which case, OS's |
| // default value will be used. |
| int32 receive_buffer_size = 0; |
| }; |
| |
| // UDPSocket is an interface that exposes UDP socket functionalities. |
| // UDPSocketReceiver is an interface that allows consumers to consume data |
| // received by the UDPSocket. The typical flow of using the interfaces is: |
| // - Acquire a UDPSocket interface pointer and optionally supply a non-null |
| // UDPSocketReceiverPtr. If consumers are not interested in received data, a |
| // null UDPSocketReceiverPtr is acceptable. |
| // - Use either Bind() or Connect() before datagrams can be sent or received. |
| // - (optional) Invoke setters (e.g. SetBroadcast()). |
| // - Send / request to receive datagrams. Received datagrams will be delivered |
| // to the bound receiver's OnReceived() call. |
| // - Close the socket by destroying the interface pointer. |
| interface UDPSocket { |
| // Binds the address/port for this socket to |local_addr|. Caller can use port |
| // 0 to let the OS pick an available port. If |socket_options| is not null, |
| // configures the socket with the options before binding the socket. |
| // Returns net::OK and the real local address used on success and a negative |
| // net error code on failure. |
| Bind(IPEndPoint local_addr, UDPSocketOptions? socket_options) |
| => (int32 result, IPEndPoint? local_addr_out); |
| |
| // Connects the socket to |remote_addr|. This automatically binds the socket |
| // to an available local port, so this cannot be used with Bind(). |
| // If |socket_options| is not null, configures the socket with the options |
| // before connecting the socket. |
| // The address family of the local socket will be of the same |
| // AddressFamily as |remote_addr|. Returns net::OK and the local address of |
| // socket on success. Subsequent packets received will be from |remote_addr|. |
| // Returns a negative net error code on failure. |
| Connect(IPEndPoint remote_addr, UDPSocketOptions? socket_options) => |
| (int32 result, IPEndPoint? local_addr_out); |
| |
| // Allows or disallows sending and receiving packets to and from broadcast |
| // addresses. Returns a net error code. Should only be called after Bind(). |
| SetBroadcast(bool broadcast) => (int32 result); |
| |
| // Sets the OS send buffer size (in bytes) for the socket. Overwrites any |
| // previously set value. Returns a net error code. |
| // See |UDPSocketOptions::send_buffer_size| for more information. |
| SetSendBufferSize(int32 send_buffer_size) => (int32 result); |
| |
| // Sets the OS receive buffer size (in bytes) for the socket. Overwrites any |
| // previously set value. Returns a net error code. |
| // See |UDPSocketOptions::receive_buffer_size| for more information. |
| SetReceiveBufferSize(int32 receive_buffer_size) => (int32 result); |
| |
| // Joins a multicast group. |group_address| is the group address to join, |
| // could be either an IPv4 or IPv6 address. Returns a net error code. |
| // See RFC 1112 for details on multicast. |
| JoinGroup(IPAddress group_address) => (int32 result); |
| |
| // Leaves the multicast group. |group_address| is the group address to leave, |
| // could be either an IPv4 or IPv6 address. If the socket hasn't joined the |
| // group, this call will be ignored. It's optional to leave the multicast |
| // group before destroying the socket. Returns a net error code. |
| LeaveGroup(IPAddress group_address) => (int32 result); |
| |
| // Notifies that the receiver is ready to accept |number| of datagrams. |
| // Correspondingly, OnReceived() of the UDPSocketReceiver interface will be |
| // called |number| times (errors also count), unless the connection is closed |
| // before that. The implementation may return net::ERR_INSUFFICIENT_RESOURCES |
| // in an OnReceived() callback if the service doesn't have enough resource to |
| // complete the operation. For example, if the implementation queues the |
| // requests internally, net::ERR_INSUFFICIENT_RESOURCES can be returned if the |
| // queue doesn't have any space to accept new ReceiveMore(). |
| // |
| // It is allowed to call this method again before the previous request is |
| // completely satisfied. For example: |
| // service->ReceiveMore(3); |
| // ... |
| // // OnReceived() is called. |
| // // OnReceived() is called. |
| // ... |
| // service->ReceiveMore(3); |
| // // The client expects 4 more calls to OnReceived(). |
| // |
| // Please note that how ReceiveMore() is used will affect performance |
| // significantly. For example: |
| // // Approach 1: |
| // service->ReceiveMore(3); |
| // // OnReceived() is called. |
| // // OnReceived() is called. |
| // // OnReceived() is called. |
| // |
| // // Approach 2: |
| // service->ReceiveMore(1); |
| // // OnReceived() is called. |
| // service->ReceiveMore(1); |
| // // OnReceived() is called. |
| // service->ReceiveMore(1); |
| // // OnReceived() is called. |
| // |
| // It is very likely that approach 1 will perform better than approach 2, |
| // because in approach 2 getting every datagram takes at least the time of a |
| // round trip to the service side. Default buffer size of 64KiB will be |
| // allocated to receive each datagram. |
| ReceiveMore(uint32 num_additional_datagrams); |
| |
| // Same as ReceiveMore(), but with an ability to set the buffer size used for |
| // receiving each datagram. Note that |buffer_size| is the application-side |
| // buffer which is different from UDPSocketOptions::receive_buffer_size which |
| // is the OS-side buffer. |buffer_size| larger than 64KiB will be capped at |
| // 64KiB as the limit on data length of a IPv4 UDP packet is 65,507 and 65,535 |
| // for IPv6. |
| ReceiveMoreWithBufferSize( |
| uint32 num_additional_datagrams, uint32 buffer_size); |
| |
| // Sends data to a particular destination, |dest_addr|. Should only be used |
| // after Bind(). There is currently no limit on the size of |data|, other |
| // than the restrictions on datagram size specified in the IP layer (e.g. |
| // 65507 bytes for IPv4) . Consumers need to be aware that sending data in |
| // larger chunks will result in higher memory usage. Upon successfully handing |
| // the data to the OS, |result| is net::OK. On failure, it is a network error |
| // code, including (but not limited to): |
| // - net::ERR_INSUFFICIENT_RESOURCES: The service doesn't have |
| // sufficient resource to complete the operation. When this happens, the |
| // requests will be failed quickly (which might happen before the completion |
| // of requests that were sent earlier). |
| SendTo(IPEndPoint dest_addr, |
| mojo_base.mojom.ReadOnlyBuffer data, |
| MutableNetworkTrafficAnnotationTag traffic_annotation) |
| => (int32 result); |
| |
| // Same as SendTo(), except this method sends data to the destination |
| // specified in an earlier Connect(). This method should only be called after |
| // a successful Connect(). |
| Send(mojo_base.mojom.ReadOnlyBuffer data, |
| MutableNetworkTrafficAnnotationTag traffic_annotation) |
| => (int32 result); |
| |
| // Closes the socket. Connect() or Bind() can be used after Close(). |
| Close(); |
| }; |
| |
| // An interface the consumers of UDPSocket can implement to listen for incoming |
| // packets. This interface is to be used together when requesting a UDPSocket. |
| interface UDPSocketReceiver { |
| // Invoked when data is received. |
| // - When UDPSocket is used with Bind(): |
| // On success, |result| is net::OK. |src_addr| indicates the address of the |
| // sender. |data| contains the received data. |
| // On failure, |result| is a negative network error code. |data| is null. |
| // |src_addr| might be null. |
| // - When UDPSocket is used with Connect(): |
| // |src_addr| is always null. Data are always received from the remote |
| // address specified in Connect(). |
| // On success, |result| is net::OK. |data| contains the received data. |
| // On failure, |result| is a negative network error code. |data| is null. |
| // |
| // Note that in both cases, |data| can be an empty buffer when |result| is |
| // net::OK, which indicates a zero-byte payload. |
| OnReceived(int32 result, |
| IPEndPoint? src_addr, |
| mojo_base.mojom.ReadOnlyBuffer? data); |
| }; |