// 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.hardware.display;

using fuchsia.sysmem;
using zx;

// Invalid id for displays, images, and events.
const uint64 INVALID_DISP_ID = 0;

enum VirtconMode : uint8 {
    INACTIVE = 0; // the virtcon is never visible.
    FALLBACK = 1; // the virtcon is visible if there is no primary client.
    FORCED = 2; // the virtcon is visible even if there is a primary client.
};

// A display mode configuration.
struct Mode {
    // Resolution in pixels.
    uint32 horizontal_resolution;
    uint32 vertical_resolution;
    // Vertical refresh rate in units of (Hz / 100).
    uint32 refresh_rate_e2;

    // Bitfield of flags defined below which further specify the mode.
    uint32 flags;
};

// === Mode flags ===

// Flag for interlaced display modes.
const int32 MODE_INTERLACED = 0x1;

// Info about valid cursor configurations.
struct CursorInfo {
    // The width and height of the cursor configuration, in pixels.
    uint32 width;
    uint32 height;

    uint32 pixel_format;
};

const uint32 IDENTIFIER_MAX_LEN = 128;

// Info contains the information about a particular attached display.
struct Info {
    uint64 id;

    // Modes supported by the attached display. The first entry is the
    // preferred mode.
    vector<Mode>:MAX modes;
    // zx_pixel_format_t constants supported by the attached display. The
    // first entry is the preferred mode.
    vector<uint32>:MAX pixel_format;

    // A list of cursor configurations most likely to be accepted by the
    // driver. Maybe be empty if there is no hardware support for cursors.
    //
    // The driver may reject some of these configurations in some
    // circumstances, and it may accept other configurations, but at least
    // one of these configurations should be valid at most times.
    vector<CursorInfo>:MAX cursor_configs;

    string:IDENTIFIER_MAX_LEN manufacturer_name;
    string:IDENTIFIER_MAX_LEN monitor_name;
    string:IDENTIFIER_MAX_LEN monitor_serial;

    /// Physical horizontal size in millimeters.
    /// If this value is not available, set to a best guess value and set the flag
    uint32 horizontal_size_mm;
    /// Physical vertical size in millimeters
    /// If this value is not available, set to a best guess value and set the flag
    uint32 vertical_size_mm;
    /// This flag is set if fallback horizontal and vertical sizes were used as opposed
    /// to actual values reported by the display.
    bool using_fallback_size;
};

// An ImageConfig accompanies image data and defines how to interpret that data.
struct ImageConfig {
    // The width and height of the image in pixels.
    uint32 width;
    uint32 height;

    // A zx_pixel_format_t constant that defines the pixel format of the data.
    uint32 pixel_format;

    // Type conveys information about what is providing the pixel data. If this
    // is not TYPE_SIMPLE, it is up to the driver and image producer to
    // agree on the meaning of the value through some mechanism outside the scope
    // of this API.
    uint32 type = TYPE_SIMPLE;
};
const uint32 TYPE_SIMPLE = 0;
// Intentionally left some gap between Simple and Capture types.
const uint32 TYPE_CAPTURE = 10; //The image is used for capture

// Rotations are applied counter-clockwise, and are applied before reflections.
enum Transform : uint8 {
    IDENTITY = 0;
    REFLECT_X = 1;
    REFLECT_Y = 2;
    ROT_90 = 3;
    ROT_180 = 4;
    ROT_270 = 5;
    ROT_90_REFLECT_X = 6;
    ROT_90_REFLECT_Y = 7;
};

enum AlphaMode : uint8 {
    // Alpha is disabled for the plane (default).
    DISABLE = 0;
    // Plane alpha is premultiplied.
    PREMULTIPLIED = 1;
    // Hardware should multiply the alpha and color channels when blending.
    HW_MULTIPLY = 2;
};

struct Frame {
    // (x_pos, y_pos) specifies the position of the upper-left corner
    // of the frame.
    uint32 x_pos;
    uint32 y_pos;
    uint32 width;
    uint32 height;
};

