SDK Development Guide for iOS and Android
What the SDK can do
The ExpressPlay SDK is designed to make it simple to build secure media players and ebook reader applications for Marlin protected audio, video and ebook content.
The SDK is available for iOS, Android, OSX Windows and Linux. The Linux version is only available as part of the ExpressPlay Source SDK. The ExpressPlay SDK shares a common core API set across all platforms. On some platforms the SDK includes an extended set of APIs unique to that platform.
For development of media applications on iOS and Android the SDK offers a simple API providing access to DRM control and media playback functions, sufficient to credential an application, acquire DRM licenses and trigger playback of Marlin-protected content. Content may be a contiguous media file or an adaptive bit rate (ABR) stream. The SDK works in conjunction with the ExpressPlay Service for device initialization (Marlin personalization) and token processing for playback (Marlin content license acquisition) while meeting the compliance and robustness rules of the MTMO (Marlin Trust Management Organization).
Steps to play content
Below is a high-level view of the steps required to play content. The exact sequence of steps to play content in your application may vary as streaming is a bit simpler than download, and some platforms have wrapper functions (such as EXP Player for iOS) that may combine steps. Regardless of the actual APIs used by your app, these steps need to happen at some level within your application and it's use of the ExpressPlay SDK.
- Initialize the DRM engine
- Get a unique player ID (personalization)
- Start up the playlist proxy
- Get the content URL
- Get a token for playback (if MS3 then it's included in the content url)
- Send the content url to the playlist proxy
- Start the player
What are the steps for ebooks
- Initialize the DRM Engine
- Get a unique player ID (personalization)
- Get a BB license for the content ID of the ebook, and store that license in the license store
- Instantiate a MediaStream object (passing it a reference to the encrypted ebook file)
- Read bytes from the mediastream object until there are none remaining. Now you have a decrypted ebook.
- Instantiate a webview object, and pass it the decrypted ebook
Key Concepts
Below is a list of key concepts that a developer should know before using the ExpressPlay SDK. It's a good idea to go through all the concepts before using the SDK as they are reference frequently throughout the SDK documentation.
SDK Usage Guidelines
In addition to the key concepts above, the ExpressPlay SDK Usage Guidelines is an overview of best practices when using the ExpressPlay SDK. The major sections of the guidelines are listed below for convenience.
Personalization
Personalization is a Marlin term for device initialization. When an app requests to be personalized by ExpressPlay, it provides a unique fingerprint. The ExpressPlay service, responds by providing the client a credential which is unique to that application copy running on a given device. Without this unique Marlin credential, the device is not able to request tokens for playback.
Additional information on Personalization can be found here.
Content License Acquisition
There are two ways to obtain a Marlin content license, using SAS (via MS3) or using a Marlin Broadband (BB) license. Either may be obtained from the ExpressPlay service. You can obtain additional information for MS3 and Marlin BroadBand licenses here.
EXP player
The EXP Player API is currently available only for iOS, and it is the easiest way to begin using ExpressPlay in an iOS media app. The EXP Player API is currently only available in the ExpressPlay SDK for iOS. The EXP Player API is new so this section will be updated with more information about this API soon.
Playlist proxy
On iOS and Android, playback of Audio/Visual content is handled by the device's native media player. This makes it possible to use the device's media decoders and preserves battery life. For the native media player to playback Marlin protected media, the ExpressPlay SDK interposes a Proxy (Playlist Proxy) between the raw protected media source and the native player. The Playlist Proxy reads from the protected media source, evaluates the license, and if the license allows it, decrypts the media and makes it available as an HLS stream to the native player.
Playlist Proxy acts as an interface between the native media playback engine and web servers or the local file system from which playable media is accessed. URL or local references to Marlin-encrypted content are redirected to the Playlist Proxy (each with the media reference included in a query field). The Playlist Proxy can help build a media player application that plays Marlin-protected content on iOS systems and on Android systems that can handle HTTP Live Streaming playlists.
How it works
The Playlist Proxy accesses the local file system or web server as required to obtain the specified media item. When the media is Marlin-encrypted content, the Playlist Proxy ensures that access to the content is allowed, and the proxy obtains the decryption key and decrypts that content before returning the cleartext result to the media player.
The Playlist Proxy can handle both Marlin and non-Marlin local and remote media, specifically:- Local and remote Marlin BBTS media.
- Local (only) Marlin PDCF files with A/V media
- Local and remote Marlin DCF files, where the media may be of any type. Note that:
- the DCF media accessed by the Playlist Proxy must be unencumbered of output control. Therefore, a license that relaxes the default marlin output controls is required for playback of DCF files. This restriction can be lifted by a MS3 extension (of type “wudo”) or a Marlin Broadband output control override (type “urn:marlin:organization:intertrust:wudo”).
- Unlike other input media types that are transformed into an HLS stream, DCF files are made available by the Proxy as a simple byte stream over HTTP. The origin server must support HTTP1.1 range requests
- Both clear and Marlin-encrypted media referenced using a Marlin Simple Secure Streaming (MS3) URL, which indicates both the media location and the media access rights.
- Playlists defined by the HTTP Live Streaming (HLS) protocol, which are understood by the native iOS media player and by the media player on some Android systems. The Playlist Proxy handles Marlin-encrypted (BBTS) media referenced by a playlist, and also handles AES-128-encrypted media whose key(s) are protected using Marlin, but will not handle cleartext media referenced by a playlist unless that playlist is supplied as part of an MS3 compound URL.
- Both clear and Marlin-encrypted media referenced by MPD (Media Presentation Description) manifests defined by the MPEG DASH protocol. Such manifests are currently not understood by native iOS or Android media players, and so the Playlist Proxy initially converts such manifests to HLS playlists.
Usage of the Playlist Proxy always involves HTTP Live Streaming playlists (essentially, lists of media to be played), whether the initial media reference is to a single file, an HLS playlist, or an MPEG-DASH MPD file.
Marlin provides extensions to the HLS playlist protocol, such as additional attributes for the EXT-X-KEY tag that are used when Marlin-encrypted content is referenced. Marlin also provides extensions for MPEG-DASH Media Presentation Descriptions (MPDs). These extensions for both HLS and MPD are described in the Marlin Adaptive Streaming Specifications referenced in Section 7.
MPEG-DASH with Playlist Proxy
The Playlist Proxy supports a constrained set of features of the MPEG-DASH manifest. The profile supported is the "8.4 ISO Base media file format live profile" of the MPEG-DASH specification "ISO/IEC JTC 1/SC 29".
The Playlist Proxy transcribes a DASH manifest into an HLS playlist on-the-fly and forwards the HLS playlist to the native player. The HLS playlist produced from an MPEG-DASH manifest has the following structure and constraints.
- Both static and dynamic DASH are supported.
- The adaptation sets are picked based on the Role@main attribute, the codecs required and available, and the language desired in the case of audio.
- The set of representations found in the first period is assumed to exist in all consecutive periods of the presentation.
- There are two levels of HLS playlist: top level with listing of the variant streams corresponding to different representations of the video (even if only one), and second level listing segments for each variant stream.
- There is one EXT-X-STREAM-INF with the BANDWIDTH attribute and the PROGRAM-ID=1 attribute for each variant stream in the top level playlist.
- There is one EXTINF tag for each segment in the variant stream playlists with duration rounded up to the nearest integer number of seconds.
- The HLS segments are aligned with DASH segments. An HLS segment maps to exactly one audio and one video DASH segment.
- Static DASH results in variant stream playlists with EXT-X-ENDLIST, dynamic DASH results in variant stream playlists without EXT-X-ENDLIST. The client media player reloads segment playlists without EXT-X-ENDLIST. Playlist Proxy reloads DASH MPD based on the HLS request from the client. Newly generated HLS playlist may add segments, and may remove segments in which case it adjusts the EXT-X-MEDIA-SEQUENCE tag value. The client is not expected to reload the top level playlist of variant steams, however the top playlist includes the EXT-X-ENDLIST in case of static DASH presentation just as does each of the variant stream playlist, and converly, none of the playlists include EXT-X-ENDLIST in the case of dynamic DASH.
- EXT-X-TARGETDURATION is set to the max of all segment durations in the playlist.
- EXT-X-DISCONTINUITY is generated before the first segment of each DASH period signalling (potential) discontinuity.
An actual segment URL contains query fields identifying the period, audio and video representations, segment indices, segment start times, etcPlaylist Proxy can take clear or protected MPEG DASH input and produce HLS playlist with clear MPEG2 TS segments. The key is managed by Marlin DRM and the Common Encryption MPEG DASH scheme is supported (as specified in Information technology — MPEG systems technologies — Part 7: Common encryption in ISO base media file format files).
HLS with Playlist Proxy
HTTP Live Streaming (HLS) is a way for a client to request streaming content according to its bandwidth limitations. It can be used for both live and VOD use cases. The specification is available as a draft IETF RFC available at:
http://tools.ietf.org/html/draft-pantos-http-live-streaming-07
This technology is used primarily on Apple devices, and is part of the iOS media stack and also part of the media stack on Android devices that can handle HLS playlists. It uses a playlist file as a manifest and MPEG2-TS as a container media format. A playlist is essentially a text file specifying media to be played in order, and the text file has a particular MIME type (application/vnd.apple.mpegurl) indicating that it’s a playlist.
The Playlist Proxy can handle HLS (M3U format) playlists. It supports the following:
- Playlists referencing either clear or Marlin-encrypted content when the playlist is part of an MS3 compound URL.
- Playlists referencing Marlin BBTS content.
- Playlists referencing AES-128-encrypted content whose key(s) are protected using Marlin.
Any other types of playlists are not supported. For example, the Playlist Proxy does not in general handle playlists when there is no use of Marlin, except when the playlist is part of an MS3 compound URL.
Playlist Proxy on iOS
On iOS the client application activities required to initiate and support usage of the Playlist Proxy are very simple, and they are summarized in the following list.
- Call WSB_PlaylistProxy_Create to instantiate a WSB_PlaylistProxy object.
- Call WSB_PlaylistProxy_Start to start the Playlist Proxy server.
- Find out the Playlist Proxy major and minor version numbers, and compare them with those expected by the client application.
- Whenever playback of a media file or broadcast is requested (with or without an HLS playlist or a DASH MPD), and you want the Playlist Proxy to be used (which is a requirement if the media is Marlin-protected), then do the following:
- Call WSB_PlaylistProxy_MakeUrl to obtain an appropriate URL that will be directed to the Playlist Proxy in order for it to handle Marlin-related activities in support of the playback of the specified media.
- Pass the URL created by WSB_PlaylistProxy_MakeUrl to the iOS media player. The URL references the Playlist Proxy. When the media player executes an HTTP GET on the URL, the Playlist Proxy is invoked to perform appropriate actions. These actions ultimately (after one or more HTTP exchanges between the Playlist Proxy and the media player) result in playback of the specified media, if the Playlist Proxy determines that access to the Marlin-protected media is allowed.
- When the Playlist Proxy is no longer needed, call WSB_PlaylistProxy_Stop to stop proxy execution, and call WSB_PlaylistProxy_Destroy to destroy the WSB_PlaylistProxy object.
Playlist Proxy on Android
On Android (version 4.0 and above) the client application activities required to initiate and support usage of the Playlist Proxy are very simple, and are summarized in the following list.
- Instantiate a PlaylistProxy object.
- Call the PlaylistProxy start method to start the Playlist Proxy server.
- Whenever playback of a media file or broadcast is requested (with or without a playlist or MPD), and you want the Playlist Proxy to be used, then do the following:
- Call the PlaylistProxy makeUrl method to obtain an appropriate URL that will be directed to the Playlist Proxy in order for it to handle Marlin-related activities in support of the playback of the specified media.
- Pass the URL created by makeUrl to the Android media player. The URL references the Playlist Proxy, so when the media player does an HTTP GET on the URL, the Playlist Proxy is invoked to perform appropriate actions. These actions will ultimately (after one or more HTTP exchanges between the Playlist Proxy and the media player) result in playback of the specified media, if the Playlist Proxy has determined that access to the Marlin-protected media is allowed.
- When the Playlist Proxy is no longer needed, call the PlaylistProxy stop method to stop proxy execution.
Creating a PlaylistProxy and Starting the Server
Instantiate a PlaylistProxy object, for example with code like the following: PlaylistProxy playlistProxy; playlistProxy = new PlaylistProxy(); Before you can utilize the functionality of the Playlist Proxy server, which is done via HTTP URLs, you must call the PlaylistProxy start method. This method creates all the internal threads that will be utilized by the server, and starts the server. It assigns the port to be used to access the server via HTTP.
Obtaining HTTP URLs to Access the Playlist Proxy
In order for a particular Marlin-protected media file (or the media specified in a playlist or MPD) to be able to be played, a complete URL referencing the Playlist Proxy must first be created. The client application must call the PlaylistProxy makeUrl method to create an appropriate URL. This way, the creators of URLs referencing Marlin-encrypted media or playlists do not have to know the URL to be used to reference the Playlist Proxy. In fact, it is not even possible for anyone to know in advance the port to be used to access the proxy, because the port is assigned by the start method called by the client application to start the proxy server.
You pass makeUrl, in the mediaSource parameter, a java.lang.String specifying a local file or playlist or a URL referencing a remote file or playlist. You also pass it a media source type (in the mediaSourceType parameter) indicating whether the specified source is a single file or a playlist.
The mediaSourceParams parameter should be NULL if no parameters further describing the media source are needed. Otherwise, the object passed in this parameter is a PlaylistProxy.MediaSourceParams instance.
The makeUrl method returns the URL to the client application. This URL includes an authentication token, which identifies the session for accessing the specified Marlin media file or playlist. When a request is made using the URL, the Playlist Proxy ensures the request includes the appropriate authentication token, thereby preventing other applications from unauthorized access.
Note: The proxy supports a single session at a time. A session is started by calling the PlaylistProxy makeUrl method.
It is possible to pass a value of 0 for bitrateBitsPerSecond, in which case the default value of (currently) 3 million bits per second will be used when estimating content length. However, the default value could change at any time, so its use is not recommended.
MediaStream (MS) for ebooks
MediaStream interface supports decryption of HTTP or file based encrypted data other than the typical Marlin protected audio/video media. Which could consist of the eBook media type, where many container formats exist, including a Marlin defined ePub container. In this scenario, either the whole eBook or specific elements of the ebook container can be encrypted and packaged into a type supported by this new interface. The application then parses the container, and uses the interface combined with a Marlin license to decrypt the content.
Additional information for ebooks can be found here.
Other DRM Functions
The Extended DRM functionality is accessible to applications using the source sdk. Including such functions as the ability to access content keys, or query the consequences of a license evaluation (to assess for instance if some form of output controls must be applied and do so as a result). This greater functionality however requires that these applications provide their own security and hardening mechanisms to prevent the loss of key and content material.