Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1237)

Side by Side Diff: content/child/webcrypto/openssl/sha_openssl.cc

Issue 379383002: Refactor WebCrypto code (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Address rsleevi comments Created 6 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include <vector>
6 #include <openssl/evp.h>
7 #include <openssl/sha.h>
8
9 #include "base/logging.h"
10 #include "content/child/webcrypto/algorithm_implementation.h"
11 #include "content/child/webcrypto/crypto_data.h"
12 #include "content/child/webcrypto/openssl/util_openssl.h"
13 #include "content/child/webcrypto/status.h"
14 #include "content/child/webcrypto/webcrypto_util.h"
15 #include "crypto/openssl_util.h"
16 #include "crypto/scoped_openssl_types.h"
17
18 namespace content {
19
20 namespace webcrypto {
21
22 namespace {
23
24 class DigestorOpenSsl : public blink::WebCryptoDigestor {
25 public:
26 explicit DigestorOpenSsl(blink::WebCryptoAlgorithmId algorithm_id)
27 : initialized_(false),
28 digest_context_(EVP_MD_CTX_create()),
29 algorithm_id_(algorithm_id) {}
30
31 virtual bool consume(const unsigned char* data, unsigned int size) {
32 return ConsumeWithStatus(data, size).IsSuccess();
33 }
34
35 Status ConsumeWithStatus(const unsigned char* data, unsigned int size) {
36 crypto::OpenSSLErrStackTracer err_tracer(FROM_HERE);
37 Status error = Init();
38 if (!error.IsSuccess())
39 return error;
40
41 if (!EVP_DigestUpdate(digest_context_.get(), data, size))
42 return Status::OperationError();
43
44 return Status::Success();
45 }
46
47 virtual bool finish(unsigned char*& result_data,
48 unsigned int& result_data_size) {
49 Status error = FinishInternal(result_, &result_data_size);
50 if (!error.IsSuccess())
51 return false;
52 result_data = result_;
53 return true;
54 }
55
56 Status FinishWithVectorAndStatus(std::vector<uint8>* result) {
57 const int hash_expected_size = EVP_MD_CTX_size(digest_context_.get());
58 result->resize(hash_expected_size);
59 unsigned char* const hash_buffer = Uint8VectorStart(result);
60 unsigned int hash_buffer_size; // ignored
61 return FinishInternal(hash_buffer, &hash_buffer_size);
62 }
63
64 private:
65 Status Init() {
66 if (initialized_)
67 return Status::Success();
68
69 const EVP_MD* digest_algorithm = GetDigest(algorithm_id_);
70 if (!digest_algorithm)
71 return Status::ErrorUnexpected();
72
73 if (!digest_context_.get())
74 return Status::OperationError();
75
76 if (!EVP_DigestInit_ex(digest_context_.get(), digest_algorithm, NULL))
77 return Status::OperationError();
78
79 initialized_ = true;
80 return Status::Success();
81 }
82
83 Status FinishInternal(unsigned char* result, unsigned int* result_size) {
84 crypto::OpenSSLErrStackTracer err_tracer(FROM_HERE);
85 Status error = Init();
86 if (!error.IsSuccess())
87 return error;
88
89 const int hash_expected_size = EVP_MD_CTX_size(digest_context_.get());
90 if (hash_expected_size <= 0)
91 return Status::ErrorUnexpected();
92 DCHECK_LE(hash_expected_size, EVP_MAX_MD_SIZE);
93
94 if (!EVP_DigestFinal_ex(digest_context_.get(), result, result_size) ||
95 static_cast<int>(*result_size) != hash_expected_size)
96 return Status::OperationError();
97
98 return Status::Success();
99 }
100
101 bool initialized_;
102 crypto::ScopedEVP_MD_CTX digest_context_;
103 blink::WebCryptoAlgorithmId algorithm_id_;
104 unsigned char result_[EVP_MAX_MD_SIZE];
105 };
106
107 class ShaImplementation : public AlgorithmImplementation {
108 public:
109 virtual Status Digest(const blink::WebCryptoAlgorithm& algorithm,
110 const CryptoData& data,
111 std::vector<uint8>* buffer) const OVERRIDE {
112 DigestorOpenSsl digestor(algorithm.id());
113 Status error = digestor.ConsumeWithStatus(data.bytes(), data.byte_length());
114 // http://crbug.com/366427: the spec does not define any other failures for
115 // digest, so none of the subsequent errors are spec compliant.
116 if (!error.IsSuccess())
117 return error;
118 return digestor.FinishWithVectorAndStatus(buffer);
119 }
120 };
121
122 } // namespace
123
124 AlgorithmImplementation* CreatePlatformShaImplementation() {
125 return new ShaImplementation();
126 }
127
128 scoped_ptr<blink::WebCryptoDigestor> CreatePlatformDigestor(
129 blink::WebCryptoAlgorithmId algorithm) {
130 return scoped_ptr<blink::WebCryptoDigestor>(new DigestorOpenSsl(algorithm));
131 }
132
133 } // namespace webcrypto
134
135 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698