Shaka Packager SDK
Loading...
Searching...
No Matches
aes_pattern_cryptor.cc
1// Copyright 2016 Google LLC. All rights reserved.
2//
3// Use of this source code is governed by a BSD-style
4// license that can be found in the LICENSE file or at
5// https://developers.google.com/open-source/licenses/bsd
6
7#include <packager/media/base/aes_pattern_cryptor.h>
8
9#include <algorithm>
10#include <cstddef>
11#include <cstdint>
12#include <cstring>
13#include <memory>
14#include <utility>
15#include <vector>
16
17#include <absl/log/check.h>
18#include <absl/log/log.h>
19
20#include <packager/macros/crypto.h>
21#include <packager/media/base/aes_cryptor.h>
22
23namespace shaka {
24namespace media {
25
26AesPatternCryptor::AesPatternCryptor(uint8_t crypt_byte_block,
27 uint8_t skip_byte_block,
28 PatternEncryptionMode encryption_mode,
29 ConstantIvFlag constant_iv_flag,
30 std::unique_ptr<AesCryptor> cryptor)
31 : AesCryptor(constant_iv_flag),
32 crypt_byte_block_(crypt_byte_block),
33 skip_byte_block_(skip_byte_block),
34 encryption_mode_(encryption_mode),
35 cryptor_(std::move(cryptor)) {
36 // Treat pattern 0:0 as 1:0.
37 if (crypt_byte_block_ == 0 && skip_byte_block_ == 0)
38 crypt_byte_block_ = 1;
39 DCHECK(cryptor_);
40 DCHECK(!cryptor_->use_constant_iv());
41}
42
43AesPatternCryptor::~AesPatternCryptor() {}
44
45bool AesPatternCryptor::InitializeWithIv(const std::vector<uint8_t>& key,
46 const std::vector<uint8_t>& iv) {
47 return SetIv(iv) && cryptor_->InitializeWithIv(key, iv);
48}
49
50bool AesPatternCryptor::CryptInternal(const uint8_t* text,
51 size_t text_size,
52 uint8_t* crypt_text,
53 size_t* crypt_text_size) {
54 // |crypt_text_size| is always the same as |text_size| for pattern encryption.
55 if (*crypt_text_size < text_size) {
56 LOG(ERROR) << "Expecting output size of at least " << text_size
57 << " bytes.";
58 return false;
59 }
60 *crypt_text_size = text_size;
61
62 while (text_size > 0) {
63 const size_t crypt_byte_size = crypt_byte_block_ * AES_BLOCK_SIZE;
64
65 if (text_size <= crypt_byte_size) {
66 const bool need_encrypt =
67 encryption_mode_ != kSkipIfCryptByteBlockRemaining &&
68 text_size >= AES_BLOCK_SIZE;
69 if (need_encrypt) {
70 // The partial pattern SHALL be followed with the partial 16-byte block
71 // remains unencrypted.
72 const size_t aligned_crypt_byte_size =
73 text_size / AES_BLOCK_SIZE * AES_BLOCK_SIZE;
74 if (!cryptor_->Crypt(text, aligned_crypt_byte_size, crypt_text))
75 return false;
76 text += aligned_crypt_byte_size;
77 text_size -= aligned_crypt_byte_size;
78 crypt_text += aligned_crypt_byte_size;
79 }
80
81 // The remaining bytes are not encrypted.
82 memcpy(crypt_text, text, text_size);
83 return true;
84 }
85
86 if (!cryptor_->Crypt(text, crypt_byte_size, crypt_text))
87 return false;
88 text += crypt_byte_size;
89 text_size -= crypt_byte_size;
90 crypt_text += crypt_byte_size;
91
92 const size_t skip_byte_size = std::min(
93 static_cast<size_t>(skip_byte_block_ * AES_BLOCK_SIZE), text_size);
94 memcpy(crypt_text, text, skip_byte_size);
95 text += skip_byte_size;
96 text_size -= skip_byte_size;
97 crypt_text += skip_byte_size;
98 }
99 return true;
100}
101
102void AesPatternCryptor::SetIvInternal() {
103 CHECK(cryptor_->SetIv(iv()));
104}
105
106} // namespace media
107} // namespace shaka
bool SetIv(const std::vector< uint8_t > &iv)
const std::vector< uint8_t > & iv() const
Definition aes_cryptor.h:86
AesPatternCryptor(uint8_t crypt_byte_block, uint8_t skip_byte_block, PatternEncryptionMode encryption_mode, ConstantIvFlag constant_iv_flag, std::unique_ptr< AesCryptor > cryptor)
bool InitializeWithIv(const std::vector< uint8_t > &key, const std::vector< uint8_t > &iv) override
All the methods that are virtual are virtual for mocking.