1 /*
2 * Copyright (C) 2021 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at:
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *
16 */
17
18 #include <AndroidKeymaster4Device.h>
19 #include <android/hardware/keymaster/4.0/IKeymasterDevice.h>
20 #include <fuzzer/FuzzedDataProvider.h>
21 #include <keymasterV4_0/authorization_set.h>
22
23 namespace keymaster::V4_0::ng::fuzzer {
24
25 using ::android::hardware::hidl_string;
26 using ::android::hardware::keymaster::V4_0::AuthorizationSet;
27 using ::android::hardware::keymaster::V4_0::AuthorizationSetBuilder;
28 using ::android::hardware::keymaster::V4_0::Digest;
29 using ::android::hardware::keymaster::V4_0::KeyFormat;
30 using ::android::hardware::keymaster::V4_0::KeyPurpose;
31 using ::android::hardware::keymaster::V4_0::PaddingMode;
32
33 constexpr SecurityLevel kSecurityLevel[] = {
34 SecurityLevel::SOFTWARE,
35 SecurityLevel::TRUSTED_ENVIRONMENT,
36 SecurityLevel::STRONGBOX,
37 };
38
39 constexpr PaddingMode kPaddingMode[] = {
40 PaddingMode::NONE,
41 PaddingMode::RSA_OAEP,
42 PaddingMode::RSA_PSS,
43 PaddingMode::RSA_PKCS1_1_5_ENCRYPT,
44 PaddingMode::RSA_PKCS1_1_5_SIGN,
45 PaddingMode::PKCS7,
46 };
47
48 constexpr Digest kDigest[] = {
49 Digest::NONE, Digest::MD5, Digest::SHA1, Digest::SHA_2_224,
50 Digest::SHA_2_256, Digest::SHA_2_384, Digest::SHA_2_512,
51 };
52
53 constexpr KeyFormat kKeyFormat[] = {
54 KeyFormat::X509,
55 KeyFormat::PKCS8,
56 KeyFormat::RAW,
57 };
58
59 constexpr KeyPurpose kKeyPurpose[] = {
60 KeyPurpose::ENCRYPT, KeyPurpose::DECRYPT, KeyPurpose::SIGN,
61 KeyPurpose::VERIFY, KeyPurpose::WRAP_KEY,
62 };
63
64 constexpr uint32_t kRSAKeySize[] = {1024, 2048, 3072, 4096};
65 constexpr uint32_t kECCKeySize[] = {224, 256, 384, 521};
66 constexpr size_t kMinBytes = 0;
67 constexpr size_t kMaxBytes = 100;
68
69 class KeyMaster4DeviceFuzzer {
70 public:
71 bool init(const uint8_t* data, size_t size);
72 void process();
73
74 private:
75 AuthorizationSet getAuthorizationSet();
76 sp<IKeymasterDevice> mKeymaster = nullptr;
77 std::unique_ptr<FuzzedDataProvider> mFdp = nullptr;
78 };
79
getAuthorizationSet()80 AuthorizationSet KeyMaster4DeviceFuzzer::getAuthorizationSet() {
81 auto keyMasterFunction = mFdp->PickValueInArray<
82 const std::function<android::hardware::keymaster::V4_0::AuthorizationSet()>>({
83 [&]() {
84 return AuthorizationSetBuilder()
85 .RsaSigningKey(mFdp->PickValueInArray(kRSAKeySize),
86 mFdp->ConsumeIntegral<uint32_t>())
87 .Digest(mFdp->PickValueInArray(kDigest))
88 .Padding(mFdp->PickValueInArray(kPaddingMode));
89 },
90 [&]() {
91 return AuthorizationSetBuilder()
92 .EcdsaKey(mFdp->PickValueInArray(kECCKeySize))
93 .Digest(mFdp->PickValueInArray(kDigest))
94 .Padding(mFdp->PickValueInArray(kPaddingMode));
95 },
96 [&]() {
97 return AuthorizationSetBuilder()
98 .AesKey(mFdp->PickValueInArray(kECCKeySize))
99 .Digest(mFdp->PickValueInArray(kDigest))
100 .Padding(mFdp->PickValueInArray(kPaddingMode));
101 },
102 [&]() {
103 return AuthorizationSetBuilder()
104 .TripleDesKey(mFdp->PickValueInArray(kRSAKeySize))
105 .Digest(mFdp->PickValueInArray(kDigest))
106 .Padding(mFdp->PickValueInArray(kPaddingMode));
107 },
108 [&]() {
109 return AuthorizationSetBuilder()
110 .HmacKey(mFdp->PickValueInArray(kRSAKeySize))
111 .Digest(mFdp->PickValueInArray(kDigest))
112 .Padding(mFdp->PickValueInArray(kPaddingMode));
113 },
114 [&]() {
115 return AuthorizationSetBuilder()
116 .RsaEncryptionKey(mFdp->PickValueInArray(kRSAKeySize),
117 mFdp->ConsumeIntegral<uint64_t>())
118 .Digest(mFdp->PickValueInArray(kDigest))
119 .Padding(mFdp->PickValueInArray(kPaddingMode));
120 },
121 [&]() {
122 return AuthorizationSetBuilder()
123 .EcdsaSigningKey(mFdp->PickValueInArray(kRSAKeySize))
124 .Digest(mFdp->PickValueInArray(kDigest))
125 .Padding(mFdp->PickValueInArray(kPaddingMode));
126 },
127 [&]() {
128 return AuthorizationSetBuilder()
129 .AesEncryptionKey(mFdp->PickValueInArray(kECCKeySize))
130 .Digest(mFdp->PickValueInArray(kDigest))
131 .Padding(mFdp->PickValueInArray(kPaddingMode));
132 },
133 [&]() {
134 return AuthorizationSetBuilder()
135 .TripleDesEncryptionKey(mFdp->PickValueInArray(kRSAKeySize))
136 .Digest(mFdp->PickValueInArray(kDigest))
137 .Padding(mFdp->PickValueInArray(kPaddingMode));
138 },
139 [&]() {
140 return AuthorizationSetBuilder()
141 .RsaKey(mFdp->PickValueInArray(kRSAKeySize), mFdp->ConsumeIntegral<uint64_t>())
142 .Digest(mFdp->PickValueInArray(kDigest))
143 .Padding(mFdp->PickValueInArray(kPaddingMode));
144 },
145 });
146 return keyMasterFunction();
147 }
148
init(const uint8_t * data,size_t size)149 bool KeyMaster4DeviceFuzzer::init(const uint8_t* data, size_t size) {
150 mFdp = std::make_unique<FuzzedDataProvider>(data, size);
151 mKeymaster = CreateKeymasterDevice(mFdp->PickValueInArray(kSecurityLevel));
152 if (!mKeymaster) {
153 return false;
154 }
155 return true;
156 }
157
process()158 void KeyMaster4DeviceFuzzer::process() {
159 std::vector<uint8_t> dataVec =
160 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
161 mKeymaster->addRngEntropy(dataVec);
162
163 hidl_vec<uint8_t> keyBlob = {};
164 mKeymaster->generateKey(getAuthorizationSet().hidl_data(),
165 [&]([[maybe_unused]] ErrorCode hidlError,
166 const hidl_vec<uint8_t>& hidlKeyBlob,
167 [[maybe_unused]] const KeyCharacteristics& hidlKeyCharacteristics) {
168 keyBlob = hidlKeyBlob;
169 });
170
171 mKeymaster->attestKey(
172 keyBlob, getAuthorizationSet().hidl_data(),
173 [&]([[maybe_unused]] ErrorCode hidlError,
174 [[maybe_unused]] const hidl_vec<hidl_vec<uint8_t>>& hidlCertificateChain) {});
175
176 mKeymaster->upgradeKey(keyBlob, hidl_vec<KeyParameter>(),
177 [&]([[maybe_unused]] ErrorCode error,
178 [[maybe_unused]] const hidl_vec<uint8_t>& upgraded_blob) {});
179
180 std::vector<uint8_t> clientId =
181 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
182 std::vector<uint8_t> appData =
183 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
184 mKeymaster->getKeyCharacteristics(
185 keyBlob, clientId, appData,
186 [&]([[maybe_unused]] ErrorCode hidlError,
187 [[maybe_unused]] const KeyCharacteristics& hidlKeyCharacteristics) {});
188
189 KeyFormat keyFormat = mFdp->PickValueInArray(kKeyFormat);
190 std::vector<uint8_t> keyData;
191 keyData =
192 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
193 ErrorCode importKeyError;
194 if (mKeymaster
195 ->importKey(getAuthorizationSet().hidl_data(), keyFormat, keyData,
196 [&]([[maybe_unused]] ErrorCode hidlError,
197 [[maybe_unused]] const hidl_vec<uint8_t>& hidlKeyBlob,
198 [[maybe_unused]] const KeyCharacteristics& hidlKeyCharacteristics) {
199 importKeyError = hidlError;
200 })
201 .isOk()) {
202 if (importKeyError == ErrorCode::OK) {
203 abort();
204 }
205 }
206
207 std::vector<uint8_t> wrappedKey, wrappingKey, maskingKey;
208 wrappedKey =
209 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
210 wrappingKey =
211 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
212 maskingKey =
213 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
214 uint64_t passwordSid = mFdp->ConsumeIntegral<uint64_t>();
215 uint64_t biometricSid = mFdp->ConsumeIntegral<uint64_t>();
216 mKeymaster->importWrappedKey(
217 wrappedKey, wrappingKey, maskingKey, getAuthorizationSet().hidl_data(), passwordSid,
218 biometricSid,
219 [&]([[maybe_unused]] ErrorCode hidlError,
220 [[maybe_unused]] const hidl_vec<uint8_t>& hidlKeyBlob,
221 [[maybe_unused]] const KeyCharacteristics& hidlKeyCharacteristics) {});
222
223 std::vector<uint8_t> keyBlobExportKey =
224 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
225 mKeymaster->exportKey(keyFormat, keyBlobExportKey, clientId, appData,
226 [&]([[maybe_unused]] ErrorCode hidlErrorCode,
227 [[maybe_unused]] const hidl_vec<uint8_t>& hidlKeyMaterial) {});
228
229 KeyPurpose keyPurpose = mFdp->PickValueInArray(kKeyPurpose);
230 mKeymaster->begin(keyPurpose, keyBlob, getAuthorizationSet().hidl_data(), HardwareAuthToken(),
231 [&]([[maybe_unused]] ErrorCode hidlError,
232 [[maybe_unused]] const hidl_vec<KeyParameter>& hidlOutParams,
233 [[maybe_unused]] uint64_t hidlOpHandle) {});
234
235 uint64_t operationHandle = mFdp->ConsumeIntegral<uint64_t>();
236 std::vector<uint8_t> input =
237 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
238 mKeymaster->update(operationHandle, getAuthorizationSet().hidl_data(), input,
239 HardwareAuthToken(), VerificationToken(),
240 [&]([[maybe_unused]] ErrorCode hidlError,
241 [[maybe_unused]] uint32_t hidlInputConsumed,
242 [[maybe_unused]] const hidl_vec<KeyParameter>& hidlOutParams,
243 [[maybe_unused]] const hidl_vec<uint8_t>& hidlOutput) {});
244
245 std::vector<uint8_t> signature =
246 mFdp->ConsumeBytes<uint8_t>(mFdp->ConsumeIntegralInRange<size_t>(kMinBytes, kMaxBytes));
247 mKeymaster->finish(operationHandle, getAuthorizationSet().hidl_data(), input, signature,
248 HardwareAuthToken(), VerificationToken(),
249 [&]([[maybe_unused]] ErrorCode hidlError,
250 [[maybe_unused]] const hidl_vec<KeyParameter>& hidlOutParams,
251 [[maybe_unused]] const hidl_vec<uint8_t>& hidlOutput) {});
252
253 mKeymaster->deleteKey(keyBlob);
254 mKeymaster->deleteAllKeys();
255 mKeymaster->abort(mFdp->ConsumeIntegral<uint64_t>());
256 }
257
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)258 extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
259 KeyMaster4DeviceFuzzer km4DeviceFuzzer;
260 if (km4DeviceFuzzer.init(data, size)) {
261 km4DeviceFuzzer.process();
262 }
263 return 0;
264 }
265 } // namespace keymaster::V4_0::ng::fuzzer
266