// Copyright 2018 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

library fuchsia.overnet;

// Overnet forms a mesh network of peer devices which can proxy some Zircon objects between
// said devices.

using fuchsia.overnet.protocol;

/// Interfaces applicable to consuming services from other devices
[FragileBase, Discoverable]
protocol ServiceConsumer {
    /// Returns a list of all peers that are connected to this Overnet.
    /// If this list has not been updated since the last call to this method, it waits until
    /// new data is available.
    /// Concurrent calls to ListPeers will result in channel closure.
    ListPeers() -> (vector<Peer>:MAX peers);
    /// Connect `chan` to some external service on `node` with name `service_name`.
    ConnectToService(fuchsia.overnet.protocol.NodeId node,
                     string:fuchsia.overnet.protocol.MAX_SERVICE_NAME_LENGTH service_name,
                     handle<channel> chan);
};

/// Interfaces applicable to sharing services with ServiceConsumer's
[FragileBase, Discoverable]
protocol ServicePublisher {
    /// Register a new service to be exported by Overnet.
    /// If an existing service has the same `service_name`, it's replaced by this service.
    PublishService(string:fuchsia.overnet.protocol.MAX_SERVICE_NAME_LENGTH service_name,
                   ServiceProvider provider);
};

/// Interfaces applicable to controlling an Overnet mesh
[Discoverable]
protocol MeshController {
    /// Attach a socket as a new link.
    AttachSocketLink(handle<socket> socket, SocketLinkOptions options);
};

/// Legacy Overnet interface for applications that did not distinguish between ServiceConsumer and
/// ServicePublisher
[Discoverable, Deprecated]
protocol Overnet {
    compose ServiceConsumer;
    compose ServicePublisher;
};

/// A ServiceProvider is a factory for one service.
protocol ServiceProvider {
    /// Connect `chan` to the service (called in response to Overnet.ConnectToService).
    /// `info` provides additional data about the connection request.
    ConnectToService(handle<channel> chan, ConnectionInfo info);
};

/// A `Peer` describes one device on the Overnet mesh.
struct Peer {
    /// The address of the peer on the Overnet mesh.
    fuchsia.overnet.protocol.NodeId id;
    /// A special peer is returned for this device, and is marked with `is_self` true.
    bool is_self;
    /// A description of the peer (includes, for example, a service list).
    fuchsia.overnet.protocol.PeerDescription description;
};

/// Extra arguments for attaching a socket link to an Overnet mesh.
table SocketLinkOptions {
    /// A label that might be used for debugging purposes.
    1: string:32 connection_label;
};

/// Information provided to a ServiceProvider about an incoming connection.
table ConnectionInfo {
    /// The peer address initiating this connection.
    1: fuchsia.overnet.protocol.NodeId peer;
};