enum ClientCompositionOpcode : uint8 {
    // The client should convert the corresponding layer to a primary layer.
    CLIENT_USE_PRIMARY = 0;
    // The client should compose all layers with CLIENT_MERGE_BASE and CLIENT_MERGE_SRC
    // into a new, single primary layer at the CLIENT_MERGE_BASE layer's z-order. The
    // driver must accept a fullscreen layer with the default pixel format, but may
    // accept other layer parameters.
    //
    // CLIENT_MERGE_BASE will only be set on one layer per display.
    CLIENT_MERGE_BASE = 1;
    // See CLIENT_MERGE_BASE.
    CLIENT_MERGE_SRC = 2;
    // The client should provide a new image produced by scaling the source image
    // such that the dimensions of the new image's src_frame and dest_frame are
    // equal to the dimensions of the current image's dest_frame.
    CLIENT_FRAME_SCALE = 3;
    // The client should provide a new image produced by clipping the source image
    // to the region specified by src_frame.
    CLIENT_SRC_FRAME = 4;
    // The client should provide a new image produced by applying the desired
    // transformation, so that TRANSFORM_IDENTITY can be specified.
    CLIENT_TRANSFORM = 5;
    // The client should apply the color conversion itself.
    CLIENT_COLOR_CONVERSION = 6;
    // The client should apply the alpha itself.
    CLIENT_ALPHA = 7;
    // The client cannot control the display gamma, and must accept
    // the uncalibrated output. Clients are expected to produce linear
    // buffers, and as such they cannot perform software gamma
    // correction.
    CLIENT_GAMMA = 8;
};

enum ConfigResult : uint32 {
    OK = 0;
    // The requested layer configuration is invalid.
    INVALID_CONFIG = 1;
    // The requested layer configuration cannot be supported by the hardware. See
    // CheckConfig struct for mode details.
    UNSUPPORTED_CONFIG = 2;
    // The number of requested displays cannot be supported.
    TOO_MANY_DISPLAYS = 3;
    // The hardware cannot support the requested modes for the displays. The client
    // should try a different set of displays or display modes.
    UNSUPPORTED_DISPLAY_MODES = 4;
};

struct ClientCompositionOp {
    /// display_id and layer_id uniquely identify the subject of the
    /// opcode.
    uint64 display_id;
    /// layer_id is 0 for whole-display issues like unsupported color
    /// conversion and gamma tables.
    uint64 layer_id;
    ClientCompositionOpcode opcode;
};

resource struct DisplayFence {
    /// The internal event object to signal.
    zx.handle:EVENT event;

    /// A bitmap indicating the scope of displays the event will affect.
    /// Each bit in `displays` represents a display in an array defined
    /// elsewhere (e.g. for ApplyConfig2(), the array is `display_ids`.)
    uint64 displays;
};

/// Maximum number of `displays` supported in an ApplyConfig2() call.
const uint64 APPLY_CONFIG_MAX_DISPLAYS = 32;

/// Maximum number of `signal_fences` supported in an ApplyConfig2() call.
const uint64 APPLY_CONFIG_MAX_SIGNAL_FENCES = 32;

/// Provider for display controllers.
///
/// The driver supports two simultaneous clients - a primary client and a virtcon
/// client.  In some cases, the provider service may provide access to only one or
/// the other; if the client tries to open the other then `ZX_ERR_NOT_SUPPORTED` will
/// be returned.
[Discoverable, ForDeprecatedCBindings]
protocol Provider {
    /// Open a virtcon client. `device` should be a handle to one endpoint of a
    /// channel that (on success) will become an open connection to a new
    /// instance of a display client device. A protocol request `controller`
    /// provides an interface to the Controller for the new device. Closing the
    /// connection to `device` will also close the `controller` interface. If
    /// the display device already has a virtcon controller then this method
    /// will return `ZX_ERR_ALREADY_BOUND`.
    // TODO(fxbug.dev/33675): Once llcpp is supported in Zircon, unify `device` and
    // `controller`.
    OpenVirtconController(zx.handle:CHANNEL device, request<Controller> controller) -> (zx.status s);

    /// Open a primary client. `device` should be a handle to one endpoint of a
    /// channel that (on success) will become an open connection to a new
    /// instance of a display client device. A protocol request `controller`
    /// provides an interface to the Controller for the new device. Closing the
    /// connection to `device` will also close the `controller` interface. If
    /// the display device already has a primary controller then this method
    /// will return `ZX_ERR_ALREADY_BOUND`.
    // TODO(fxbug.dev/33675): Once llcpp is supported in Zircon, unify `device` and
    // `controller`.
    OpenController(zx.handle:CHANNEL device, request<Controller> controller) -> (zx.status s);
};

