// %BANNER_BEGIN%
// ---------------------------------------------------------------------
// %COPYRIGHT_BEGIN%
// Copyright (c) (2018-2022) Magic Leap, Inc. All Rights Reserved.
// Use of this file is governed by the Software License Agreement, located here: https://www.magicleap.com/software-license-agreement-ml2
// Terms and conditions applicable to third-party materials accompanying this distribution may also be found in the top-level NOTICE file appearing herein.
// %COPYRIGHT_END%
// ---------------------------------------------------------------------
// %BANNER_END%
namespace UnityEngine.XR.MagicLeap
{
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using UnityEngine.XR.MagicLeap.Native;
///
/// MLMedia APIs.
///
public partial class MLMedia
{
///
/// Media player script that allows playback of a streaming video (either from file or web URL)
/// This script will update the main texture parameter of the Renderer attached as a sibling
/// with the video frame from playback. Audio is also handled through this class and will
/// playback audio from the file.
///
public partial class Player
{
///
/// Track from the prepared source that can be selected by the media player.
///
public partial class Track
{
///
/// MediaDRM to obtain the content keys for decrypting protected media streams.
///
public partial class DRM
{
///
/// See ml_media_drm.h for additional comments.
///
internal class NativeBindings : MagicLeapNativeBindings
{
private const string PROPERTY_VENDOR = "vendor";
private const string PROPERTY_VERSION = "version";
private const string PROPERTY_DESCRIPTION = "description";
private const string PROPERTY_ALGORITHMS = "algorithms";
private const string PROPERTY_DEVICE_UNIQUE_ID = "deviceUniqueId";
public delegate void OnEventDelegate(ulong handle, [In] ref MLMediaDRMEventInfo info);
public delegate void OnExpirationUpdateDelegate(ulong handle, [In] ref MLMediaDRMExpirationUpdateInfo info);
public delegate void OnKeyStatusChangeDelegate(ulong handle, [In] ref MLMediaDRMKeyStatusInfo info);
internal static readonly Dictionary Properties = new Dictionary()
{
{ Property.Vendor, PROPERTY_VENDOR},
{ Property.Version, PROPERTY_VERSION},
{ Property.Description, PROPERTY_DESCRIPTION},
{ Property.Algorithms, PROPERTY_ALGORITHMS},
{ Property.DeviceUniqueId, PROPERTY_DEVICE_UNIQUE_ID},
};
///
/// Data type containing {key, value} pair.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMKeyValue
{
public MLMediaDRMKeyValue(KeyValuePair pair)
{
this.Key = pair.Key;
this.Value = pair.Value;
}
///
/// Key.
///
[MarshalAs(UnmanagedType.LPStr)]
public readonly string Key;
///
/// Value.
///
[MarshalAs(UnmanagedType.LPStr)]
public readonly string Value;
public KeyValuePair KeyValue => new KeyValuePair(this.Key, this.Value);
};
///
/// Data type containing byte array buffer and the size.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMByteArray
{
///
/// Byte array buffer.
///
public IntPtr Data;
///
/// Size of Data.
///
public ulong Length;
public void AllocResources(byte[] data)
{
this.Data = Marshal.AllocHGlobal(data.Length);
Marshal.Copy(data, 0, this.Data, data.Length);
this.Length = (ulong)data.Length;
}
public void FreeResources()
{
Marshal.FreeHGlobal(this.Data);
}
public byte[] Bytes
{
get
{
if (IntPtr.Zero == this.Data)
return new byte[0];
byte[] bytes = new byte[this.Length];
Marshal.Copy(this.Data, bytes, 0, (int)this.Length);
return bytes;
}
}
};
///
/// Data type that encapsulates algorithm, key_set_id for HMAC based Sign/Verify.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMHMACInputParam
{
///
/// The MAC algorithm used for the MAC-HASH operation. "HmacSHA256" is the only supported algorithm now.
///
[MarshalAs(UnmanagedType.LPStr)]
public string Algorithm;
///
/// The identifier for the key to be used.
///
public IntPtr KeySetId;
internal void AllocResources(string algorithm, MLMediaDRMByteArray keySetId)
{
this.Algorithm = algorithm;
this.KeySetId = Marshal.AllocHGlobal(Marshal.SizeOf(keySetId));
Marshal.StructureToPtr(keySetId, this.KeySetId, false);
}
internal void FreeResources()
{
Marshal.FreeHGlobal(this.KeySetId);
}
};
///
/// Data type that encapsulates algorithm, wrapped_key for RSA operation.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMRSAInputParam
{
///
/// The MAC algorithm used for padding/signing. "HmacSHA256" is the only supported algorithm now.
///
public string Algorithm;
///
/// The wrapped RSA key to be used.
///
public IntPtr WrappedRsaKey;
internal void AllocResources(string algorithm, MLMediaDRMByteArray keySetId)
{
this.Algorithm = algorithm;
this.WrappedRsaKey = Marshal.AllocHGlobal(Marshal.SizeOf(keySetId));
Marshal.StructureToPtr(keySetId, this.WrappedRsaKey, false);
}
internal void FreeResources()
{
Marshal.FreeHGlobal(this.WrappedRsaKey);
}
};
///
/// Data type containing list of byte array buffers and the size.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMByteArrayList
{
///
/// Byte array buffer.
///
public IntPtr Ptr;
///
/// Length of #ptr.
///
public uint Length;
internal byte[][] ByteArrays
{
get
{
byte[][] byteArrays = new byte[this.Length][];
IntPtr walkPtr = this.Ptr;
for (int i = 0; i < this.Length; ++i)
{
NativeBindings.MLMediaDRMByteArray secureStopNative = Marshal.PtrToStructure(walkPtr);
byteArrays[i] = secureStopNative.Bytes;
walkPtr = new IntPtr(walkPtr.ToInt64() + Marshal.SizeOf());
}
return byteArrays;
}
}
};
///
/// Data type containing array of {key, value} pair.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMKeyValueArray
{
///
/// Array of {key, value} pair.
///
public readonly IntPtr Ptr;
///
/// Length of #ptr.
///
public readonly uint Length;
///
/// Index.
///
public readonly uint Index;
public KeyValuePair[] KeyValues
{
get
{
KeyValuePair[] keyValues = new KeyValuePair[this.Length];
IntPtr walkPtr = this.Ptr;
for (uint i = this.Index; i < this.Length; ++i)
{
MLMediaDRMKeyValue keyVal = Marshal.PtrToStructure(walkPtr);
keyValues[i] = keyVal.KeyValue;
walkPtr = new IntPtr(walkPtr.ToInt64() + Marshal.SizeOf());
}
return keyValues;
}
}
};
///
/// Data type that encapsulates Key Request input arguments.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMKeyRequestInputParam
{
internal MLMediaDRMKeyRequestInputParam(string mimeType, KeyType keyType)
{
this.MimeType = mimeType;
this.KeyType = keyType;
this.InitData = IntPtr.Zero;
this.OptionalParams = IntPtr.Zero;
}
internal void AllocResources(Player.NativeBindings.MLMediaPlayerPSSHEntry psshEntry)
{
this.InitData = Marshal.AllocHGlobal(Marshal.SizeOf());
NativeBindings.MLMediaDRMByteArray pssh = new NativeBindings.MLMediaDRMByteArray();
pssh.Data = psshEntry.data;
pssh.Length = psshEntry.size;
Marshal.StructureToPtr(pssh, this.InitData, false);
}
internal void FreeResources()
{
Marshal.FreeHGlobal(this.InitData);
Marshal.FreeHGlobal(this.OptionalParams);
}
///
/// The container-specific data, its meaning is interpreted based on the mime-type provided in the mime_type parameter. It
/// could contain, for example, the content ID, key ID or other data obtained from the content metadata that is required in
/// generating the key request.
///
public IntPtr InitData;
///
/// The mime type of the content.
///
[MarshalAs(UnmanagedType.LPStr)]
public string MimeType;
///
/// The type of the request. The request may be to acquire keys for streaming or offline content, or to release previously
/// acquired keys, which are identified by a key_set_id.
///
public KeyType KeyType;
///
/// Optional parameters included in the key request message to allow a client application to provide additional message
/// parameters to the server.
///
public readonly IntPtr OptionalParams;
};
///
/// Data type that encapsulates either of the following along with an URL: For Key Request Message: an opaque key request
/// byte array that should be delivered to the license server. For Provision Request Message: an opaque provision request
/// byte array that should be delivered to the provisioning server.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMRequestMessage
{
///
/// The opaque request byte array.
///
public readonly NativeBindings.MLMediaDRMByteArray Request;
///
/// The recommended URL to deliver the request to.
///
[MarshalAs(UnmanagedType.LPStr)]
public readonly string DefaultURL;
};
///
/// Data type that encapsulates algorithm, key_set_id and IV for Encryption/Decryption.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMCryptoInputParam
{
///
/// The cipher mode used for the crypto operation. "AES/CBC/NoPadding" is the only supported algorithm now.
///
[MarshalAs(UnmanagedType.LPStr)]
public string Algorithm;
///
/// The identifier for the key to be used.
///
public IntPtr KeySetId;
///
/// The initial vector used for the crypto operation.
///
public IntPtr InitialVector;
internal void AllocResources(string algorithm, MLMediaDRMByteArray keySetId, MLMediaDRMByteArray initialVector)
{
this.Algorithm = algorithm;
this.KeySetId = Marshal.AllocHGlobal(Marshal.SizeOf(keySetId));
Marshal.StructureToPtr(keySetId, this.KeySetId, false);
this.InitialVector = Marshal.AllocHGlobal(Marshal.SizeOf(initialVector));
Marshal.StructureToPtr(initialVector, this.InitialVector, false);
}
internal void FreeResources()
{
Marshal.FreeHGlobal(this.KeySetId);
Marshal.FreeHGlobal(this.InitialVector);
}
};
///
/// Data type containing array of {key, value} pair.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMEventCallbacks
{
internal static MLMediaDRMEventCallbacks Create()
{
MLMediaDRMEventCallbacks callbacks = new MLMediaDRMEventCallbacks();
callbacks.version = 1;
callbacks.onEvent = NativeBindings.OnEvent;
callbacks.onExpirationUpdate = NativeBindings.OnExpirationUpdate;
callbacks.onKeyStatusChange = NativeBindings.OnKeyStatusChange;
return callbacks;
}
private uint version;
public OnEventDelegate onEvent;
public OnExpirationUpdateDelegate onExpirationUpdate;
public OnKeyStatusChangeDelegate onKeyStatusChange;
};
///
/// MediaDRM event info associated with a session.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMEventInfo
{
///
/// DRM session id associated with the event.
///
public readonly IntPtr sessionIdByteArray;
///
/// Type of Media DRM event.
///
public readonly EventType eventType;
///
/// Extra Secondary error code.
///
public readonly int extra;
///
/// Optional data that may be associated with the event.
///
public readonly IntPtr eventDataByteArray;
///
/// User data as passed to MLMediaDRMPlayerSetEventCallbacksEx().
///
public readonly IntPtr data;
};
///
/// MediaDRM expiration update info associated with a session.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMExpirationUpdateInfo
{
///
/// DRM session id associated with the event.
///
public readonly IntPtr sessionIdByteArray;
///
/// The new expiration time for the keys in the session. The time is in milliseconds ,relative to the Unix epoch.
/// A time of 0 indicates that the keys never expire.
///
public readonly ulong expirationTimeMs;
///
/// User data as passed to MLMediaDRMPlayerSetEventCallbacksEx().
///
public readonly IntPtr data;
};
///
/// MediaDRM session key status.
///
[StructLayout(LayoutKind.Sequential)]
public readonly struct MLMediaDRMKeyStatus
{
///
/// KeyID that belongs to one of th DRM session key.
///
public readonly MLMediaDRMByteArray keyId;
///
/// Status code of the corresponding key.
///
public readonly KeyStatus status;
public Key Data => new Key(this.keyId.Bytes, this.status);
}
///
/// MediaDRM session keys status change info.
///
[StructLayout(LayoutKind.Sequential)]
public struct MLMediaDRMKeyStatusInfo
{
///
/// DRM session id associated with the event.
///
public IntPtr sessionIdByteArray;
///
/// Number of KeyStatus entries.
///
public ulong keyStatusCount;
///
/// Pointer to array of size keyStatusCount.
///
public IntPtr keyStatuses;
///
/// Indicates if a key has been added that is usable, which may trigger an attempt to resume playback on the media stream if it is currently blocked waiting for a key.
///
[MarshalAs(UnmanagedType.I1)]
public bool hasNewUsableKey;
///
/// User data as passed to MLMediaDRMPlayerSetEventCallbacksEx().
///
public IntPtr data;
};
///
/// Query if the given scheme identified by its UUID is supported on this device. And whether the drm plugin is able to
/// handle the media container format.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMIsCryptoSchemeSupported(Native.MagicLeapNativeBindings.MLUUID Uuid, IntPtr MimeType, [MarshalAs(UnmanagedType.I1)] out bool supported);
///
/// Release Request Message.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMRequestMessageRelease(ref MLMediaDRMRequestMessage Request);
///
/// Perform a signature verification using the specified algorithm (if specified) over the message data referenced by the
/// message parameter. The key must have been loaded into the session using MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMVerify(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMHMACInputParam HMACParam, [In] ref MLMediaDRMByteArray Message, [In] ref MLMediaDRMByteArray Signature, [MarshalAs(UnmanagedType.I1)] out bool IsMatch);
///
/// Generate a signature using the specified algorithm (if provided) over the message data and store the signature. The key
/// to use is identified by the 16 byte keyId. The key must have been loaded into the session using
/// MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMSign(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMHMACInputParam HMACParam, [In] ref MLMediaDRMByteArray Message, out MLMediaDRMByteArray Signature);
///
/// Remove the current keys from a session.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMRemoveKeys(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMByteArray KeySetId);
///
/// String property name: identifies the maker of the DRM engine plugin.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMByteArrayAllocate(uint Size, out MLMediaDRMByteArray OutArray);
///
/// Allocate and Copy to byte array buffer.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMByteArrayAllocAndCopy(IntPtr CopyFrom, uint Size, out MLMediaDRMByteArray OutArray);
///
/// Allocate array of {key, value} pairs.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMKeyValueArrayAllocate(uint Size, out MLMediaDRMKeyValueArray OutArray);
///
/// Create a
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMCreate(Native.MagicLeapNativeBindings.MLUUID uuid, out ulong handle);
///
/// Release the
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMRelease(ulong drmHandle);
///
/// Release byte array buffer.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMByteArrayRelease(ref MLMediaDRMByteArray array);
///
/// Release list of byte array buffer.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMByteArrayListRelease(ref MLMediaDRMByteArrayList Array);
///
/// Release {key, value} pair array.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMKeyValueArrayRelease(ref MLMediaDRMKeyValueArray Array);
///
/// Add a {key, value} pair to the array of {key, value} pairs.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMKeyValueArrayAdd([In] ref MLMediaDRMKeyValue Pair, out MLMediaDRMKeyValueArray OutArray);
///
/// Register a callback to be invoked when an event occurs.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMSetOnEventListenerEx(ulong MediaDrm, ref MLMediaDRMEventCallbacks Listener, IntPtr data);
///
/// Opens a new session. A session ID is returned.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMOpenSession(ulong MediaDrm, out MLMediaDRMByteArray sessionId);
///
/// Closes a session that was previously opened.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMCloseSession(ulong drmHandle, ref MLMediaDRMByteArray sessionId);
///
/// A key request/response exchange occurs between the app and a license server to obtain or release keys used to decrypt
/// encrypted content. MLMediaDRMGetKeyRequest() is used to obtain an opaque key request byte array that is delivered to the
/// license server. The opaque key request byte array is returned in out_key_request. request The recommended URL to
/// deliver the key request to is returned in out_key_request. default_URL. After the app has received the key request response
/// from the server, it should deliver to the response to the DRM engine plugin using the method
/// MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetKeyRequest(ulong drmHandle, [In] ref MLMediaDRMByteArray sessionId, [In] ref MLMediaDRMKeyRequestInputParam keyRequestParam, out MLMediaDRMRequestMessage keyRequest);
///
/// A key response is received from the license server by the app, then it is provided to the DRM engine plugin using
/// MLMediaDRMProvideKeyResponse(). When the response is for an offline key request, a key_set_id is returned that can be used to
/// later restore the keys to a new session with restoreKeys(). When the response is for a streaming or release request, a
/// null key_set_id is returned.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMProvideKeyResponse(ulong drmHandle, [In] ref MLMediaDRMByteArray sessionId, [In] ref MLMediaDRMByteArray response, out MLMediaDRMByteArray keySetId);
///
/// Restore persisted offline keys into a new session. key_set_id identifies the keys to load, obtained from a prior call
/// to MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMRestoreKeys(ulong MediaDrm, [In] ref MLMediaDRMByteArray sessionId, [In] ref MLMediaDRMByteArray KeySetId);
///
/// Request an informative description of the key status for the session. The status is in the form of {key, value} pairs.
/// Since DRM license policies vary by vendor, the specific status field names are determined by each DRM vendor. Refer to
/// your DRM provider documentation for definitions of the field names for a particular DRM engine plugin.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMQueryKeyStatus(ulong MediaDrm, [In] ref MLMediaDRMByteArray sessionId, out MLMediaDRMKeyValueArray OutInfoMap);
///
/// A provision request/response exchange occurs between the app and a provisioning server to retrieve a device certificate.
/// If provisioning is required, the #EVENT_PROVISION_REQUIRED event will be sent to the event handler.
/// MLMediaDRMGetProvisionRequest() is used to obtain the opaque provision request byte array that should be delivered to the provisioning
/// server.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetProvisionRequest(ulong drmHandle, [MarshalAs(UnmanagedType.LPStr)] string certType, out MLMediaDRMRequestMessage provisionRequest);
///
/// After a provision response is received by the app, it is provided to the DRM engine plugin using this method.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMProvideProvisionResponse(ulong drmHandle, [In] ref MLMediaDRMByteArray response, out MLMediaDRMByteArray certificate, out MLMediaDRMByteArray wrappedKey);
///
/// Access all secure stops. Secure Stop: A means of enforcing limits on the number of concurrent streams per subscriber
/// across devices is provided via #SecureStop. This is achieved by securely monitoring the lifetime of sessions.
/// Information from the server related to the current playback session is written to persistent storage on the device when each
/// #MediaCrypto object is created. In the normal case, playback will be completed, the session destroyed and the Secure Stops
/// will be queried. The app queries secure stops and forwards the secure stop message to the server which verifies the
/// signature and notifies the server side database that the session destruction has been confirmed. The persisted record on
/// the client is only removed after positive confirmation that the server received the message using releaseSecureStops().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetSecureStops(ulong MediaDrm, out MLMediaDRMByteArrayList SecureStops);
///
/// Access secure stop by secure stop ID. \see MLMediaDRMGetSecureStops()
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetSecureStop(ulong MediaDrm, [In] ref MLMediaDRMByteArray SecureStopId, out MLMediaDRMByteArray SecureStop);
///
/// Process the SecureStop server response message. After authenticating the message, remove the SecureStops identified in
/// the response.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMReleaseSecureStops(ulong MediaDrm, [In] ref MLMediaDRMByteArray SecureStop);
///
/// Remove all the SecureStops.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMReleaseAllSecureStops(ulong MediaDrm);
///
/// Read a DRM engine plugin String property value, given the property name.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetPropertyString(ulong MediaDrm, [MarshalAs(UnmanagedType.LPStr)] string PropertyName, [MarshalAs(UnmanagedType.LPStr)] out string OutPropertyValue);
///
/// Read a DRM engine plugin byte array property value, given the property name.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMGetPropertyByteArray(ulong MediaDrm, [MarshalAs(UnmanagedType.LPStr)] string PropertyName, out MLMediaDRMByteArray OutPropertyValue);
///
/// Set a DRM engine plugin String property value.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMSetPropertyString(ulong MediaDrm, [MarshalAs(UnmanagedType.LPStr)] string PropertyName, [MarshalAs(UnmanagedType.LPStr)] string PropertyValue);
///
/// Set a DRM engine plugin byte array property value.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMSetPropertyByteArray(ulong MediaDrm, [MarshalAs(UnmanagedType.LPStr)] string PropertyName, [In] ref MLMediaDRMByteArray PropertyValue);
///
/// Encrypt the data referenced by input using algorithm if specified, and write the encrypted result into output. The key
/// to use is identified by the 16 byte keyId. The key must have been loaded into the session using
/// MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMEncrypt(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMCryptoInputParam CryptoKeyParam, [In] ref MLMediaDRMByteArray Input, out MLMediaDRMByteArray Output);
///
/// Decrypt the data referenced by input using algorithm if specified, and write the encrypted result into output. The key
/// to use is identified by the 16 byte keyId. The key must have been loaded into the session using
/// MLMediaDRMProvideKeyResponse().
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMDecrypt(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMCryptoInputParam CryptoKeyParam, [In] ref MLMediaDRMByteArray Input, out MLMediaDRMByteArray Output);
///
/// Generate a signature using the specified RSA Key and algorithm.
///
[DllImport(MLMediaDRMDll, CallingConvention = CallingConvention.Cdecl)]
public static extern MLResult.Code MLMediaDRMSignRSA(ulong MediaDrm, [In] ref MLMediaDRMByteArray SessionId, [In] ref MLMediaDRMRSAInputParam HMACParam, [In] ref MLMediaDRMByteArray Message, out MLMediaDRMByteArray Signature);
///
/// Callback for the OnVideoSizeChanged event.
///
[AOT.MonoPInvokeCallback(typeof(NativeBindings.OnEventDelegate))]
private static void OnEvent(ulong MediaDrm, [In] ref MLMediaDRMEventInfo info)
{
GCHandle gcHandle = GCHandle.FromIntPtr(info.data);
DRM drm = gcHandle.Target as DRM;
if (drm != null)
{
MLMediaDRMByteArray eventData = Marshal.PtrToStructure(info.eventDataByteArray);
MLMediaDRMByteArray sessionId = Marshal.PtrToStructure(info.sessionIdByteArray);
// free these?
Event eventInfo = new Event(eventData.Bytes, sessionId.Bytes, info.eventType, info.extra);
MLThreadDispatch.Call(drm, eventInfo, drm.OnEvent);
}
}
///
/// Callback for the OnVideoSizeChanged event.
///
[AOT.MonoPInvokeCallback(typeof(NativeBindings.OnExpirationUpdateDelegate))]
private static void OnExpirationUpdate(ulong MediaDrm, [In] ref MLMediaDRMExpirationUpdateInfo info)
{
GCHandle gcHandle = GCHandle.FromIntPtr(info.data);
DRM drm = gcHandle.Target as DRM;
if (drm != null)
{
MLMediaDRMByteArray sessionIdArray = Marshal.PtrToStructure(info.sessionIdByteArray);
Expiration expiration = new Expiration(sessionIdArray.Bytes, info.expirationTimeMs);
MLThreadDispatch.Call(drm, expiration, drm.OnExpirationUpdate);
}
}
///
/// Callback for the OnVideoSizeChanged event.
///
[AOT.MonoPInvokeCallback(typeof(NativeBindings.OnKeyStatusChangeDelegate))]
private static void OnKeyStatusChange(ulong MediaDrm, [In] ref MLMediaDRMKeyStatusInfo info)
{
GCHandle gcHandle = GCHandle.FromIntPtr(info.data);
DRM drm = gcHandle.Target as DRM;
if (drm != null)
{
MLMediaDRMByteArray sessionIdArray = Marshal.PtrToStructure(info.sessionIdByteArray);
Key[] keys = new Key[info.keyStatusCount];
IntPtr walkPtr = info.keyStatuses;
for (ulong i = 0; i < info.keyStatusCount; ++i)
{
keys[i] = Marshal.PtrToStructure(walkPtr).Data;
walkPtr = new IntPtr(walkPtr.ToInt64() + Marshal.SizeOf());
}
KeyStatuses keyStatuses = new KeyStatuses(sessionIdArray.Bytes, keys, info.hasNewUsableKey);
MLThreadDispatch.Call(drm, keyStatuses, drm.OnKeyStatusChange);
}
}
}
}
}
}
}
}