// Copyright 2016 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.modular.internal;

using fuchsia.io;
using fuchsia.sys;
using fuchsia.ui.views;

/// The basemgr application (there is no `Basemgr` service) requests
/// an instance of this service in order to launch and display a `Sessionmgr`.
@discoverable // Created by sessionmgr application.
protocol Sessionmgr {
    /// Launches a sessionmgr instance identified by a unique device-local
    /// `session_id`. The uniqueness of `session_id` must be guaranteed by the
    /// caller, because `sessionmgr` creates an Environment namespace with the
    /// given `session_id`, and this will crash if we try to create an
    /// environment with a pre-existing name, because the services sessionmgr
    /// tries to access won't be available.
    ///
    /// `additional_services_for_agents` is currently used by `basemgr` to
    /// expose specified services from CFv2 components to `sessionmgr` so they
    /// can be used by CFv1 components.
    ///
    /// `services_from_sessionmgr` is a handle to a subdirectory
    /// (`/svc_from_v1_sessionmgr`) in the caller's (basemgr's) outgoing
    /// directory, which should be populated by sessionmgr with services from
    /// CFv1 components (such as agent services and modular APIs like
    /// PuppetMaster) so they can also be used by CFv2 components hosted by
    /// basemgr.
    ///
    /// `view_creation_token` is a token for the Flatland view that is created
    /// by the session shell launched by sessionmgr, and presented by basemgr
    /// as the root view.
    ///
    /// This should be called when basemgr uses Flatland to present the
    /// root view.
    Initialize(resource struct {
        session_id string;
        session_context client_end:SessionContext;
        additional_services_for_agents fuchsia.sys.ServiceList;
        services_from_sessionmgr server_end:fuchsia.io.Directory;
        view_creation_token fuchsia.ui.views.ViewCreationToken;
    });
    /// Launches sessionmgr. See `Initialize`.
    ///
    /// `view_token`, `control_ref`, and `view_ref` are used to create the Gfx
    /// session shell view, passed to the session shell component launched
    /// by sessionmgr, and presented by basemgr as the root view.
    ///
    /// This should be called when basemgr uses Gfx to present the root view.
    InitializeLegacy(resource struct {
        session_id string;
        session_context client_end:SessionContext;
        additional_services_for_agents fuchsia.sys.ServiceList;
        services_from_sessionmgr server_end:fuchsia.io.Directory;
        view_token fuchsia.ui.views.ViewToken;
        control_ref fuchsia.ui.views.ViewRefControl;
        view_ref fuchsia.ui.views.ViewRef;
    });
    /// Launches sessionmgr. See `Initialize`.
    ///
    /// sessionmgr does not receive a view through this method. `use_flatland`
    /// indicates if Flatland protocol should be used instead of Gfx.
    ///
    /// This should be called when using a v2 session shell component,
    /// launched by basemgr, instead of a v1 shell launched by sessionmgr.
    /// In this case, basemgr presents the shell's view directly.
    InitializeWithoutView(resource struct {
        session_id string;
        session_context client_end:SessionContext;
        additional_services_for_agents fuchsia.sys.ServiceList;
        services_from_sessionmgr server_end:fuchsia.io.Directory;
        use_flatland bool;
    });
};

/// This interface is provided by basemgr to `Sessionmgr`.
protocol SessionContext {
    /// Restarts the session.
    Restart();

    /// Restarts the session due to an unrecoverable error. This may reboot the
    /// device.
    RestartDueToCriticalFailure();
};
