// Copyright 2014 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 media.mojom;

import "media/mojo/mojom/decryptor.mojom";
import "media/mojo/mojom/media_types.mojom";
import "url/mojom/url.mojom";
import "mojo/public/mojom/base/unguessable_token.mojom";

// See media::EmeInitDataType.
[Native]
enum EmeInitDataType;

// See media::CdmSessionType
[Native]
enum CdmSessionType;

// See media::CdmMessageType
[Native]
enum CdmMessageType;

// See media::CdmKeyInformation::KeyStatus
enum CdmKeyStatus {
    USABLE,
    INTERNAL_ERROR,
    EXPIRED,
    OUTPUT_RESTRICTED,
    OUTPUT_DOWNSCALED,
    KEY_STATUS_PENDING,
    RELEASED,
};

// See media::HdcpVersion
[Native]
enum HdcpVersion;

// See media::CdmConfig
[Native]
struct CdmConfig;

// Transport layer of media::CdmPromise (see media/base/cdm_promise.h).
// - When |success| is true, the promise is resolved and all other fields should
//   be ignored.
// - When |success| is false, the promise is rejected with |exception|,
//   |system_code| and |error_message|.
struct CdmPromiseResult {
  // See media::CdmPromise::Exception
  [Native]
  enum Exception;

  bool success;
  Exception exception;
  uint32 system_code;
  string error_message;
};

// Transport layer of media::CdmKeyInformation (see
// media/base/cdm_key_information.h). It is used to specify a key_id and it's
// associated status.
struct CdmKeyInformation {
  array<uint8> key_id;
  CdmKeyStatus status;
  uint32 system_code;
};

// An interface that represents a CDM in the Encrypted Media Extensions (EME)
// spec (https://w3c.github.io/encrypted-media/).
// - Process Model: For security reason, the CDM is running in its own process
// as the CDM contains untrusted code and handles arbitrary data. The exact
// process model varies on various platforms. For example, on desktop, the CDM
// runs in a CDM (utility) process. On Android, the CDM runs in the GPU process.
// The client of the CDM is MojoCdm, which runs in the render process.
// - Session ID: Passed as `session_id` in some methods, it is a unique string
// identifier generated by the CDM that can be used to identify CDM sessions.
// A ContentDecryptionModule can manage mutilple sessions per the EME spec. See
// https://www.w3.org/TR/encrypted-media/#session-id.
// - Also see media/base/content_decryption_module.h and media/mojo/README.md.
interface ContentDecryptionModule {
  // Sets ContentDecryptionModuleClient. Must be called before any other calls.
  // Use associated interface to ensure ordering, e.g. events on the client
  // interface and promise fulfillment.
  SetClient(pending_associated_remote<ContentDecryptionModuleClient> client);

  // Provides a server certificate to be used to encrypt messages to the
  // license server.
  SetServerCertificate(array<uint8> certificate_data)
      => (CdmPromiseResult result);

  // Gets the key status if there's a hypothetical key that requires the
  // |min_hdcp_version|. Resolve the |promise| with the |key_status| after the
  // operation completes. Reject the |promise| if this operation is not
  // supported or unexpected error happened.
  GetStatusForPolicy(HdcpVersion min_hdcp_version)
      => (CdmPromiseResult result, CdmKeyStatus key_status);

  // Creates a session with the |init_data_type|, |init_data| and |session_type|
  // provided. If |result.success| is false, the output |session_id| will be
  // empty.
  CreateSessionAndGenerateRequest(CdmSessionType session_type,
                                  EmeInitDataType init_data_type,
                                  array<uint8> init_data)
      => (CdmPromiseResult result, string session_id);

  // Loads the session associated with |session_id| and |session_type|.
  // Combinations of |result.success| and |session_id| means:
  //   (true, non-empty) : Session successfully loaded.
  //   (true, empty) : Session not found.
  //   (false, non-empty): N/A; this combination is not allowed.
  //   (false, empty) : Unexpected error. See other fields in |result|.
  LoadSession(CdmSessionType session_type, string session_id)
      => (CdmPromiseResult result, string session_id);

  // Updates a session specified by |session_id| with |response|.
  UpdateSession(string session_id, array<uint8> response)
      => (CdmPromiseResult result);

  // Closes the session specified by |session_id|.
  CloseSession(string session_id) => (CdmPromiseResult result);

  // Removes stored session data associated with the active session specified by
  // |session_id|.
  RemoveSession(string session_id) => (CdmPromiseResult result);
};

// Session callbacks. The implementation is MojoCdm that runs in the render
// process. The caller is the remote CDM (mojom::ContentDecryptionModule). See
// comments above for more details on CDM process model and session ID.
// Also see media/base/content_decryption_module.h and media/mojo/README.md.
interface ContentDecryptionModuleClient {
  // Called when the CDM needs to queue a message event to the session object.
  // See http://w3c.github.io/encrypted-media/#dom-evt-message
  OnSessionMessage(string session_id, CdmMessageType message_type,
                   array<uint8> message);

  // Called when the session specified by |session_id| is closed. Note that the
  // CDM may close a session at any point, e.g. in response to `CloseSession()`,
  // when the session is no longer needed, or when system resources are lost.
  // After `OnSessionClosed()` is called for a `session_id`, no methods in this
  // interface should be called with the same `session_id`.
  // See http://w3c.github.io/encrypted-media/#session-close
  OnSessionClosed(string session_id, CdmSessionClosedReason reason);

  // Called when there has been a change in the keys in the session or their
  // status.
  // See http://w3c.github.io/encrypted-media/#dom-evt-keystatuseschange
  OnSessionKeysChange(string session_id, bool has_additional_usable_key,
                      array<CdmKeyInformation> keys_info);

  // Called when the CDM changes the expiration time of a session.
  // See http://w3c.github.io/encrypted-media/#update-expiration
  // |new_expiry_time_sec| is the number of seconds since epoch (Jan 1, 1970).
  OnSessionExpirationUpdate(string session_id, double new_expiry_time_sec);
};

// Context associated with the remote CDM, mostly to populate media::CdmContext.
struct CdmContext {
  // An ID that can be used to locate the CDM at the remote side.
  mojo_base.mojom.UnguessableToken cdm_id;

  // The remote Decryptor if the CDM implementation provides one.
  pending_remote<Decryptor>? decryptor;

  // Whether MediaFoundationRenderer is required by the CDM.
  [EnableIf=is_win]
  bool requires_media_foundation_renderer;
};

// Factory interface used for creating ContentDecryptionModule instances.
interface CdmFactory {
  // Creates a CDM based on the |key_system| and |cdm_config| provided. A
  // |key_system| is a generic term for a decryption mechanism and/or content
  // protection provider. It should be a reverse domain name,
  // e.g. "com.example.somesystem". However, this call may be initiated by an
  // untrusted process (e.g. renderer), so the implementation must fully
  // validate |key_system| before creating the CDM. |cdm_config| specifies other
  // properties of the CDM which may influence creation. Upon failure, the
  // returned |cdm| and |cdm_context| will be null, and |error_message| will
  // specify the error reason. Upon success, |cdm| and |cdm_context| will be
  // valid, and |error_message| will be empty.
  CreateCdm(string key_system, CdmConfig cdm_config) =>
            (pending_remote<ContentDecryptionModule>? cdm,
             CdmContext? cdm_context,
             string error_message);
};
