1 /*
2 **
3 ** Copyright 2017, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 **     http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17 
18 #pragma once
19 
20 #include <map>
21 #include <vector>
22 
23 #include <hardware/keymaster1.h>
24 #include <hardware/keymaster_defs.h>
25 
26 #include <keymaster/UniquePtr.h>
27 #include <keymaster/android_keymaster_utils.h>
28 #include <keymaster/authorization_set.h>
29 #include <keymaster/key_factory.h>
30 
31 #include "ec_keymaster1_key.h"
32 #include "keymaster1_engine.h"
33 #include "keymaster_passthrough_engine.h"
34 #include "keymaster_passthrough_key.h"
35 #include "rsa_keymaster1_key.h"
36 
37 namespace keymaster {
38 
39 class Keymaster1LegacySupport {
40   public:
41     typedef std::pair<keymaster_algorithm_t, keymaster_purpose_t> AlgPurposePair;
42     typedef std::map<AlgPurposePair, std::vector<keymaster_digest_t>> DigestMap;
43 
44     // NOLINTNEXTLINE(google-explicit-constructor)
45     Keymaster1LegacySupport(const keymaster1_device_t* dev);
46 
47     bool RequiresSoftwareDigesting(const AuthorizationSet& key_description) const;
48     bool RequiresSoftwareDigesting(const keymaster_digest_t digest,
49                                    const AuthProxy& key_description) const;
50 
51   private:
52     DigestMap device_digests_;
53     bool supports_all_;
54 };
55 
56 class SoftwareKeyBlobMaker;
57 
58 template <typename KM1_SOFTDIGEST_FACTORY> class Keymaster1ArbitrationFactory : public KeyFactory {
59   public:
60     template <typename... SOFT_FACTORY_CONSRUCTOR_ARGS>
Keymaster1ArbitrationFactory(const KeymasterPassthroughEngine * ptengine,keymaster_algorithm_t algorithm,const keymaster1_device_t * dev,SOFT_FACTORY_CONSRUCTOR_ARGS &&...args)61     Keymaster1ArbitrationFactory(const KeymasterPassthroughEngine* ptengine,
62                                  keymaster_algorithm_t algorithm, const keymaster1_device_t* dev,
63                                  SOFT_FACTORY_CONSRUCTOR_ARGS&&... args)
64         : software_digest_factory_(forward<SOFT_FACTORY_CONSRUCTOR_ARGS>(args)...),
65           passthrough_factory_(ptengine, algorithm), legacy_support_(dev) {}
GenerateKey(const AuthorizationSet & key_description,UniquePtr<Key> attest_key,const KeymasterBlob & issuer_subject,KeymasterKeyBlob * key_blob,AuthorizationSet * hw_enforced,AuthorizationSet * sw_enforced,CertificateChain * cert_chain)66     keymaster_error_t GenerateKey(const AuthorizationSet& key_description,
67                                   UniquePtr<Key> attest_key,  //
68                                   const KeymasterBlob& issuer_subject,
69                                   KeymasterKeyBlob* key_blob,     //
70                                   AuthorizationSet* hw_enforced,  //
71                                   AuthorizationSet* sw_enforced,
72                                   CertificateChain* cert_chain) const {
73         if (legacy_support_.RequiresSoftwareDigesting(key_description)) {
74             return software_digest_factory_.GenerateKey(key_description, move(attest_key),
75                                                         issuer_subject, key_blob, hw_enforced,
76                                                         sw_enforced, cert_chain);
77         } else {
78             return passthrough_factory_.GenerateKey(key_description, move(attest_key),
79                                                     issuer_subject, key_blob, hw_enforced,
80                                                     sw_enforced, cert_chain);
81         }
82     }
83 
ImportKey(const AuthorizationSet & key_description,keymaster_key_format_t input_key_material_format,const KeymasterKeyBlob & input_key_material,UniquePtr<Key> attest_key,const KeymasterBlob & issuer_subject,KeymasterKeyBlob * output_key_blob,AuthorizationSet * hw_enforced,AuthorizationSet * sw_enforced,CertificateChain * cert_chain)84     keymaster_error_t ImportKey(const AuthorizationSet& key_description,
85                                 keymaster_key_format_t input_key_material_format,
86                                 const KeymasterKeyBlob& input_key_material,
87                                 UniquePtr<Key> attest_key,  //
88                                 const KeymasterBlob& issuer_subject,
89                                 KeymasterKeyBlob* output_key_blob,  //
90                                 AuthorizationSet* hw_enforced,      //
91                                 AuthorizationSet* sw_enforced, CertificateChain* cert_chain) const {
92         if (legacy_support_.RequiresSoftwareDigesting(key_description)) {
93             return software_digest_factory_.ImportKey(
94                 key_description, input_key_material_format, input_key_material, move(attest_key),
95                 issuer_subject, output_key_blob, hw_enforced, sw_enforced, cert_chain);
96         } else {
97             return passthrough_factory_.ImportKey(
98                 key_description, input_key_material_format, input_key_material, move(attest_key),
99                 issuer_subject, output_key_blob, hw_enforced, sw_enforced, cert_chain);
100         }
101     }
102 
LoadKey(KeymasterKeyBlob && key_material,const AuthorizationSet & additional_params,AuthorizationSet && hw_enforced,AuthorizationSet && sw_enforced,UniquePtr<Key> * key)103     keymaster_error_t LoadKey(KeymasterKeyBlob&& key_material,
104                               const AuthorizationSet& additional_params,
105                               AuthorizationSet&& hw_enforced, AuthorizationSet&& sw_enforced,
106                               UniquePtr<Key>* key) const override {
107         keymaster_digest_t digest;
108         if (!additional_params.GetTagValue(TAG_DIGEST, &digest)) {
109             digest = KM_DIGEST_NONE;
110         }
111 
112         if (legacy_support_.RequiresSoftwareDigesting(digest,
113                                                       AuthProxy(hw_enforced, sw_enforced))) {
114             return software_digest_factory_.LoadKey(move(key_material), additional_params,
115                                                     move(hw_enforced), move(sw_enforced), key);
116         } else {
117             return passthrough_factory_.LoadKey(move(key_material), additional_params,
118                                                 move(hw_enforced), move(sw_enforced), key);
119         }
120     }
121 
GetOperationFactory(keymaster_purpose_t)122     OperationFactory* GetOperationFactory(keymaster_purpose_t /*purpose*/) const override {
123         // The passthrough operation factory must not be queried. To get the operation factory for
124         // a Key call key.key_factory()->GetOperationFactory()
125         assert(false);
126         return nullptr;
127     }
128 
129     // Informational methods.
SupportedImportFormats(size_t * format_count)130     const keymaster_key_format_t* SupportedImportFormats(size_t* format_count) const override {
131         *format_count = 0;
132         return nullptr;
133     }
SupportedExportFormats(size_t * format_count)134     const keymaster_key_format_t* SupportedExportFormats(size_t* format_count) const override {
135         *format_count = 0;
136         return nullptr;
137     }
138 
139   private:
140     KM1_SOFTDIGEST_FACTORY software_digest_factory_;
141     KeymasterPassthroughKeyFactory passthrough_factory_;
142     Keymaster1LegacySupport legacy_support_;
143 };
144 
145 template <>
146 keymaster_error_t Keymaster1ArbitrationFactory<EcdsaKeymaster1KeyFactory>::GenerateKey(
147     const AuthorizationSet& key_description,  //
148     UniquePtr<Key> attest_key,                //
149     const KeymasterBlob& issuer_subject,      //
150     KeymasterKeyBlob* key_blob,               //
151     AuthorizationSet* hw_enforced,            //
152     AuthorizationSet* sw_enforced,            //
153     CertificateChain* cert_chain) const;
154 
155 template <>
156 keymaster_error_t Keymaster1ArbitrationFactory<EcdsaKeymaster1KeyFactory>::LoadKey(
157     KeymasterKeyBlob&& key_material, const AuthorizationSet& additional_params,
158     AuthorizationSet&& hw_enforced, AuthorizationSet&& sw_enforced, UniquePtr<Key>* key) const;
159 
160 template <>
161 keymaster_error_t Keymaster1ArbitrationFactory<RsaKeymaster1KeyFactory>::LoadKey(
162     KeymasterKeyBlob&& key_material, const AuthorizationSet& additional_params,
163     AuthorizationSet&& hw_enforced, AuthorizationSet&& sw_enforced, UniquePtr<Key>* key) const;
164 
165 }  // namespace keymaster
166