/// Interface for accessing the display hardware.
///
/// A display configuration can be separated into two parts: the layer layout and
/// the layer contents. The layout includes all parts of a configuration other
/// than the image handles. The active configuration is composed of the most
/// recently applied layout and an active image from each layer - see
/// SetLayerImage for details on how the active image is defined. Note the
/// requirement that each layer has an active image. Whenever a new active
/// configuration is available, it is immediately given to the hardware. This
/// allows the layout and each layer's contents to advance independently when
/// possible.
///
/// Performing illegal actions on the interface will result in the interface
/// being closed.
protocol Controller {
    // Event fired when displays are added or removed. This event will be fired
    // when the callback is registered if there are any connected displays.
    //
    // A display change always invalidates the current configuration. When a
    // client receives this event, they must either apply a new configuration
    // or revalidate and reapply their current configuration.
    -> OnDisplaysChanged(vector<Info>:MAX added, vector<uint64>:MAX removed);

    // Imports a VMO backed image. If tiling is not TYPE_SIMPLE, it is up to
    // the driver and client to agree on its meaning through some mechanism
    // outside the scope of this API.
    //
    // DEPRECATED: This should not be used with buffer collections - ImportImage
    // should be used instead.
    ImportVmoImage(ImageConfig image_config, zx.handle:VMO vmo, int32 offset) -> (zx.status res, uint64 image_id);

    // Imports a Buffer-Collection backed image. If tiling is not TYPE_SIMPLE,
    // it is up to the driver and client to agree on its meaning through some
    // mechanism outside the scope of this API. The ImageConfig must be
    // compatible with that passed through SetBufferCollectionConstraints on
    // the collection id.
    ImportImage(ImageConfig image_config, uint64 collection_id, uint32 index)
        -> (zx.status res, uint64 image_id);

    // Releases an image.
    //
    // It is safe to call this at any time. When an image is released, it
    // is immediately removed from any pending or active configurations,
    // and any fences associated with the image are dropped. The resources
    // associated with the image will be released as soon as the image is
    // no longer in use.
    ReleaseImage(uint64 image_id);

    /// Imports an event into the driver and associates it with the given id.
    ///
    /// It is illegal for id to be equal to INVALID_DISP_ID, and it is undefined to
    /// import one event with two different ids or to import two different events
    /// with the same id (note that ids map well to koids).
    ///
    /// If a client is reusing events, they must clear the signal
    /// before referencing the id again.
    ImportEvent(zx.handle:EVENT event, uint64 id);

    /// Releases the event imported with the given id.
    ///
    /// If any images are currently using the given event, the event
    /// will still be waited up or signaled as appropriate before its
    /// resources are released. It is an error to reuse an ID while the
    /// active config has references to it.
    ReleaseEvent(uint64 id);

    // Creates a new layer.
    //
    // Layers are not associated with a particular display, but they can only be
    // shown on at most one display at any given time.  A layer is considered in
    // use from the time it is passed to SetDisplayLayers until a subsequent
    // configuration is applied which does not include the layer or until its
    // display is removed.
    CreateLayer() -> (zx.status res, uint64 layer_id);

    // Destroys the given layer.
    //
    // It is illegal to destroy a layer which does not exist or which is in use.
    DestroyLayer(uint64 layer_id);

    /// Import a gamma table for display calibration.
    ///
    /// Each array is a quantized representation of the gamma curve for a single
    /// color channel. An input luminance in [0.0, 1.0] is mapped to an index
    /// between 0-255, and the value in the array is used as the output
    /// luminance. Rounding behavior is hardware-specific, and most often it
    /// will floor(input * 255.0), requiring an input luminance of 1.0 to get
    /// the max output luminance.
    ///
    /// It is an error to use output luminances outside of [0.0, 1.0]. Hardware
    /// drivers may either clamp such values or disconnect a client that
    /// provides invalid tables.
    ImportGammaTable(uint64 gamma_table_id,
                     array<float32>:256 r,
                     array<float32>:256 g,
                     array<float32>:256 b);

    /// Release an imported gamma table.
    ///
    /// Subsequent calls to SetDisplayGammaTable cannot reference this
    /// table. It is legal to re-use the gamma_table_id after making
    /// this call. Releasing a table while it is set on a display is
    /// safe, and will not modify the output of the display.
    ReleaseGammaTable(uint64 gamma_table_id);

    // Sets the display mode for the given display.
    //
    // It is illegal to pass a display mode which was not part of the display's Info.
    SetDisplayMode(uint64 display_id, Mode mode);

