Remove FairPlayPsshGenerator
This was introduced earlier to indicate FairPlay protection system. But in fact, it is sufficient to just use the system id for the indication. - Also updated various parts of the pipeline to support empty PSSH. - Added an additional FairPlay end to end test using fMP4. Change-Id: Ica48b7b5235e9a2b5a7f722bcd0fc1ef2073ac13
This commit is contained in:
parent
f39f9de6d8
commit
08aa9b6b2b
|
@ -862,6 +862,13 @@ class PackagerFunctionalTest(PackagerAppTest):
|
||||||
self._GetFlags(encryption=True, output_dash=True))
|
self._GetFlags(encryption=True, output_dash=True))
|
||||||
self._CheckTestResults('encryption', verify_decryption=True)
|
self._CheckTestResults('encryption', verify_decryption=True)
|
||||||
|
|
||||||
|
def testEncryptionWithFairplay(self):
|
||||||
|
self.assertPackageSuccess(
|
||||||
|
self._GetStreams(['audio', 'video']),
|
||||||
|
self._GetFlags(
|
||||||
|
encryption=True, fairplay=True, output_dash=True, output_hls=True))
|
||||||
|
self._CheckTestResults('encryption-with-fairplay')
|
||||||
|
|
||||||
# Test deprecated flag --enable_fixed_key_encryption, which is still
|
# Test deprecated flag --enable_fixed_key_encryption, which is still
|
||||||
# supported currently.
|
# supported currently.
|
||||||
def testEncryptionUsingFixedKey(self):
|
def testEncryptionUsingFixedKey(self):
|
||||||
|
|
Binary file not shown.
Binary file not shown.
|
@ -0,0 +1,7 @@
|
||||||
|
#EXTM3U
|
||||||
|
## Generated with https://github.com/google/shaka-packager version <tag>-<hash>-<test>
|
||||||
|
|
||||||
|
#EXT-X-MEDIA:TYPE=AUDIO,URI="stream_0.m3u8",GROUP-ID="default-audio-group",NAME="stream_0",AUTOSELECT=YES,CHANNELS="2"
|
||||||
|
|
||||||
|
#EXT-X-STREAM-INF:BANDWIDTH=1111406,AVERAGE-BANDWIDTH=1009412,CODECS="avc1.64001e,mp4a.40.2",RESOLUTION=640x360,AUDIO="default-audio-group"
|
||||||
|
stream_1.m3u8
|
|
@ -0,0 +1,27 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<!--Generated with https://github.com/google/shaka-packager version <tag>-<hash>-<test>-->
|
||||||
|
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xlink="http://www.w3.org/1999/xlink" xsi:schemaLocation="urn:mpeg:dash:schema:mpd:2011 DASH-MPD.xsd" xmlns:cenc="urn:mpeg:cenc:2013" profiles="urn:mpeg:dash:profile:isoff-on-demand:2011" minBufferTime="PT2S" type="static" mediaPresentationDuration="PT2.7360665798187256S">
|
||||||
|
<Period id="0">
|
||||||
|
<AdaptationSet id="0" contentType="video" width="640" height="360" frameRate="30000/1001" subsegmentAlignment="true" par="16:9">
|
||||||
|
<ContentProtection value="cenc" schemeIdUri="urn:mpeg:dash:mp4protection:2011" cenc:default_KID="31323334-3536-3738-3930-313233343536"/>
|
||||||
|
<ContentProtection schemeIdUri="urn:uuid:29701fe4-3cc7-4a34-8c5b-ae90c7439a47"/>
|
||||||
|
<Representation id="0" bandwidth="977743" codecs="avc1.64001e" mimeType="video/mp4" sar="1:1">
|
||||||
|
<BaseURL>bear-640x360-video.mp4</BaseURL>
|
||||||
|
<SegmentBase indexRange="1075-1142" timescale="30000">
|
||||||
|
<Initialization range="0-1074"/>
|
||||||
|
</SegmentBase>
|
||||||
|
</Representation>
|
||||||
|
</AdaptationSet>
|
||||||
|
<AdaptationSet id="1" contentType="audio" subsegmentAlignment="true">
|
||||||
|
<ContentProtection value="cenc" schemeIdUri="urn:mpeg:dash:mp4protection:2011" cenc:default_KID="31323334-3536-3738-3930-313233343536"/>
|
||||||
|
<ContentProtection schemeIdUri="urn:uuid:29701fe4-3cc7-4a34-8c5b-ae90c7439a47"/>
|
||||||
|
<Representation id="1" bandwidth="133663" codecs="mp4a.40.2" mimeType="audio/mp4" audioSamplingRate="44100">
|
||||||
|
<AudioChannelConfiguration schemeIdUri="urn:mpeg:dash:23003:3:audio_channel_configuration:2011" value="2"/>
|
||||||
|
<BaseURL>bear-640x360-audio.mp4</BaseURL>
|
||||||
|
<SegmentBase indexRange="951-1018" timescale="44100">
|
||||||
|
<Initialization range="0-950"/>
|
||||||
|
</SegmentBase>
|
||||||
|
</Representation>
|
||||||
|
</AdaptationSet>
|
||||||
|
</Period>
|
||||||
|
</MPD>
|
|
@ -0,0 +1,17 @@
|
||||||
|
#EXTM3U
|
||||||
|
#EXT-X-VERSION:6
|
||||||
|
## Generated with https://github.com/google/shaka-packager version <tag>-<hash>-<test>
|
||||||
|
#EXT-X-TARGETDURATION:2
|
||||||
|
#EXT-X-PLAYLIST-TYPE:VOD
|
||||||
|
#EXT-X-MAP:URI="bear-640x360-audio.mp4",BYTERANGE="951@0"
|
||||||
|
#EXT-X-KEY:METHOD=SAMPLE-AES-CTR,URI="skd://www.license.com/getkey?KeyId=31323334-3536-3738-3930-313233343536",KEYFORMATVERSIONS="1",KEYFORMAT="com.apple.streamingkeydelivery"
|
||||||
|
#EXTINF:1.022,
|
||||||
|
#EXT-X-BYTERANGE:17028@1019
|
||||||
|
bear-640x360-audio.mp4
|
||||||
|
#EXTINF:0.998,
|
||||||
|
#EXT-X-BYTERANGE:16682
|
||||||
|
bear-640x360-audio.mp4
|
||||||
|
#EXTINF:0.720,
|
||||||
|
#EXT-X-BYTERANGE:9859
|
||||||
|
bear-640x360-audio.mp4
|
||||||
|
#EXT-X-ENDLIST
|
|
@ -0,0 +1,17 @@
|
||||||
|
#EXTM3U
|
||||||
|
#EXT-X-VERSION:6
|
||||||
|
## Generated with https://github.com/google/shaka-packager version <tag>-<hash>-<test>
|
||||||
|
#EXT-X-TARGETDURATION:2
|
||||||
|
#EXT-X-PLAYLIST-TYPE:VOD
|
||||||
|
#EXT-X-MAP:URI="bear-640x360-video.mp4",BYTERANGE="1075@0"
|
||||||
|
#EXT-X-KEY:METHOD=SAMPLE-AES-CTR,URI="skd://www.license.com/getkey?KeyId=31323334-3536-3738-3930-313233343536",KEYFORMATVERSIONS="1",KEYFORMAT="com.apple.streamingkeydelivery"
|
||||||
|
#EXTINF:1.001,
|
||||||
|
#EXT-X-BYTERANGE:99313@1143
|
||||||
|
bear-640x360-video.mp4
|
||||||
|
#EXTINF:1.001,
|
||||||
|
#EXT-X-BYTERANGE:122340
|
||||||
|
bear-640x360-video.mp4
|
||||||
|
#EXTINF:0.734,
|
||||||
|
#EXT-X-BYTERANGE:80067
|
||||||
|
bear-640x360-video.mp4
|
||||||
|
#EXT-X-ENDLIST
|
|
@ -1,44 +0,0 @@
|
||||||
// Copyright 2018 Google LLC. All rights reserved.
|
|
||||||
//
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file or at
|
|
||||||
// https://developers.google.com/open-source/licenses/bsd
|
|
||||||
|
|
||||||
#include "packager/media/base/fairplay_pssh_generator.h"
|
|
||||||
|
|
||||||
#include "packager/media/base/protection_system_ids.h"
|
|
||||||
|
|
||||||
namespace shaka {
|
|
||||||
namespace media {
|
|
||||||
namespace {
|
|
||||||
const uint8_t kFairPlayPsshBoxVersion = 1;
|
|
||||||
} // namespace
|
|
||||||
|
|
||||||
FairPlayPsshGenerator::FairPlayPsshGenerator()
|
|
||||||
: PsshGenerator(std::vector<uint8_t>(std::begin(kFairPlaySystemId),
|
|
||||||
std::end(kFairPlaySystemId)),
|
|
||||||
kFairPlayPsshBoxVersion) {}
|
|
||||||
|
|
||||||
FairPlayPsshGenerator::~FairPlayPsshGenerator() = default;
|
|
||||||
|
|
||||||
bool FairPlayPsshGenerator::SupportMultipleKeys() {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
base::Optional<std::vector<uint8_t>>
|
|
||||||
FairPlayPsshGenerator::GeneratePsshDataFromKeyIdAndKey(
|
|
||||||
const std::vector<uint8_t>& key_id,
|
|
||||||
const std::vector<uint8_t>& key) const {
|
|
||||||
NOTIMPLEMENTED();
|
|
||||||
return base::nullopt;
|
|
||||||
}
|
|
||||||
|
|
||||||
base::Optional<std::vector<uint8_t>>
|
|
||||||
FairPlayPsshGenerator::GeneratePsshDataFromKeyIds(
|
|
||||||
const std::vector<std::vector<uint8_t>>& key_ids) const {
|
|
||||||
// Intentionally empty PSSH data for FairPlay.
|
|
||||||
return std::vector<uint8_t>();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace media
|
|
||||||
} // namespace shaka
|
|
|
@ -1,42 +0,0 @@
|
||||||
// Copyright 2018 Google LLC. All rights reserved.
|
|
||||||
//
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file or at
|
|
||||||
// https://developers.google.com/open-source/licenses/bsd
|
|
||||||
|
|
||||||
#ifndef PACKAGER_MEDIA_BASE_FAIRPLAY_PSSH_GENERATOR_H_
|
|
||||||
#define PACKAGER_MEDIA_BASE_FAIRPLAY_PSSH_GENERATOR_H_
|
|
||||||
|
|
||||||
#include "packager/media/base/pssh_generator.h"
|
|
||||||
|
|
||||||
namespace shaka {
|
|
||||||
namespace media {
|
|
||||||
|
|
||||||
class FairPlayPsshGenerator : public PsshGenerator {
|
|
||||||
public:
|
|
||||||
FairPlayPsshGenerator();
|
|
||||||
~FairPlayPsshGenerator() override;
|
|
||||||
|
|
||||||
/// @name PsshGenerator implemetation overrides.
|
|
||||||
/// @{
|
|
||||||
bool SupportMultipleKeys() override;
|
|
||||||
/// @}
|
|
||||||
|
|
||||||
private:
|
|
||||||
FairPlayPsshGenerator& operator=(const FairPlayPsshGenerator&) = delete;
|
|
||||||
FairPlayPsshGenerator(const FairPlayPsshGenerator&) = delete;
|
|
||||||
|
|
||||||
// PsshGenerator implemetation overrides.
|
|
||||||
|
|
||||||
base::Optional<std::vector<uint8_t>> GeneratePsshDataFromKeyIds(
|
|
||||||
const std::vector<std::vector<uint8_t>>& key_ids) const override;
|
|
||||||
|
|
||||||
base::Optional<std::vector<uint8_t>> GeneratePsshDataFromKeyIdAndKey(
|
|
||||||
const std::vector<uint8_t>& key_id,
|
|
||||||
const std::vector<uint8_t>& key) const override;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace media
|
|
||||||
} // namespace shaka
|
|
||||||
|
|
||||||
#endif // PACKAGER_MEDIA_BASE_FAIRPLAY_PSSH_GENERATOR_H_
|
|
|
@ -8,8 +8,8 @@
|
||||||
|
|
||||||
#include "packager/base/logging.h"
|
#include "packager/base/logging.h"
|
||||||
#include "packager/media/base/common_pssh_generator.h"
|
#include "packager/media/base/common_pssh_generator.h"
|
||||||
#include "packager/media/base/fairplay_pssh_generator.h"
|
|
||||||
#include "packager/media/base/playready_pssh_generator.h"
|
#include "packager/media/base/playready_pssh_generator.h"
|
||||||
|
#include "packager/media/base/protection_system_ids.h"
|
||||||
#include "packager/media/base/widevine_pssh_generator.h"
|
#include "packager/media/base/widevine_pssh_generator.h"
|
||||||
#include "packager/status_macros.h"
|
#include "packager/status_macros.h"
|
||||||
|
|
||||||
|
@ -30,7 +30,8 @@ KeySource::KeySource(int protection_systems_flags, FourCC protection_scheme) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (protection_systems_flags & FAIRPLAY_PROTECTION_SYSTEM_FLAG) {
|
if (protection_systems_flags & FAIRPLAY_PROTECTION_SYSTEM_FLAG) {
|
||||||
pssh_generators_.emplace_back(new FairPlayPsshGenerator());
|
no_pssh_systems_.emplace_back(std::begin(kFairPlaySystemId),
|
||||||
|
std::end(kFairPlaySystemId));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -60,6 +61,14 @@ Status KeySource::UpdateProtectionSystemInfo(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (const auto& no_pssh_system : no_pssh_systems_) {
|
||||||
|
ProtectionSystemSpecificInfo info;
|
||||||
|
info.system_id = no_pssh_system;
|
||||||
|
for (const EncryptionKeyMap::value_type& pair : *encryption_key_map) {
|
||||||
|
pair.second->key_system_info.push_back(info);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return Status::OK;
|
return Status::OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -92,6 +92,7 @@ class KeySource {
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<std::unique_ptr<PsshGenerator>> pssh_generators_;
|
std::vector<std::unique_ptr<PsshGenerator>> pssh_generators_;
|
||||||
|
std::vector<std::vector<uint8_t>> no_pssh_systems_;
|
||||||
|
|
||||||
DISALLOW_COPY_AND_ASSIGN(KeySource);
|
DISALLOW_COPY_AND_ASSIGN(KeySource);
|
||||||
};
|
};
|
||||||
|
|
|
@ -46,8 +46,6 @@
|
||||||
'decryptor_source.cc',
|
'decryptor_source.cc',
|
||||||
'decryptor_source.h',
|
'decryptor_source.h',
|
||||||
'encryption_config.h',
|
'encryption_config.h',
|
||||||
'fairplay_pssh_generator.cc',
|
|
||||||
'fairplay_pssh_generator.h',
|
|
||||||
'fourccs.h',
|
'fourccs.h',
|
||||||
'http_key_fetcher.cc',
|
'http_key_fetcher.cc',
|
||||||
'http_key_fetcher.h',
|
'http_key_fetcher.h',
|
||||||
|
|
|
@ -268,10 +268,15 @@ Status MP4Muxer::DelayInitializeMuxer() {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (stream->is_encrypted() && options().mp4_params.include_pssh_in_stream) {
|
if (stream->is_encrypted() && options().mp4_params.include_pssh_in_stream) {
|
||||||
|
moov->pssh.clear();
|
||||||
const auto& key_system_info = stream->encryption_config().key_system_info;
|
const auto& key_system_info = stream->encryption_config().key_system_info;
|
||||||
moov->pssh.resize(key_system_info.size());
|
for (const ProtectionSystemSpecificInfo& system : key_system_info) {
|
||||||
for (size_t j = 0; j < key_system_info.size(); j++)
|
if (system.psshs.empty())
|
||||||
moov->pssh[j].raw_box = key_system_info[j].psshs;
|
continue;
|
||||||
|
ProtectionSystemSpecificHeader pssh;
|
||||||
|
pssh.raw_box = system.psshs;
|
||||||
|
moov->pssh.push_back(pssh);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -278,11 +278,15 @@ void Segmenter::FinalizeFragmentForKeyRotation(
|
||||||
bool fragment_encrypted,
|
bool fragment_encrypted,
|
||||||
const EncryptionConfig& encryption_config) {
|
const EncryptionConfig& encryption_config) {
|
||||||
if (options_.mp4_params.include_pssh_in_stream) {
|
if (options_.mp4_params.include_pssh_in_stream) {
|
||||||
const std::vector<ProtectionSystemSpecificInfo>& system_info =
|
moof_->pssh.clear();
|
||||||
encryption_config.key_system_info;
|
const auto& key_system_info = encryption_config.key_system_info;
|
||||||
moof_->pssh.resize(system_info.size());
|
for (const ProtectionSystemSpecificInfo& system : key_system_info) {
|
||||||
for (size_t i = 0; i < system_info.size(); i++)
|
if (system.psshs.empty())
|
||||||
moof_->pssh[i].raw_box = system_info[i].psshs;
|
continue;
|
||||||
|
ProtectionSystemSpecificHeader pssh;
|
||||||
|
pssh.raw_box = system.psshs;
|
||||||
|
moof_->pssh.push_back(pssh);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
LOG(WARNING)
|
LOG(WARNING)
|
||||||
<< "Key rotation and no pssh in stream may not work well together.";
|
<< "Key rotation and no pssh in stream may not work well together.";
|
||||||
|
|
|
@ -352,7 +352,7 @@ void AddContentProtectionElementsHelperTemplated(
|
||||||
if (entry.has_name_version())
|
if (entry.has_name_version())
|
||||||
drm_content_protection.value = entry.name_version();
|
drm_content_protection.value = entry.name_version();
|
||||||
|
|
||||||
if (entry.has_pssh()) {
|
if (!entry.pssh().empty()) {
|
||||||
std::string base64_encoded_pssh;
|
std::string base64_encoded_pssh;
|
||||||
base::Base64Encode(
|
base::Base64Encode(
|
||||||
base::StringPiece(entry.pssh().data(), entry.pssh().size()),
|
base::StringPiece(entry.pssh().data(), entry.pssh().size()),
|
||||||
|
|
Loading…
Reference in New Issue