Decryption_GetBoundLicense.cpp
[The AD RMS SDK leveraging functionality exposed by the client in Msdrm.dll is available for use in Windows Server 2008, Windows Vista, Windows Server 2008 R2, Windows 7, Windows Server 2012, and Windows 8. It may be altered or unavailable in subsequent versions. Instead, use Active Directory Rights Management Services SDK 2.1, which leverages functionality exposed by the client in Msipc.dll.]
The following code example retrieves an end-user license chain from the certificate store, acquires the end-user license from the chain, and binds the license to the EDIT right.
#include "DecryptingContent.h"
/*===================================================================
File: Decryption_GetBoundLicense.cpp
THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
PARTICULAR PURPOSE.
Copyright (C) Microsoft. All rights reserved.
===================================================================*/
/////////////////////////////////////////////////////////////////////
// The GetBoundLicense function binds an end user license to the
// EDIT right and returns a pointer to the license handle.
//
HRESULT GetBoundLicense (
DRMHSESSION hClient,
DRMENVHANDLE hEnv,
DRMHANDLE hLib,
PWSTR pwszRAC,
PWSTR pwszSignedIL,
DRMHANDLE* phBoundLic)
{
///////////////////////////////////////////////////////////////////
// Declare variables:
// hr........................Return value
// pwszEULChain..............End user license chain
// pwszEUL...................End user license
// pwszContentID.............Content ID string
// uiEUL.....................Number of characters in the EUL
// hEnablingPrin.............Enabling principal used for binding
// hLicenseStorage...........Handle to license storage session
// DW_WAIT_TIME..............Maximum time to wait for signal
// dwWaitResult..............Actual time of wait for signal
// idNULL....................DRMID structure
// idContent.................Structure for binding a license
// oParams...................Structure for binding a license
// idStandardEP..............Structure for enabling principal
// context...................Callback context
HRESULT hr = S_OK;
PWSTR pwszEULChain = NULL;
PWSTR pwszEUL = NULL;
PWSTR pwszContentID = NULL;
UINT uiEUL = 0;
DRMHANDLE hEnablingPrin = NULL;
DRMHSESSION hLicenseStorage = NULL;
const DWORD DW_WAIT_TIME = 60000;
DWORD dwWaitResult = 0;
DRMID idContent;
DRMID idStandardEP;
DRMID idNULL;
DRM_CONTEXT context;
DRMBOUNDLICENSEPARAMS oParams;
wprintf(L"\r\nEntering GetBoundLicense.\r\n");
// Create a license storage session.
hr = DRMCreateLicenseStorageSession(
hEnv, // Environment handle
hLib, // Library handle
hClient, // Client session handle
0, // Reserved
pwszSignedIL, // Signed issuance license
&hLicenseStorage ); // License storage handle
if(FAILED(hr)) goto e_Exit;
wprintf(L"DRMCreateLicenseStorageSession: hLicenseStorage=%i\r\n",
hLicenseStorage);
// Initialize the callback context.
context.hEvent = NULL; // Event handle
context.pwszData = NULL; // Signed license
// Create an event to signal when the license has been acquired.
context.hEvent = CreateEvent(
NULL, // No attributes
FALSE, // Automatic reset
FALSE, // Initial state not signaled
NULL); // Event object not named
if(NULL == context.hEvent) goto e_Exit;
// Call DRMAcquireLicense, which will put the end-user license
// into the permanent license store for you by default, or specify
// DRM_AL_NOPERSIST if you want to put the license into the
// temporarystore and handle storage and management yourself.
hr = DRMAcquireLicense(
hLicenseStorage, // Storage session handle
0, // No flags set
NULL, // No RAC specified
NULL, // Reserved
NULL, // Custom data
NULL, // Optional license URL
(VOID*)&context); // Callback context
if(FAILED(hr)) goto e_Exit;
// Wait for the callback to return.
dwWaitResult = WaitForSingleObject(context.hEvent, DW_WAIT_TIME);
if(WAIT_TIMEOUT == dwWaitResult || FAILED(context.hr)) goto e_Exit;
// Enumerate the end user license chain from the license store.
// Note: This example assumes that there is only one EUL in the
// license store. If others exist, you can increment the
// index of the DRMEnumerateLicense function until you
// receive an E_DRM_NO_MORE_DATA error to ensure that you
// have tried all of the possible EULs for this content.
hr = GetCertificate(
hLicenseStorage, // License storage session
DRM_EL_EUL, // Certificate type
&pwszEULChain); // EUL chain
if (FAILED(hr)) goto e_Exit;
wprintf(L"GetCertificate (pwszEULChain) succeeded.\r\n");
// Retrieve the EUL from the EUL chain.
// - Call DRMDeconstructCertificateChain once to retrieve the
// length of the license.
// - Allocate memory for the license.
// - Call DRMDeconstructCertificateChain again to retrieve the
// license.
hr = DRMDeconstructCertificateChain(
pwszEULChain, // The EUL certificate chain
0, // Index of certificate
&uiEUL, // Certificate length
NULL);
if (FAILED(hr)) goto e_Exit;
// Allocate memory for the end user license.
pwszEUL = new WCHAR[uiEUL];
if (NULL == pwszEUL)
{
hr = E_OUTOFMEMORY;
goto e_Exit;
}
hr = DRMDeconstructCertificateChain(
pwszEULChain, // The EUL certificate chain
0, // Item 0 is the EUL
&uiEUL, // Certificate length
pwszEUL); // End user license
if (FAILED(hr)) goto e_Exit;
wprintf(L"DRMDeconstructCertificateChain succeeded.\r\n");
// Retrieve the content ID from the end user license.
hr = GetContentID(
pwszEUL, // End user license
&pwszContentID); // Content ID string
if (FAILED(hr)) goto e_Exit;
wprintf(L"GetContentID: pwszContentID = \r\n", pwszContentID);
// Create an enabling principal.
SecureZeroMemory(&idNULL, sizeof(idNULL));
SecureZeroMemory(&idStandardEP, sizeof(idStandardEP));
idStandardEP.wszIDType = L"ASCII Tag";
idStandardEP.wszID = L"UDStdPlg Enabling Principal";
hr = DRMCreateEnablingPrincipal (
hEnv, // Secure environment handle
hLib, // Library handle
idStandardEP.wszID, // Enabling principal type
&idNULL, // DRMID structure
pwszRAC, // Current RAC
&hEnablingPrin); // Enabling principal handle
if (FAILED(hr)) goto e_Exit;
wprintf(L"DRMCreateEnablingPrincipal succeeded.\r\n");
// Bind the end user license to the EDIT right. The content ID
// defined by the pwszContentID parameter is the same as that
// defined when creating the issuance license.
SecureZeroMemory(&idContent, sizeof(idContent));
idContent.wszIDType = L"MS-GUID";
idContent.wszID = pwszContentID;
SecureZeroMemory(&oParams, sizeof(oParams));
oParams.hEnablingPrincipal = hEnablingPrin;
oParams.wszRightsRequested = L"EDIT";
oParams.wszRightsGroup = L"Main-Rights";
oParams.idResource = idContent;
// Create a bound license.
hr = DRMCreateBoundLicense (
hEnv, // Secure environment handle
&oParams, // Additional license options
pwszEULChain, // EUL chain
phBoundLic, // Handle to bound license
NULL); // Reserved
if (FAILED(hr)) goto e_Exit;
wprintf(L"DRMCreateBoundLicense: hBoundLic = %i\r\n", *phBoundLic);
e_Exit:
if (NULL != hLicenseStorage)
{
hr = DRMCloseSession(hLicenseStorage);
hLicenseStorage = NULL;
}
if (NULL != pwszEULChain)
{
delete [] pwszEULChain;
pwszEULChain = NULL;
}
if (NULL != pwszEUL)
{
delete [] pwszEUL;
pwszEUL = NULL;
}
wprintf(L"Leaving GetBoundLicense: hr = %x\r\n", hr);
return hr;
}
Related topics