    // Set the color conversion applied to the display. The conversion is applied to
    // to each pixel according to the formula:
    //
    // (coefficients * (pixel + preoffsets)) + postoffsets
    //
    // where pixel is a column vector consisting of the pixel's 3 components.
    //
    // `coefficients` is passed in row-major order. If the first entry of an array is NaN, the
    // array is treated as the identity element for the relevant operation.
    // Hardware that support color correction generally accept a limited range of coefficient
    // values. Coefficients in the range of [-2, 2] inclusive will be accepted by most
    // hardware. The hardware driver will clamp values that are outside its accetable range.
    //
    // `preoffsets`, `postoffsets`: Clients are encourged to produce color correction values that
    // do not depend on pre and post offsets since some hardware do not have support for that.
    // For cases where pre and post offset values need to be used, the range should be limited to
    // (-1, 1) exclusive as confirmed by CheckConfig API. Values outside this range will be
    // rejected.
    //
    // Clients are encouraged to use the CheckConfig API to confirm support for correction and to
    // validate their color correction input values.
    SetDisplayColorConversion(uint64 display_id,
                              array<float32>:3 preoffsets,
                              array<float32>:9 coefficients,
                              array<float32>:3 postoffsets);

    /// Set the gamma correction table for a display.
    ///
    /// gamma_table_id must be a table registered with ImportGammaTable. It is
    /// safe to release a gamma table after using it here, and will not modify
    /// display output.
    SetDisplayGammaTable(uint64 display_id, uint64 gamma_table_id);

    // Sets which layers are on a display. The list is in increasing z-order.
    //
    // It is illegal to use a layer on multiple displays concurrently. If a layer
    // needs to be moved between displays, it must be removed from the first display's
    // pending config before being added to the second display's pending config. It
    // is also illegal to pass an invalid layer id.
    SetDisplayLayers(uint64 display_id, vector<uint64>:MAX layer_ids);

    // Configures the layer as a primary layer with no image and the default
    // config (no src_frame cropping, the identity transform, positioned in the
    // top-left corner of the composed output, and no scaling).
    //
    // See the documentation on SetLayerImage for details on how this method
    // affects the layer's contents.
    //
    // It is illegal to pass an invalid layer id.
    SetLayerPrimaryConfig(uint64 layer_id, ImageConfig image_config);

    // Sets the layer transform, scaling, and positioning.
    //
    // `src_frame` must be non-empty and must fit entirely within the source
    // image. `dest_frame` must be non-empty and must fit entirely within the
    // composed output. CheckConfig will return INVALID_CONFIG if any of these
    // conditions is violated.
    //
    // Calling this on a non-primary layer or passing an invalid transform
    // is illegal.
    SetLayerPrimaryPosition(uint64 layer_id, Transform transform, Frame src_frame, Frame dest_frame);

    // Sets the alpha mode of the plane.
    //
    // If `mode` == DISABLED, the layer is opaque and `val` is ignored.
    //
    // If `mode` == PREMULTIPLIED or HW_MULTIPLY and `val` is NaN, the alpha
    // used when blending is determined by the per-pixel alpha channel.
    //
    // If `mode` == PREMULTIPLIED or HW_MULTIPLY and `val` is not NaN, the
    // alpha used when blending is the product of `val` and any per-pixel
    // alpha. Additionally, if `mode` == PREMULTIPLIED, then the hardware
    // premultiplies the color channel with `val` before blending.
    //
    // It is illegal to call this on a non-primary layer, to pass an
    // invalid mode, or to pass a value of `val` which is not NaN or
    // in the range [0, 1].
    SetLayerPrimaryAlpha(uint64 layer_id, AlphaMode mode, float32 val);

    // Configures the layer as a cursor layer with the given config. The
    // default position is (0, 0).
    //
    // See the documentation on SetLayerImage for details on how this method
    // affects the layer's contents.
    //
    // It is illegal to call this on an invalid layer.
    SetLayerCursorConfig(uint64 layer_id, ImageConfig image_config);

    // Updates the cursor position.
    //
    // The driver will clamp x to [-cursor_width + 1, display_width - 1] and
    // will clamp y to [-cursor_height + 1, display_height - 1].
    //
    // It is illegal to call this on a non-cursor layer.
    SetLayerCursorPosition(uint64 layer_id, int32 x, int32 y);

