Nota
L'accesso a questa pagina richiede l'autorizzazione. Puoi provare ad accedere o a cambiare directory.
L'accesso a questa pagina richiede l'autorizzazione. Puoi provare a cambiare directory.
I servizi che implementano PlayReady devono gestire un sistema di gestione delle chiavi (KMS) per archiviare e gestire le chiavi di contenuto. In particolare, i valori di {KID, Content Key} vengono archiviati per ogni asset di contenuto gestito dal servizio. Questi valori vengono archiviati in fase di crittografia e recuperati in fase di rilascio delle licenze.
PlayReady offre un modo pratico per evitare un sistema di gestione delle chiavi complesso. L'algoritmo Seed della chiave di contenuto consente la derivazione di chiavi di contenuto diverse per una raccolta di asset di contenuto, da un KID variabile e da un Seed della chiave fisso:
Ck(KID) = f(KID, KeySeed)
Di seguito è riportato l'algoritmo standard PlayReady:
byte[] GeneratePlayReadyContentKey(byte[] keySeed, Guid keyId)
{
const int DRM_AES_KEYSIZE_128 = 16;
byte[] contentKey = new byte[DRM_AES_KEYSIZE_128];
//
// Truncate the key seed to 30 bytes, key seed must be at least 30 bytes long.
//
byte[] truncatedKeySeed = new byte[30];
Array.Copy(keySeed, truncatedKeySeed, truncatedKeySeed.Length);
//
// Get the keyId as a byte array
//
byte[] keyIdAsBytes = keyId.ToByteArray();
//
// Create sha_A_Output buffer. It is the SHA of the truncatedKeySeed and the keyIdAsBytes
//
SHA256Managed sha_A = new SHA256Managed();
sha_A.TransformBlock(truncatedKeySeed, 0, truncatedKeySeed.Length, truncatedKeySeed, 0);
sha_A.TransformFinalBlock(keyIdAsBytes, 0, keyIdAsBytes.Length);
byte[] sha_A_Output = sha_A.Hash;
//
// Create sha_B_Output buffer. It is the SHA of the truncatedKeySeed, the keyIdAsBytes, and
// the truncatedKeySeed again.
//
SHA256Managed sha_B = new SHA256Managed();
sha_B.TransformBlock(truncatedKeySeed, 0, truncatedKeySeed.Length, truncatedKeySeed, 0);
sha_B.TransformBlock(keyIdAsBytes, 0, keyIdAsBytes.Length, keyIdAsBytes, 0);
sha_B.TransformFinalBlock(truncatedKeySeed, 0, truncatedKeySeed.Length);
byte[] sha_B_Output = sha_B.Hash;
//
// Create sha_C_Output buffer. It is the SHA of the truncatedKeySeed, the keyIdAsBytes,
// the truncatedKeySeed again, and the keyIdAsBytes again.
//
SHA256Managed sha_C = new SHA256Managed();
sha_C.TransformBlock(truncatedKeySeed, 0, truncatedKeySeed.Length, truncatedKeySeed, 0);
sha_C.TransformBlock(keyIdAsBytes, 0, keyIdAsBytes.Length, keyIdAsBytes, 0);
sha_C.TransformBlock(truncatedKeySeed, 0, truncatedKeySeed.Length, truncatedKeySeed, 0);
sha_C.TransformFinalBlock(keyIdAsBytes, 0, keyIdAsBytes.Length);
byte[] sha_C_Output = sha_C.Hash;
for (int i = 0; i < DRM_AES_KEYSIZE_128; i++)
{
contentKey[i] = Convert.ToByte(sha_A_Output[i] ^ sha_A_Output[i + DRM_AES_KEYSIZE_128]
^ sha_B_Output[i] ^ sha_B_Output[i + DRM_AES_KEYSIZE_128]
^ sha_C_Output[i] ^ sha_C_Output[i + DRM_AES_KEYSIZE_128]);
}
return contentKey;
}