diff options
author | tsepez <tsepez@chromium.org> | 2016-12-16 11:16:19 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2016-12-16 11:16:19 -0800 |
commit | ad3cd2aeff15bd31aa38544063075d910ac63823 (patch) | |
tree | 19b41babfdd6348b0400ad18702215e2d064f558 /core | |
parent | 47fb8c06acd0ff9ea50c8c2d7f67510ea5c28577 (diff) | |
download | pdfium-chromium/2954.tar.xz |
Better tests for password protected documents.chromium/2954
- Add unit tests for sha256 implementation.
- Remove void* types from API in favor of correct actual types.
Review-Url: https://codereview.chromium.org/2577223002
Diffstat (limited to 'core')
-rw-r--r-- | core/fdrm/crypto/fx_crypt.h | 60 | ||||
-rw-r--r-- | core/fdrm/crypto/fx_crypt_sha.cpp | 112 | ||||
-rw-r--r-- | core/fdrm/crypto/fx_crypt_unittest.cpp | 29 | ||||
-rw-r--r-- | core/fpdfapi/parser/cpdf_security_handler.cpp | 123 |
4 files changed, 198 insertions, 126 deletions
diff --git a/core/fdrm/crypto/fx_crypt.h b/core/fdrm/crypto/fx_crypt.h index fe043dcb12..a498f4e19b 100644 --- a/core/fdrm/crypto/fx_crypt.h +++ b/core/fdrm/crypto/fx_crypt.h @@ -13,17 +13,37 @@ extern "C" { #endif -struct CRYPT_rc4_context { +typedef struct { int32_t x; int32_t y; int32_t m[256]; -}; +} CRYPT_rc4_context; -struct CRYPT_md5_context { +typedef struct { uint32_t total[2]; uint32_t state[4]; uint8_t buffer[64]; -}; +} CRYPT_md5_context; + +typedef struct { + unsigned int h[5]; + unsigned char block[64]; + int blkused; + unsigned int lenhi; + unsigned int lenlo; +} CRYPT_sha1_context; + +typedef struct { + uint32_t total[2]; + uint32_t state[8]; + uint8_t buffer[64]; +} CRYPT_sha256_context; + +typedef struct { + uint64_t total[2]; + uint64_t state[8]; + uint8_t buffer[128]; +} CRYPT_sha384_context; void CRYPT_ArcFourCryptBlock(uint8_t* data, uint32_t size, @@ -35,6 +55,7 @@ void CRYPT_ArcFourSetup(CRYPT_rc4_context* context, void CRYPT_ArcFourCrypt(CRYPT_rc4_context* context, uint8_t* data, uint32_t size); + void CRYPT_AESSetKey(void* context, uint32_t blocklen, const uint8_t* key, @@ -49,28 +70,39 @@ void CRYPT_AESEncrypt(void* context, uint8_t* dest, const uint8_t* src, uint32_t size); -void CRYPT_MD5Generate(const uint8_t* data, uint32_t size, uint8_t digest[16]); + void CRYPT_MD5Start(CRYPT_md5_context* context); void CRYPT_MD5Update(CRYPT_md5_context* context, const uint8_t* data, uint32_t size); void CRYPT_MD5Finish(CRYPT_md5_context* context, uint8_t digest[16]); +void CRYPT_MD5Generate(const uint8_t* data, uint32_t size, uint8_t digest[16]); + +void CRYPT_SHA1Start(CRYPT_sha1_context* context); +void CRYPT_SHA1Update(CRYPT_sha1_context* context, + const uint8_t* data, + uint32_t size); +void CRYPT_SHA1Finish(CRYPT_sha1_context* context, uint8_t digest[20]); void CRYPT_SHA1Generate(const uint8_t* data, uint32_t size, uint8_t digest[20]); -void CRYPT_SHA1Start(void* context); -void CRYPT_SHA1Update(void* context, const uint8_t* data, uint32_t size); -void CRYPT_SHA1Finish(void* context, uint8_t digest[20]); + +void CRYPT_SHA256Start(CRYPT_sha256_context* context); +void CRYPT_SHA256Update(CRYPT_sha256_context* context, + const uint8_t* data, + uint32_t size); +void CRYPT_SHA256Finish(CRYPT_sha256_context* context, uint8_t digest[32]); void CRYPT_SHA256Generate(const uint8_t* data, uint32_t size, uint8_t digest[32]); -void CRYPT_SHA256Start(void* context); -void CRYPT_SHA256Update(void* context, const uint8_t* data, uint32_t size); -void CRYPT_SHA256Finish(void* context, uint8_t digest[32]); -void CRYPT_SHA384Start(void* context); -void CRYPT_SHA384Update(void* context, const uint8_t* data, uint32_t size); -void CRYPT_SHA384Finish(void* context, uint8_t digest[48]); + +void CRYPT_SHA384Start(CRYPT_sha384_context* context); +void CRYPT_SHA384Update(CRYPT_sha384_context* context, + const uint8_t* data, + uint32_t size); +void CRYPT_SHA384Finish(CRYPT_sha384_context* context, uint8_t digest[48]); void CRYPT_SHA384Generate(const uint8_t* data, uint32_t size, uint8_t digest[48]); + void CRYPT_SHA512Start(void* context); void CRYPT_SHA512Update(void* context, const uint8_t* data, uint32_t size); void CRYPT_SHA512Finish(void* context, uint8_t digest[64]); diff --git a/core/fdrm/crypto/fx_crypt_sha.cpp b/core/fdrm/crypto/fx_crypt_sha.cpp index 5fb45ab66a..79ff503334 100644 --- a/core/fdrm/crypto/fx_crypt_sha.cpp +++ b/core/fdrm/crypto/fx_crypt_sha.cpp @@ -9,12 +9,6 @@ #ifdef __cplusplus extern "C" { #endif -typedef struct { - unsigned int h[5]; - unsigned char block[64]; - int blkused; - unsigned int lenhi, lenlo; -} SHA_State; #define rol(x, y) (((x) << (y)) | (((unsigned int)x) >> (32 - y))) static void SHA_Core_Init(unsigned int h[5]) { h[0] = 0x67452301; @@ -78,14 +72,16 @@ static void SHATransform(unsigned int* digest, unsigned int* block) { digest[3] += d; digest[4] += e; } -void CRYPT_SHA1Start(void* context) { - SHA_State* s = (SHA_State*)context; + +void CRYPT_SHA1Start(CRYPT_sha1_context* s) { SHA_Core_Init(s->h); s->blkused = 0; s->lenhi = s->lenlo = 0; } -void CRYPT_SHA1Update(void* context, const uint8_t* data, uint32_t size) { - SHA_State* s = (SHA_State*)context; + +void CRYPT_SHA1Update(CRYPT_sha1_context* s, + const uint8_t* data, + uint32_t size) { unsigned char* q = (unsigned char*)data; unsigned int wordblock[16]; int len = size; @@ -114,8 +110,8 @@ void CRYPT_SHA1Update(void* context, const uint8_t* data, uint32_t size) { s->blkused = len; } } -void CRYPT_SHA1Finish(void* context, uint8_t digest[20]) { - SHA_State* s = (SHA_State*)context; + +void CRYPT_SHA1Finish(CRYPT_sha1_context* s, uint8_t digest[20]) { int i; int pad; unsigned char c[64]; @@ -149,16 +145,11 @@ void CRYPT_SHA1Finish(void* context, uint8_t digest[20]) { void CRYPT_SHA1Generate(const uint8_t* data, uint32_t size, uint8_t digest[20]) { - SHA_State s; + CRYPT_sha1_context s; CRYPT_SHA1Start(&s); CRYPT_SHA1Update(&s, data, size); CRYPT_SHA1Finish(&s, digest); } -typedef struct { - uint32_t total[2]; - uint32_t state[8]; - uint8_t buffer[64]; -} sha256_context; #define GET_UINT32(n, b, i) \ { \ (n) = ((uint32_t)(b)[(i)] << 24) | ((uint32_t)(b)[(i) + 1] << 16) | \ @@ -171,8 +162,8 @@ typedef struct { (b)[(i) + 2] = (uint8_t)((n) >> 8); \ (b)[(i) + 3] = (uint8_t)((n)); \ } -void CRYPT_SHA256Start(void* context) { - sha256_context* ctx = (sha256_context*)context; + +void CRYPT_SHA256Start(CRYPT_sha256_context* ctx) { ctx->total[0] = 0; ctx->total[1] = 0; ctx->state[0] = 0x6A09E667; @@ -184,7 +175,8 @@ void CRYPT_SHA256Start(void* context) { ctx->state[6] = 0x1F83D9AB; ctx->state[7] = 0x5BE0CD19; } -static void sha256_process(sha256_context* ctx, const uint8_t data[64]) { + +static void sha256_process(CRYPT_sha256_context* ctx, const uint8_t data[64]) { uint32_t temp1, temp2, W[64]; uint32_t A, B, C, D, E, F, G, H; GET_UINT32(W[0], data, 0); @@ -300,14 +292,15 @@ static void sha256_process(sha256_context* ctx, const uint8_t data[64]) { ctx->state[6] += G; ctx->state[7] += H; } -void CRYPT_SHA256Update(void* context, const uint8_t* input, uint32_t length) { - sha256_context* ctx = (sha256_context*)context; - uint32_t left, fill; - if (!length) { + +void CRYPT_SHA256Update(CRYPT_sha256_context* ctx, + const uint8_t* input, + uint32_t length) { + if (!length) return; - } - left = ctx->total[0] & 0x3F; - fill = 64 - left; + + uint32_t left = ctx->total[0] & 0x3F; + uint32_t fill = 64 - left; ctx->total[0] += length; ctx->total[0] &= 0xFFFFFFFF; if (ctx->total[0] < length) { @@ -329,12 +322,13 @@ void CRYPT_SHA256Update(void* context, const uint8_t* input, uint32_t length) { FXSYS_memcpy((void*)(ctx->buffer + left), (void*)input, length); } } + static const uint8_t sha256_padding[64] = { 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; -void CRYPT_SHA256Finish(void* context, uint8_t digest[32]) { - sha256_context* ctx = (sha256_context*)context; + +void CRYPT_SHA256Finish(CRYPT_sha256_context* ctx, uint8_t digest[32]) { uint32_t last, padn; uint32_t high, low; uint8_t msglen[8]; @@ -355,19 +349,16 @@ void CRYPT_SHA256Finish(void* context, uint8_t digest[32]) { PUT_UINT32(ctx->state[6], digest, 24); PUT_UINT32(ctx->state[7], digest, 28); } + void CRYPT_SHA256Generate(const uint8_t* data, uint32_t size, uint8_t digest[32]) { - sha256_context ctx; + CRYPT_sha256_context ctx; CRYPT_SHA256Start(&ctx); CRYPT_SHA256Update(&ctx, data, size); CRYPT_SHA256Finish(&ctx, digest); } -typedef struct { - uint64_t total[2]; - uint64_t state[8]; - uint8_t buffer[128]; -} sha384_context; + uint64_t FX_ato64i(const FX_CHAR* str) { ASSERT(str); uint64_t ret = 0; @@ -389,12 +380,12 @@ uint64_t FX_ato64i(const FX_CHAR* str) { } return ret; } -void CRYPT_SHA384Start(void* context) { - if (!context) { + +void CRYPT_SHA384Start(CRYPT_sha384_context* ctx) { + if (!ctx) return; - } - sha384_context* ctx = (sha384_context*)context; - FXSYS_memset(ctx, 0, sizeof(sha384_context)); + + FXSYS_memset(ctx, 0, sizeof(CRYPT_sha384_context)); ctx->state[0] = FX_ato64i("cbbb9d5dc1059ed8"); ctx->state[1] = FX_ato64i("629a292a367cd507"); ctx->state[2] = FX_ato64i("9159015a3070dd17"); @@ -404,6 +395,7 @@ void CRYPT_SHA384Start(void* context) { ctx->state[6] = FX_ato64i("db0c2e0d64f98fa7"); ctx->state[7] = FX_ato64i("47b5481dbefa4fa4"); } + #define SHA384_F0(x, y, z) ((x & y) | (z & (x | y))) #define SHA384_F1(x, y, z) (z ^ (x & (y ^ z))) #define SHA384_SHR(x, n) (x >> n) @@ -422,6 +414,9 @@ void CRYPT_SHA384Start(void* context) { d += temp1; \ h = temp1 + temp2; \ } +#define SHA384_R(t) \ + (W[t] = SHA384_S1(W[t - 2]) + W[t - 7] + SHA384_S0(W[t - 15]) + W[t - 16]) + static const uint8_t sha384_padding[128] = { 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -430,8 +425,7 @@ static const uint8_t sha384_padding[128] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, }; -#define SHA384_R(t) \ - (W[t] = SHA384_S1(W[t - 2]) + W[t - 7] + SHA384_S0(W[t - 15]) + W[t - 16]) + static const FX_CHAR* constants[] = { "428a2f98d728ae22", "7137449123ef65cd", "b5c0fbcfec4d3b2f", "e9b5dba58189dbbc", "3956c25bf348b538", "59f111f1b605d019", @@ -479,7 +473,8 @@ static const FX_CHAR* constants[] = { (b)[(i) + 6] = (uint8_t)((n) >> 8); \ (b)[(i) + 7] = (uint8_t)((n)); \ } -static void sha384_process(sha384_context* ctx, const uint8_t data[128]) { + +static void sha384_process(CRYPT_sha384_context* ctx, const uint8_t data[128]) { uint64_t temp1, temp2; uint64_t A, B, C, D, E, F, G, H; uint64_t W[80]; @@ -546,8 +541,10 @@ static void sha384_process(sha384_context* ctx, const uint8_t data[128]) { ctx->state[6] += G; ctx->state[7] += H; } -void CRYPT_SHA384Update(void* context, const uint8_t* input, uint32_t length) { - sha384_context* ctx = (sha384_context*)context; + +void CRYPT_SHA384Update(CRYPT_sha384_context* ctx, + const uint8_t* input, + uint32_t length) { uint32_t left, fill; if (!length) { return; @@ -574,8 +571,8 @@ void CRYPT_SHA384Update(void* context, const uint8_t* input, uint32_t length) { FXSYS_memcpy((void*)(ctx->buffer + left), (void*)input, length); } } -void CRYPT_SHA384Finish(void* context, uint8_t digest[48]) { - sha384_context* ctx = (sha384_context*)context; + +void CRYPT_SHA384Finish(CRYPT_sha384_context* ctx, uint8_t digest[48]) { uint32_t last, padn; uint8_t msglen[16]; FXSYS_memset(msglen, 0, 16); @@ -595,20 +592,22 @@ void CRYPT_SHA384Finish(void* context, uint8_t digest[48]) { PUT_UINT64(ctx->state[4], digest, 32); PUT_UINT64(ctx->state[5], digest, 40); } + void CRYPT_SHA384Generate(const uint8_t* data, uint32_t size, uint8_t digest[64]) { - sha384_context context; + CRYPT_sha384_context context; CRYPT_SHA384Start(&context); CRYPT_SHA384Update(&context, data, size); CRYPT_SHA384Finish(&context, digest); } + void CRYPT_SHA512Start(void* context) { if (!context) { return; } - sha384_context* ctx = (sha384_context*)context; - FXSYS_memset(ctx, 0, sizeof(sha384_context)); + CRYPT_sha384_context* ctx = (CRYPT_sha384_context*)context; + FXSYS_memset(ctx, 0, sizeof(CRYPT_sha384_context)); ctx->state[0] = FX_ato64i("6a09e667f3bcc908"); ctx->state[1] = FX_ato64i("bb67ae8584caa73b"); ctx->state[2] = FX_ato64i("3c6ef372fe94f82b"); @@ -618,11 +617,14 @@ void CRYPT_SHA512Start(void* context) { ctx->state[6] = FX_ato64i("1f83d9abfb41bd6b"); ctx->state[7] = FX_ato64i("5be0cd19137e2179"); } + void CRYPT_SHA512Update(void* context, const uint8_t* data, uint32_t size) { - CRYPT_SHA384Update(context, data, size); + CRYPT_sha384_context* ctx = (CRYPT_sha384_context*)context; + CRYPT_SHA384Update(ctx, data, size); } + void CRYPT_SHA512Finish(void* context, uint8_t digest[64]) { - sha384_context* ctx = (sha384_context*)context; + CRYPT_sha384_context* ctx = (CRYPT_sha384_context*)context; uint32_t last, padn; uint8_t msglen[16]; FXSYS_memset(msglen, 0, 16); @@ -644,14 +646,16 @@ void CRYPT_SHA512Finish(void* context, uint8_t digest[64]) { PUT_UINT64(ctx->state[6], digest, 48); PUT_UINT64(ctx->state[7], digest, 56); } + void CRYPT_SHA512Generate(const uint8_t* data, uint32_t size, uint8_t digest[64]) { - sha384_context context; + CRYPT_sha384_context context; CRYPT_SHA512Start(&context); CRYPT_SHA512Update(&context, data, size); CRYPT_SHA512Finish(&context, digest); } + #ifdef __cplusplus }; #endif diff --git a/core/fdrm/crypto/fx_crypt_unittest.cpp b/core/fdrm/crypto/fx_crypt_unittest.cpp index 6db43fb54a..4e3da6e186 100644 --- a/core/fdrm/crypto/fx_crypt_unittest.cpp +++ b/core/fdrm/crypto/fx_crypt_unittest.cpp @@ -198,3 +198,32 @@ TEST(FXCRYPT, ContextWithStringData) { std::string expected = "900150983cd24fb0d6963f7d28e17f72"; EXPECT_EQ(expected, actual); } + +TEST(FXCRYPT, Sha256TestB1) { + // Example B.1 from FIPS 180-2: one-block message. + const char* input = "abc"; + const uint8_t expected[32] = {0xba, 0x78, 0x16, 0xbf, 0x8f, 0x01, 0xcf, 0xea, + 0x41, 0x41, 0x40, 0xde, 0x5d, 0xae, 0x22, 0x23, + 0xb0, 0x03, 0x61, 0xa3, 0x96, 0x17, 0x7a, 0x9c, + 0xb4, 0x10, 0xff, 0x61, 0xf2, 0x00, 0x15, 0xad}; + uint8_t actual[32]; + CRYPT_SHA256Generate(reinterpret_cast<const uint8_t*>(input), strlen(input), + actual); + for (size_t i = 0; i < 32; ++i) + EXPECT_EQ(expected[i], actual[i]) << " at byte " << i; +} + +TEST(FXCRYPT, Sha256TestB2) { + // Example B.2 from FIPS 180-2: multi-block message. + const char* input = + "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"; + const uint8_t expected[32] = {0x24, 0x8d, 0x6a, 0x61, 0xd2, 0x06, 0x38, 0xb8, + 0xe5, 0xc0, 0x26, 0x93, 0x0c, 0x3e, 0x60, 0x39, + 0xa3, 0x3c, 0xe4, 0x59, 0x64, 0xff, 0x21, 0x67, + 0xf6, 0xec, 0xed, 0xd4, 0x19, 0xdb, 0x06, 0xc1}; + uint8_t actual[32]; + CRYPT_SHA256Generate(reinterpret_cast<const uint8_t*>(input), strlen(input), + actual); + for (size_t i = 0; i < 32; ++i) + EXPECT_EQ(expected[i], actual[i]) << " at byte " << i; +} diff --git a/core/fpdfapi/parser/cpdf_security_handler.cpp b/core/fpdfapi/parser/cpdf_security_handler.cpp index 3f10807caf..5476b5485e 100644 --- a/core/fpdfapi/parser/cpdf_security_handler.cpp +++ b/core/fpdfapi/parser/cpdf_security_handler.cpp @@ -228,21 +228,22 @@ int BigOrder64BitsMod3(uint8_t* data) { } return (int)ret; } + void Revision6_Hash(const uint8_t* password, uint32_t size, const uint8_t* salt, const uint8_t* vector, uint8_t* hash) { - int iBlockSize = 32; - uint8_t sha[128]; - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, password, size); - CRYPT_SHA256Update(sha, salt, 8); - if (vector) { - CRYPT_SHA256Update(sha, vector, 48); - } + CRYPT_sha256_context sha; + CRYPT_SHA256Start(&sha); + CRYPT_SHA256Update(&sha, password, size); + CRYPT_SHA256Update(&sha, salt, 8); + if (vector) + CRYPT_SHA256Update(&sha, vector, 48); + uint8_t digest[32]; - CRYPT_SHA256Finish(sha, digest); + CRYPT_SHA256Finish(&sha, digest); + CFX_ByteTextBuf buf; uint8_t* input = digest; uint8_t* key = input; @@ -251,6 +252,7 @@ void Revision6_Hash(const uint8_t* password, int iBufLen = buf.GetLength(); CFX_ByteTextBuf interDigest; int i = 0; + int iBlockSize = 32; uint8_t* aes = FX_Alloc(uint8_t, 2048); while (i < 64 || i < E[iBufLen - 1] + 32) { int iRoundSize = size + iBlockSize; @@ -304,52 +306,54 @@ void Revision6_Hash(const uint8_t* password, FXSYS_memcpy(hash, input, 32); } } + bool CPDF_SecurityHandler::AES256_CheckPassword(const uint8_t* password, uint32_t size, bool bOwner, uint8_t* key) { - CFX_ByteString okey = - m_pEncryptDict ? m_pEncryptDict->GetStringFor("O") : CFX_ByteString(); - if (okey.GetLength() < 48) { + if (!m_pEncryptDict) return false; - } - CFX_ByteString ukey = - m_pEncryptDict ? m_pEncryptDict->GetStringFor("U") : CFX_ByteString(); - if (ukey.GetLength() < 48) { + + CFX_ByteString okey = m_pEncryptDict->GetStringFor("O"); + if (okey.GetLength() < 48) return false; - } - const uint8_t* pkey = (bOwner ? okey : ukey).raw_str(); - uint8_t sha[128]; + + CFX_ByteString ukey = m_pEncryptDict->GetStringFor("U"); + if (ukey.GetLength() < 48) + return false; + + const uint8_t* pkey = bOwner ? okey.raw_str() : ukey.raw_str(); + CRYPT_sha256_context sha; uint8_t digest[32]; if (m_Revision >= 6) { Revision6_Hash(password, size, (const uint8_t*)pkey + 32, bOwner ? ukey.raw_str() : nullptr, digest); } else { - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, password, size); - CRYPT_SHA256Update(sha, pkey + 32, 8); - if (bOwner) { - CRYPT_SHA256Update(sha, ukey.raw_str(), 48); - } - CRYPT_SHA256Finish(sha, digest); + CRYPT_SHA256Start(&sha); + CRYPT_SHA256Update(&sha, password, size); + CRYPT_SHA256Update(&sha, pkey + 32, 8); + if (bOwner) + CRYPT_SHA256Update(&sha, ukey.raw_str(), 48); + + CRYPT_SHA256Finish(&sha, digest); } - if (FXSYS_memcmp(digest, pkey, 32) != 0) { + if (FXSYS_memcmp(digest, pkey, 32) != 0) return false; - } - if (!key) { + + if (!key) return true; - } + if (m_Revision >= 6) { Revision6_Hash(password, size, (const uint8_t*)pkey + 40, bOwner ? ukey.raw_str() : nullptr, digest); } else { - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, password, size); - CRYPT_SHA256Update(sha, pkey + 40, 8); - if (bOwner) { - CRYPT_SHA256Update(sha, ukey.raw_str(), 48); - } - CRYPT_SHA256Finish(sha, digest); + CRYPT_SHA256Start(&sha); + CRYPT_SHA256Update(&sha, password, size); + CRYPT_SHA256Update(&sha, pkey + 40, 8); + if (bOwner) + CRYPT_SHA256Update(&sha, ukey.raw_str(), 48); + + CRYPT_SHA256Finish(&sha, digest); } CFX_ByteString ekey = m_pEncryptDict ? m_pEncryptDict->GetStringFor(bOwner ? "OE" : "UE") @@ -533,12 +537,12 @@ void CPDF_SecurityHandler::OnCreate(CPDF_Dictionary* pEncryptDict, } if (m_Revision >= 5) { int t = (int)time(nullptr); - uint8_t sha[128]; - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, (uint8_t*)&t, sizeof t); - CRYPT_SHA256Update(sha, m_EncryptKey, 32); - CRYPT_SHA256Update(sha, (uint8_t*)"there", 5); - CRYPT_SHA256Finish(sha, m_EncryptKey); + CRYPT_sha256_context sha; + CRYPT_SHA256Start(&sha); + CRYPT_SHA256Update(&sha, (uint8_t*)&t, sizeof t); + CRYPT_SHA256Update(&sha, m_EncryptKey, 32); + CRYPT_SHA256Update(&sha, (uint8_t*)"there", 5); + CRYPT_SHA256Finish(&sha, m_EncryptKey); AES256_SetPassword(pEncryptDict, user_pass, user_size, false, m_EncryptKey); if (bDefault) { AES256_SetPassword(pEncryptDict, owner_pass, owner_size, true, @@ -632,25 +636,28 @@ void CPDF_SecurityHandler::AES256_SetPassword(CPDF_Dictionary* pEncryptDict, uint32_t size, bool bOwner, const uint8_t* key) { - uint8_t sha[128]; - CRYPT_SHA1Start(sha); - CRYPT_SHA1Update(sha, key, 32); - CRYPT_SHA1Update(sha, (uint8_t*)"hello", 5); + CRYPT_sha1_context sha; + CRYPT_SHA1Start(&sha); + CRYPT_SHA1Update(&sha, key, 32); + CRYPT_SHA1Update(&sha, (uint8_t*)"hello", 5); + uint8_t digest[20]; - CRYPT_SHA1Finish(sha, digest); + CRYPT_SHA1Finish(&sha, digest); + CFX_ByteString ukey = pEncryptDict->GetStringFor("U"); + CRYPT_sha256_context sha2; uint8_t digest1[48]; if (m_Revision >= 6) { Revision6_Hash(password, size, digest, bOwner ? ukey.raw_str() : nullptr, digest1); } else { - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, password, size); - CRYPT_SHA256Update(sha, digest, 8); + CRYPT_SHA256Start(&sha2); + CRYPT_SHA256Update(&sha2, password, size); + CRYPT_SHA256Update(&sha2, digest, 8); if (bOwner) { - CRYPT_SHA256Update(sha, ukey.raw_str(), ukey.GetLength()); + CRYPT_SHA256Update(&sha2, ukey.raw_str(), ukey.GetLength()); } - CRYPT_SHA256Finish(sha, digest1); + CRYPT_SHA256Finish(&sha2, digest1); } FXSYS_memcpy(digest1 + 32, digest, 16); pEncryptDict->SetNewFor<CPDF_String>(bOwner ? "O" : "U", @@ -659,13 +666,13 @@ void CPDF_SecurityHandler::AES256_SetPassword(CPDF_Dictionary* pEncryptDict, Revision6_Hash(password, size, digest + 8, bOwner ? ukey.raw_str() : nullptr, digest1); } else { - CRYPT_SHA256Start(sha); - CRYPT_SHA256Update(sha, password, size); - CRYPT_SHA256Update(sha, digest + 8, 8); + CRYPT_SHA256Start(&sha2); + CRYPT_SHA256Update(&sha2, password, size); + CRYPT_SHA256Update(&sha2, digest + 8, 8); if (bOwner) { - CRYPT_SHA256Update(sha, ukey.raw_str(), ukey.GetLength()); + CRYPT_SHA256Update(&sha2, ukey.raw_str(), ukey.GetLength()); } - CRYPT_SHA256Finish(sha, digest1); + CRYPT_SHA256Finish(&sha2, digest1); } uint8_t* aes = FX_Alloc(uint8_t, 2048); CRYPT_AESSetKey(aes, 16, digest1, 32, true); |