    // Configures the layer as a color layer with the given color. The
    // color_bytes vector is little-endian and must have length appropriate
    // for the pixel format.
    //
    // It is illegal to call this on an invalid layer or for the length of
    // color_bytes to mismatch the size of the supplied format.
    SetLayerColorConfig(uint64 layer_id, uint32 pixel_format, vector<uint8>:MAX color_bytes);

    // Sets the image for the layer.
    //
    // If wait_event_id corresponds to an imported event, the driver will
    // wait for ZX_EVENT_SIGNALED on the object before presenting the image.
    //
    // If signal_event_id is valid, then the driver will signal the event with
    // ZX_EVENT_SIGNALED when the image is no longer being presented.
    //
    // A layer's active image is the most recently applied image which either has
    // no wait event or whose wait event has been signaled. Whenever a new image
    // becomes active, any older images which never became active are dropped, and
    // their signal events will be fired as soon as their wait events are
    // signaled. The driver also does not have any concept like 'target vsync',
    // meaning that if multiple images become active within one vsync period, then
    // only the last image will actually be displayed.
    //
    // By default, the driver retains an active image until a new image becomes
    // active. However, setting a layer's ImageConfig with SetLayerPrimaryConfig
    // or SetLayerCursorConfig reset the layer's active and pending images, even
    // if the new ImageConfig matches the old ImageConfig.
    //
    // An image cannot be used for multiple layers simultaneously, nor can an
    // image be given back to the display controller while it is still in use.
    // An image is considered in use when it is part of a pending configuration
    // or from when its configuration is applied until its signal_event_id is
    // signaled.
    //
    // It is illegal to call this with an invalid layer or image id, to
    // call it on a color layer, or to call it with an image and layer whose
    // ImageConfigs do not match. It is illegal to apply a configuration
    // with an image layer that has no image (note that is is not illegal to
    // validate such a configuration). It is illegal to reuse a wait event which
    // another layer that has not been presented is waiting on.
    SetLayerImage(uint64 layer_id, uint64 image_id, uint64 wait_event_id, uint64 signal_event_id);

    // Attempts to validate the current configuration.
    //
    // When CheckConfig is called, the driver will validate the pending
    // configuration. If res is UNSUPPORTED_CONFIG, then ops will be
    // non-empty.
    //
    // Most SetX operation require re-validating the configuration. The exception
    // are SetLayerCursorPosition and SetLayerImage - these operations do not
    // modify the configuration in a way which requires revalidation.
    //
    // If discard is true, the pending changes will be discarded after validation.
    CheckConfig(bool discard) -> (ConfigResult res, vector<ClientCompositionOp>:MAX ops);

    // Applies any pending changes to the current configuration. This will
    // not apply pending changes to layers which are not on any display.
    //
    // If the pending configuration cannot be applied, this call will silently
    // fail, so the client should ensure its configuration is valid with
    // CheckConfig.
    ApplyConfig();

    /// Applies any pending changes to the current configuration. This will
    /// not apply pending changes to layers which are not on any display.
    ///
    /// For each `event` in `signal_fences`, once the pending configuration is
    /// applied to and contents are displayed on all the displays in its
    /// `displays` bitmap, the fence signal will be signaled immediately.
    ///
    /// Arguments
    ///
    ///   `display_ids`:
    ///     Lists all display IDs which are used on the incoming configuration.
    ///     Each display ID represents the corresponding bit in the `display`
    ///     field of `signal_fences`.
    ///
    ///   `signal_fences`:
    ///     Stores all fence events that will be signaled once the configuration
    ///     is applied and display scopes of each event. See the definition of
    ///     `DisplayFences` for details.
    ///
    /// Error handling
    ///
    ///     If the input is invalid, for example:
    ///         - `signal_fences` contains invalid events
    ///         - `display` has bits referring to display ID `INVALID_DISP_ID`.
    ///     or the pending configuration cannot be applied, this call will
    ///     silently fail, so the client should ensure its configuration is
    ///     valid with CheckConfig().
    [Transitional]
    ApplyConfig2(
        vector<uint64>:APPLY_CONFIG_MAX_DISPLAYS display_ids,
        vector<DisplayFence>:APPLY_CONFIG_MAX_SIGNAL_FENCES signal_fences);

    // Sets whether or not vsync events will be given to this client. Defaults
    // to false.
    EnableVsync(bool enable);

    // This API is used by the client to acknowledge receipt of vsync messages.
    // The cookie sent should match the cookie received via vsync message (OnVsync).
    // A cookie can only be acknowledged once. Using invalid cookies, or previously
    // acknowledged cookies will not be accepted by the driver.
    AcknowledgeVsync(uint64 cookie);

    // Event sent for every vsync.
    //
    // display_id is the identifies the display on which the vsync occurred, and
    // timestamp indicates the time the vsync occurred. images is a (possibly
    // empty) vector of all images that were actively being displayed. cookie is a unique
    // number returned by the driver.
    // Cookie is used to acknowledge the receipt of vsync events using AcknowledgeVsync API.
    // When cookie has a value of zero, no acknowledgement is required by the client. A non-zero
    // valued cookie requires immediate acknowledgement by client. Failure to acknowledge
    // vsync events will result in driver suspending vsync event notification. All vsync
    // messages containing a non-zero cookie require acknowledgement regardless of whether
    // client has applied a (new) configuration or not (via ApplyConfig).
    // If a client fails to acknowledge vsync messages, the driver will store incoming
    // hardware-generated vsyncs in a circular buffer and send them
    // to the client once it resumes acknowledgement. Due to limited size of buffer, only the most
    // recently received vsyncs will be stored and older ones will be dropped.
    -> OnVsync(uint64 display_id, uint64 timestamp, vector<uint64>:MAX images, uint64 cookie);

    // Sets the visibility behavior of the virtcon. It is illegal to call this
    // from the primary client.
    SetVirtconMode(uint8 mode);

    // Event fired when the client gains or loses ownership of the displays.
    //
    // New clients should assume they do not have ownership of the display
    // until this event informs them otherwise.
    -> OnClientOwnershipChange(bool has_ownership);

    // Import a sysmem buffer collection token. `collection_id` must not
    // already be in use.
    ImportBufferCollection(uint64 collection_id,
                           fuchsia.sysmem.BufferCollectionToken collection_token)
        -> (zx.status res);

    // Release an imported buffer collection.
    ReleaseBufferCollection(uint64 collection_id);

    // Takes an imported buffer collection and sets the constraints
    // on it so that it can be imported with a specific config.
    SetBufferCollectionConstraints(uint64 collection_id, ImageConfig config) -> (zx.status res);

    // If the system only supports single-buffered mode with a single framebuffer, then this returns
    // that buffer and its stride. Otherwise it can return ZX_ERR_NOT_SUPPORTED.
    GetSingleBufferFramebuffer() -> (zx.status res, zx.handle:VMO? vmo, uint32 stride);

    /// Returns true if Capture is supported on the platform.
    IsCaptureSupported() -> (bool supported) error zx.status;

    /// Imports a buffer collection backed VMO into the display controller. The VMO
    /// will be used by display controller to capture the image being displayed.
    /// Returns ZX_OK along with an image_id.
    /// image_id must be used by the client to start capture and/or release
    /// resources allocated for capture.
    /// Returns ZX_ERR_NOT_SUPPORTED if controller does not support capture
    ImportImageForCapture(ImageConfig image_config, uint64 collection_id,
                          uint32 index) -> (uint64 image_id) error zx.status;

    /// Starts capture. Client must provide a valid signal_event_id and
    /// image_id. signal_event_id must have been imported into the driver
    /// using ImportEvent FIDL API. Image_id is the id from ImportImageForCapture.
    /// The client will get notified once capture is complete via signal_event_id.
    /// Returns ZX_ERR_NOT_SUPPORTED if controller does not support capture
    StartCapture(uint64 signal_event_id, uint64 image_id) -> () error zx.status;

    /// Releases resources allocated for capture.
    /// Returns ZX_ERR_NOT_SUPPORTED if controller does not support capture
    ReleaseCapture(uint64 image_id) -> () error zx.status;

    /// Set the minimum value of rgb channels. Valid range [0 255] inclusive. Returns
    /// ZX_ERR_NOT_SUPPORTED when the display hardware does not support this feature.
    /// This API is meant to address backlight bleeding that may occur on some hardware
    /// that have a specific type of panel and hardware assembly. The evolution of this
    /// API is highly hardware and product dependant and therefore as products evolve, this
    /// API may change or support for this API may become non-existent. Therefore, this
    /// API should be used with caution.
    SetMinimumRgb(uint8 minimum_rgb) -> () error zx.status;
};
