blob: 1cd4b2c07b9eed493dc9772b4f52317d6cb20928 [file] [log] [blame]
Andreas Gampedf10b322014-06-11 21:46:05 -07001/*
2 * Copyright (C) 2011 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#include "dex_file_verifier.h"
18
Andreas Gampe8cf9cb32017-07-19 09:28:38 -070019#include <zlib.h>
20
Andreas Gampee6215c02015-08-31 18:54:38 -070021#include <functional>
Ian Rogerse63db272014-07-15 15:36:11 -070022#include <memory>
Andreas Gampedf10b322014-06-11 21:46:05 -070023
Andreas Gampee6215c02015-08-31 18:54:38 -070024#include "base/bit_utils.h"
Andreas Gampedf10b322014-06-11 21:46:05 -070025#include "base/macros.h"
David Sehre1123402018-02-01 02:46:18 -080026#include "base64_test_util.h"
David Sehr0225f8e2018-01-31 08:52:24 +000027#include "descriptors_names.h"
Andreas Gampee6215c02015-08-31 18:54:38 -070028#include "dex_file-inl.h"
Mathieu Chartier79c87da2017-10-10 11:54:29 -070029#include "dex_file_loader.h"
Andreas Gampea5b09a62016-11-17 15:21:22 -080030#include "dex_file_types.h"
David Sehre1123402018-02-01 02:46:18 -080031#include "gtest/gtest.h"
Andreas Gampee6215c02015-08-31 18:54:38 -070032#include "leb128.h"
Mathieu Chartier292567e2017-10-12 13:24:38 -070033#include "standard_dex_file.h"
Andreas Gampedf10b322014-06-11 21:46:05 -070034
35namespace art {
36
David Sehre1123402018-02-01 02:46:18 -080037static constexpr char kLocationString[] = "dex_file_location";
38
Alex Light0ed05212016-05-06 17:36:36 -070039// Make the Dex file version 37.
40static void MakeDexVersion37(DexFile* dex_file) {
41 size_t offset = OFFSETOF_MEMBER(DexFile::Header, magic_) + 6;
42 CHECK_EQ(*(dex_file->Begin() + offset), '5');
43 *(const_cast<uint8_t*>(dex_file->Begin()) + offset) = '7';
44}
45
Andreas Gampee6215c02015-08-31 18:54:38 -070046static void FixUpChecksum(uint8_t* dex_file) {
47 DexFile::Header* header = reinterpret_cast<DexFile::Header*>(dex_file);
48 uint32_t expected_size = header->file_size_;
49 uint32_t adler_checksum = adler32(0L, Z_NULL, 0);
50 const uint32_t non_sum = sizeof(DexFile::Header::magic_) + sizeof(DexFile::Header::checksum_);
51 const uint8_t* non_sum_ptr = dex_file + non_sum;
52 adler_checksum = adler32(adler_checksum, non_sum_ptr, expected_size - non_sum);
53 header->checksum_ = adler_checksum;
54}
55
David Sehre1123402018-02-01 02:46:18 -080056class DexFileVerifierTest : public testing::Test {
Andreas Gampee6215c02015-08-31 18:54:38 -070057 protected:
Aart Bik37d6a3b2016-06-21 18:30:10 -070058 DexFile* GetDexFile(const uint8_t* dex_bytes, size_t length) {
David Sehr733bd4d2017-10-26 10:39:15 -070059 return new StandardDexFile(dex_bytes, length, "tmp", 0, nullptr, nullptr);
Aart Bik37d6a3b2016-06-21 18:30:10 -070060 }
61
Andreas Gampee6215c02015-08-31 18:54:38 -070062 void VerifyModification(const char* dex_file_base64_content,
63 const char* location,
Andreas Gampeca620d72016-11-08 08:09:33 -080064 const std::function<void(DexFile*)>& f,
Andreas Gampee6215c02015-08-31 18:54:38 -070065 const char* expected_error) {
Vladimir Marko59399ab2016-05-03 16:31:52 +010066 size_t length;
Alex Light9c20a142016-08-23 15:05:12 -070067 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(dex_file_base64_content, &length));
Vladimir Marko59399ab2016-05-03 16:31:52 +010068 CHECK(dex_bytes != nullptr);
69 // Note: `dex_file` will be destroyed before `dex_bytes`.
Aart Bik37d6a3b2016-06-21 18:30:10 -070070 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
Andreas Gampee6215c02015-08-31 18:54:38 -070071 f(dex_file.get());
72 FixUpChecksum(const_cast<uint8_t*>(dex_file->Begin()));
73
Aart Bik37d6a3b2016-06-21 18:30:10 -070074 static constexpr bool kVerifyChecksum = true;
Andreas Gampee6215c02015-08-31 18:54:38 -070075 std::string error_msg;
76 bool success = DexFileVerifier::Verify(dex_file.get(),
77 dex_file->Begin(),
78 dex_file->Size(),
79 location,
Aart Bik37d6a3b2016-06-21 18:30:10 -070080 kVerifyChecksum,
Andreas Gampee6215c02015-08-31 18:54:38 -070081 &error_msg);
82 if (expected_error == nullptr) {
83 EXPECT_TRUE(success) << error_msg;
84 } else {
85 EXPECT_FALSE(success) << "Expected " << expected_error;
86 if (!success) {
87 EXPECT_NE(error_msg.find(expected_error), std::string::npos) << error_msg;
88 }
89 }
90 }
Andreas Gampee6215c02015-08-31 18:54:38 -070091};
92
Richard Uhlerfbef44d2014-12-23 09:48:51 -080093static std::unique_ptr<const DexFile> OpenDexFileBase64(const char* base64,
94 const char* location,
95 std::string* error_msg) {
Andreas Gampedf10b322014-06-11 21:46:05 -070096 // decode base64
Mathieu Chartier2cebb242015-04-21 16:50:40 -070097 CHECK(base64 != nullptr);
Andreas Gampedf10b322014-06-11 21:46:05 -070098 size_t length;
Ian Rogers13735952014-10-08 12:43:28 -070099 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(base64, &length));
Mathieu Chartier2cebb242015-04-21 16:50:40 -0700100 CHECK(dex_bytes.get() != nullptr);
Andreas Gampedf10b322014-06-11 21:46:05 -0700101
David Sehre1123402018-02-01 02:46:18 -0800102 // read dex
Richard Uhlerfbef44d2014-12-23 09:48:51 -0800103 std::vector<std::unique_ptr<const DexFile>> tmp;
David Sehre1123402018-02-01 02:46:18 -0800104 const DexFileLoader dex_file_loader;
105 bool success = dex_file_loader.OpenAll(dex_bytes.get(),
106 length,
107 location,
108 /* verify */ true,
109 /* verify_checksum */ true,
110 error_msg,
111 &tmp);
Andreas Gampe672bcf52017-09-19 20:02:42 -0700112 CHECK(success) << *error_msg;
Andreas Gampe833a4852014-05-21 18:46:59 -0700113 EXPECT_EQ(1U, tmp.size());
Richard Uhlerfbef44d2014-12-23 09:48:51 -0800114 std::unique_ptr<const DexFile> dex_file = std::move(tmp[0]);
Andreas Gampe833a4852014-05-21 18:46:59 -0700115 return dex_file;
Andreas Gampedf10b322014-06-11 21:46:05 -0700116}
117
Roland Levillain621b5ea2016-05-18 11:41:33 +0100118// To generate a base64 encoded Dex file (such as kGoodTestDex, below)
119// from Smali files, use:
120//
Ben Gruver14fc9db2017-04-28 15:30:49 -0700121// smali assemble -o classes.dex class1.smali [class2.smali ...]
Roland Levillain621b5ea2016-05-18 11:41:33 +0100122// base64 classes.dex >classes.dex.base64
123
Andreas Gampedf10b322014-06-11 21:46:05 -0700124// For reference.
125static const char kGoodTestDex[] =
126 "ZGV4CjAzNQDrVbyVkxX1HljTznNf95AglkUAhQuFtmKkAgAAcAAAAHhWNBIAAAAAAAAAAAQCAAAN"
127 "AAAAcAAAAAYAAACkAAAAAgAAALwAAAABAAAA1AAAAAQAAADcAAAAAQAAAPwAAACIAQAAHAEAAFoB"
128 "AABiAQAAagEAAIEBAACVAQAAqQEAAL0BAADDAQAAzgEAANEBAADVAQAA2gEAAN8BAAABAAAAAgAA"
129 "AAMAAAAEAAAABQAAAAgAAAAIAAAABQAAAAAAAAAJAAAABQAAAFQBAAAEAAEACwAAAAAAAAAAAAAA"
130 "AAAAAAoAAAABAAEADAAAAAIAAAAAAAAAAAAAAAEAAAACAAAAAAAAAAcAAAAAAAAA8wEAAAAAAAAB"
131 "AAEAAQAAAOgBAAAEAAAAcBADAAAADgACAAAAAgAAAO0BAAAIAAAAYgAAABoBBgBuIAIAEAAOAAEA"
132 "AAADAAY8aW5pdD4ABkxUZXN0OwAVTGphdmEvaW8vUHJpbnRTdHJlYW07ABJMamF2YS9sYW5nL09i"
133 "amVjdDsAEkxqYXZhL2xhbmcvU3RyaW5nOwASTGphdmEvbGFuZy9TeXN0ZW07AARUZXN0AAlUZXN0"
134 "LmphdmEAAVYAAlZMAANmb28AA291dAAHcHJpbnRsbgABAAcOAAMABw54AAAAAgAAgYAEnAIBCbQC"
135 "AAAADQAAAAAAAAABAAAAAAAAAAEAAAANAAAAcAAAAAIAAAAGAAAApAAAAAMAAAACAAAAvAAAAAQA"
136 "AAABAAAA1AAAAAUAAAAEAAAA3AAAAAYAAAABAAAA/AAAAAEgAAACAAAAHAEAAAEQAAABAAAAVAEA"
137 "AAIgAAANAAAAWgEAAAMgAAACAAAA6AEAAAAgAAABAAAA8wEAAAAQAAABAAAABAIAAA==";
138
139TEST_F(DexFileVerifierTest, GoodDex) {
Andreas Gampedf10b322014-06-11 21:46:05 -0700140 std::string error_msg;
David Sehre1123402018-02-01 02:46:18 -0800141 std::unique_ptr<const DexFile> raw(OpenDexFileBase64(kGoodTestDex,
142 kLocationString,
Andreas Gampedf10b322014-06-11 21:46:05 -0700143 &error_msg));
144 ASSERT_TRUE(raw.get() != nullptr) << error_msg;
145}
146
Andreas Gampedf10b322014-06-11 21:46:05 -0700147TEST_F(DexFileVerifierTest, MethodId) {
Andreas Gampee6215c02015-08-31 18:54:38 -0700148 // Class idx error.
149 VerifyModification(
150 kGoodTestDex,
151 "method_id_class_idx",
152 [](DexFile* dex_file) {
153 DexFile::MethodId* method_id = const_cast<DexFile::MethodId*>(&dex_file->GetMethodId(0));
Andreas Gampea5b09a62016-11-17 15:21:22 -0800154 method_id->class_idx_ = dex::TypeIndex(0xFF);
Andreas Gampee6215c02015-08-31 18:54:38 -0700155 },
156 "could not find declaring class for direct method index 0");
157
158 // Proto idx error.
159 VerifyModification(
160 kGoodTestDex,
161 "method_id_proto_idx",
162 [](DexFile* dex_file) {
163 DexFile::MethodId* method_id = const_cast<DexFile::MethodId*>(&dex_file->GetMethodId(0));
164 method_id->proto_idx_ = 0xFF;
165 },
166 "inter_method_id_item proto_idx");
167
168 // Name idx error.
169 VerifyModification(
170 kGoodTestDex,
171 "method_id_name_idx",
172 [](DexFile* dex_file) {
173 DexFile::MethodId* method_id = const_cast<DexFile::MethodId*>(&dex_file->GetMethodId(0));
Andreas Gampe8a0128a2016-11-28 07:38:35 -0800174 method_id->name_idx_ = dex::StringIndex(0xFF);
Andreas Gampee6215c02015-08-31 18:54:38 -0700175 },
176 "String index not available for method flags verification");
177}
178
179// Method flags test class generated from the following smali code. The declared-synchronized
180// flags are there to enforce a 3-byte uLEB128 encoding so we don't have to relayout
181// the code, but we need to remove them before doing tests.
182//
183// .class public LMethodFlags;
184// .super Ljava/lang/Object;
185//
186// .method public static constructor <clinit>()V
187// .registers 1
188// return-void
189// .end method
190//
191// .method public constructor <init>()V
192// .registers 1
193// return-void
194// .end method
195//
196// .method private declared-synchronized foo()V
197// .registers 1
198// return-void
199// .end method
200//
201// .method public declared-synchronized bar()V
202// .registers 1
203// return-void
204// .end method
205
206static const char kMethodFlagsTestDex[] =
207 "ZGV4CjAzNQCyOQrJaDBwiIWv5MIuYKXhxlLLsQcx5SwgAgAAcAAAAHhWNBIAAAAAAAAAAJgBAAAH"
208 "AAAAcAAAAAMAAACMAAAAAQAAAJgAAAAAAAAAAAAAAAQAAACkAAAAAQAAAMQAAAA8AQAA5AAAAOQA"
209 "AADuAAAA9gAAAAUBAAAZAQAAHAEAACEBAAACAAAAAwAAAAQAAAAEAAAAAgAAAAAAAAAAAAAAAAAA"
210 "AAAAAAABAAAAAAAAAAUAAAAAAAAABgAAAAAAAAABAAAAAQAAAAAAAAD/////AAAAAHoBAAAAAAAA"
211 "CDxjbGluaXQ+AAY8aW5pdD4ADUxNZXRob2RGbGFnczsAEkxqYXZhL2xhbmcvT2JqZWN0OwABVgAD"
212 "YmFyAANmb28AAAAAAAAAAQAAAAAAAAAAAAAAAQAAAA4AAAABAAEAAAAAAAAAAAABAAAADgAAAAEA"
213 "AQAAAAAAAAAAAAEAAAAOAAAAAQABAAAAAAAAAAAAAQAAAA4AAAADAQCJgASsAgGBgATAAgKCgAjU"
214 "AgKBgAjoAgAACwAAAAAAAAABAAAAAAAAAAEAAAAHAAAAcAAAAAIAAAADAAAAjAAAAAMAAAABAAAA"
215 "mAAAAAUAAAAEAAAApAAAAAYAAAABAAAAxAAAAAIgAAAHAAAA5AAAAAMQAAABAAAAKAEAAAEgAAAE"
216 "AAAALAEAAAAgAAABAAAAegEAAAAQAAABAAAAmAEAAA==";
217
218// Find the method data for the first method with the given name (from class 0). Note: the pointer
219// is to the access flags, so that the caller doesn't have to handle the leb128-encoded method-index
220// delta.
Vladimir Marko59399ab2016-05-03 16:31:52 +0100221static const uint8_t* FindMethodData(const DexFile* dex_file,
222 const char* name,
223 /*out*/ uint32_t* method_idx = nullptr) {
Andreas Gampee6215c02015-08-31 18:54:38 -0700224 const DexFile::ClassDef& class_def = dex_file->GetClassDef(0);
225 const uint8_t* class_data = dex_file->GetClassData(class_def);
226
227 ClassDataItemIterator it(*dex_file, class_data);
228
229 const uint8_t* trailing = class_data;
230 // Need to manually decode the four entries. DataPointer() doesn't work for this, as the first
231 // element has already been loaded into the iterator.
232 DecodeUnsignedLeb128(&trailing);
233 DecodeUnsignedLeb128(&trailing);
234 DecodeUnsignedLeb128(&trailing);
235 DecodeUnsignedLeb128(&trailing);
236
237 // Skip all fields.
238 while (it.HasNextStaticField() || it.HasNextInstanceField()) {
239 trailing = it.DataPointer();
240 it.Next();
Andreas Gampedf10b322014-06-11 21:46:05 -0700241 }
242
Mathieu Chartierb7c273c2017-11-10 18:07:56 -0800243 while (it.HasNextMethod()) {
Andreas Gampee6215c02015-08-31 18:54:38 -0700244 uint32_t method_index = it.GetMemberIndex();
Andreas Gampe8a0128a2016-11-28 07:38:35 -0800245 dex::StringIndex name_index = dex_file->GetMethodId(method_index).name_idx_;
Andreas Gampee6215c02015-08-31 18:54:38 -0700246 const DexFile::StringId& string_id = dex_file->GetStringId(name_index);
247 const char* str = dex_file->GetStringData(string_id);
248 if (strcmp(name, str) == 0) {
Vladimir Marko59399ab2016-05-03 16:31:52 +0100249 if (method_idx != nullptr) {
250 *method_idx = method_index;
251 }
Andreas Gampee6215c02015-08-31 18:54:38 -0700252 DecodeUnsignedLeb128(&trailing);
253 return trailing;
254 }
255
256 trailing = it.DataPointer();
257 it.Next();
Andreas Gampedf10b322014-06-11 21:46:05 -0700258 }
259
Andreas Gampee6215c02015-08-31 18:54:38 -0700260 return nullptr;
261}
262
263// Set the method flags to the given value.
264static void SetMethodFlags(DexFile* dex_file, const char* method, uint32_t mask) {
265 uint8_t* method_flags_ptr = const_cast<uint8_t*>(FindMethodData(dex_file, method));
266 CHECK(method_flags_ptr != nullptr) << method;
267
268 // Unroll this, as we only have three bytes, anyways.
269 uint8_t base1 = static_cast<uint8_t>(mask & 0x7F);
270 *(method_flags_ptr++) = (base1 | 0x80);
271 mask >>= 7;
272
273 uint8_t base2 = static_cast<uint8_t>(mask & 0x7F);
274 *(method_flags_ptr++) = (base2 | 0x80);
275 mask >>= 7;
276
277 uint8_t base3 = static_cast<uint8_t>(mask & 0x7F);
278 *method_flags_ptr = base3;
279}
280
281static uint32_t GetMethodFlags(DexFile* dex_file, const char* method) {
282 const uint8_t* method_flags_ptr = const_cast<uint8_t*>(FindMethodData(dex_file, method));
283 CHECK(method_flags_ptr != nullptr) << method;
284 return DecodeUnsignedLeb128(&method_flags_ptr);
285}
286
287// Apply the given mask to method flags.
288static void ApplyMaskToMethodFlags(DexFile* dex_file, const char* method, uint32_t mask) {
289 uint32_t value = GetMethodFlags(dex_file, method);
290 value &= mask;
291 SetMethodFlags(dex_file, method, value);
292}
293
294// Apply the given mask to method flags.
295static void OrMaskToMethodFlags(DexFile* dex_file, const char* method, uint32_t mask) {
296 uint32_t value = GetMethodFlags(dex_file, method);
297 value |= mask;
298 SetMethodFlags(dex_file, method, value);
299}
300
301// Set code_off to 0 for the method.
302static void RemoveCode(DexFile* dex_file, const char* method) {
303 const uint8_t* ptr = FindMethodData(dex_file, method);
304 // Next is flags, pass.
305 DecodeUnsignedLeb128(&ptr);
306
307 // Figure out how many bytes the code_off is.
308 const uint8_t* tmp = ptr;
309 DecodeUnsignedLeb128(&tmp);
310 size_t bytes = tmp - ptr;
311
312 uint8_t* mod = const_cast<uint8_t*>(ptr);
313 for (size_t i = 1; i < bytes; ++i) {
314 *(mod++) = 0x80;
Andreas Gampedf10b322014-06-11 21:46:05 -0700315 }
Andreas Gampee6215c02015-08-31 18:54:38 -0700316 *mod = 0x00;
317}
318
319TEST_F(DexFileVerifierTest, MethodAccessFlagsBase) {
320 // Check that it's OK when the wrong declared-synchronized flag is removed from "foo."
321 VerifyModification(
322 kMethodFlagsTestDex,
323 "method_flags_ok",
324 [](DexFile* dex_file) {
325 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
326 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
327 },
328 nullptr);
329}
330
331TEST_F(DexFileVerifierTest, MethodAccessFlagsConstructors) {
332 // Make sure we still accept constructors without their flags.
333 VerifyModification(
334 kMethodFlagsTestDex,
335 "method_flags_missing_constructor_tag_ok",
336 [](DexFile* dex_file) {
337 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
338 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
339
340 ApplyMaskToMethodFlags(dex_file, "<init>", ~kAccConstructor);
341 ApplyMaskToMethodFlags(dex_file, "<clinit>", ~kAccConstructor);
342 },
343 nullptr);
344
345 constexpr const char* kConstructors[] = { "<clinit>", "<init>"};
346 for (size_t i = 0; i < 2; ++i) {
347 // Constructor with code marked native.
348 VerifyModification(
349 kMethodFlagsTestDex,
350 "method_flags_constructor_native",
351 [&](DexFile* dex_file) {
352 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
353 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
354
355 OrMaskToMethodFlags(dex_file, kConstructors[i], kAccNative);
356 },
357 "has code, but is marked native or abstract");
358 // Constructor with code marked abstract.
359 VerifyModification(
360 kMethodFlagsTestDex,
361 "method_flags_constructor_abstract",
362 [&](DexFile* dex_file) {
363 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
364 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
365
366 OrMaskToMethodFlags(dex_file, kConstructors[i], kAccAbstract);
367 },
368 "has code, but is marked native or abstract");
369 // Constructor as-is without code.
370 VerifyModification(
371 kMethodFlagsTestDex,
372 "method_flags_constructor_nocode",
373 [&](DexFile* dex_file) {
374 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
375 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
376
377 RemoveCode(dex_file, kConstructors[i]);
378 },
379 "has no code, but is not marked native or abstract");
380 // Constructor without code marked native.
381 VerifyModification(
382 kMethodFlagsTestDex,
383 "method_flags_constructor_native_nocode",
384 [&](DexFile* dex_file) {
Alex Light0ed05212016-05-06 17:36:36 -0700385 MakeDexVersion37(dex_file);
Andreas Gampee6215c02015-08-31 18:54:38 -0700386 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
387 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
388
389 OrMaskToMethodFlags(dex_file, kConstructors[i], kAccNative);
390 RemoveCode(dex_file, kConstructors[i]);
391 },
392 "must not be abstract or native");
393 // Constructor without code marked abstract.
394 VerifyModification(
395 kMethodFlagsTestDex,
396 "method_flags_constructor_abstract_nocode",
397 [&](DexFile* dex_file) {
Alex Light0ed05212016-05-06 17:36:36 -0700398 MakeDexVersion37(dex_file);
Andreas Gampee6215c02015-08-31 18:54:38 -0700399 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
400 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
401
402 OrMaskToMethodFlags(dex_file, kConstructors[i], kAccAbstract);
403 RemoveCode(dex_file, kConstructors[i]);
404 },
405 "must not be abstract or native");
406 }
407 // <init> may only have (modulo ignored):
408 // kAccPrivate | kAccProtected | kAccPublic | kAccStrict | kAccVarargs | kAccSynthetic
409 static constexpr uint32_t kInitAllowed[] = {
410 0,
411 kAccPrivate,
412 kAccProtected,
413 kAccPublic,
414 kAccStrict,
415 kAccVarargs,
416 kAccSynthetic
417 };
418 for (size_t i = 0; i < arraysize(kInitAllowed); ++i) {
419 VerifyModification(
420 kMethodFlagsTestDex,
421 "init_allowed_flags",
422 [&](DexFile* dex_file) {
423 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
424 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
425
426 ApplyMaskToMethodFlags(dex_file, "<init>", ~kAccPublic);
427 OrMaskToMethodFlags(dex_file, "<init>", kInitAllowed[i]);
428 },
429 nullptr);
430 }
431 // Only one of public-private-protected.
432 for (size_t i = 1; i < 8; ++i) {
433 if (POPCOUNT(i) < 2) {
434 continue;
435 }
436 // Technically the flags match, but just be defensive here.
437 uint32_t mask = ((i & 1) != 0 ? kAccPrivate : 0) |
438 ((i & 2) != 0 ? kAccProtected : 0) |
439 ((i & 4) != 0 ? kAccPublic : 0);
440 VerifyModification(
441 kMethodFlagsTestDex,
442 "init_one_of_ppp",
443 [&](DexFile* dex_file) {
444 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
445 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
446
447 ApplyMaskToMethodFlags(dex_file, "<init>", ~kAccPublic);
448 OrMaskToMethodFlags(dex_file, "<init>", mask);
449 },
450 "Method may have only one of public/protected/private");
451 }
452 // <init> doesn't allow
453 // kAccStatic | kAccFinal | kAccSynchronized | kAccBridge
454 // Need to handle static separately as it has its own error message.
455 VerifyModification(
456 kMethodFlagsTestDex,
457 "init_not_allowed_flags",
458 [&](DexFile* dex_file) {
Alex Light0ed05212016-05-06 17:36:36 -0700459 MakeDexVersion37(dex_file);
Andreas Gampee6215c02015-08-31 18:54:38 -0700460 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
461 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
462
463 ApplyMaskToMethodFlags(dex_file, "<init>", ~kAccPublic);
464 OrMaskToMethodFlags(dex_file, "<init>", kAccStatic);
465 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800466 "Constructor 1(LMethodFlags;.<init>) is not flagged correctly wrt/ static");
Andreas Gampee6215c02015-08-31 18:54:38 -0700467 static constexpr uint32_t kInitNotAllowed[] = {
468 kAccFinal,
469 kAccSynchronized,
470 kAccBridge
471 };
472 for (size_t i = 0; i < arraysize(kInitNotAllowed); ++i) {
473 VerifyModification(
474 kMethodFlagsTestDex,
475 "init_not_allowed_flags",
476 [&](DexFile* dex_file) {
477 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
478 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
479
480 ApplyMaskToMethodFlags(dex_file, "<init>", ~kAccPublic);
481 OrMaskToMethodFlags(dex_file, "<init>", kInitNotAllowed[i]);
482 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800483 "Constructor 1(LMethodFlags;.<init>) flagged inappropriately");
Andreas Gampee6215c02015-08-31 18:54:38 -0700484 }
485}
486
487TEST_F(DexFileVerifierTest, MethodAccessFlagsMethods) {
488 constexpr const char* kMethods[] = { "foo", "bar"};
489 for (size_t i = 0; i < arraysize(kMethods); ++i) {
490 // Make sure we reject non-constructors marked as constructors.
491 VerifyModification(
492 kMethodFlagsTestDex,
493 "method_flags_non_constructor",
494 [&](DexFile* dex_file) {
495 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
496 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
497
498 OrMaskToMethodFlags(dex_file, kMethods[i], kAccConstructor);
499 },
500 "is marked constructor, but doesn't match name");
501
502 VerifyModification(
503 kMethodFlagsTestDex,
504 "method_flags_native_with_code",
505 [&](DexFile* dex_file) {
506 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
507 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
508
509 OrMaskToMethodFlags(dex_file, kMethods[i], kAccNative);
510 },
511 "has code, but is marked native or abstract");
512
513 VerifyModification(
514 kMethodFlagsTestDex,
515 "method_flags_abstract_with_code",
516 [&](DexFile* dex_file) {
517 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
518 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
519
520 OrMaskToMethodFlags(dex_file, kMethods[i], kAccAbstract);
521 },
522 "has code, but is marked native or abstract");
523
524 VerifyModification(
525 kMethodFlagsTestDex,
526 "method_flags_non_abstract_native_no_code",
527 [&](DexFile* dex_file) {
528 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
529 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
530
531 RemoveCode(dex_file, kMethods[i]);
532 },
533 "has no code, but is not marked native or abstract");
534
535 // Abstract methods may not have the following flags.
536 constexpr uint32_t kAbstractDisallowed[] = {
537 kAccPrivate,
538 kAccStatic,
539 kAccFinal,
540 kAccNative,
541 kAccStrict,
542 kAccSynchronized,
543 };
544 for (size_t j = 0; j < arraysize(kAbstractDisallowed); ++j) {
545 VerifyModification(
546 kMethodFlagsTestDex,
547 "method_flags_abstract_and_disallowed_no_code",
548 [&](DexFile* dex_file) {
549 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
550 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
551
552 RemoveCode(dex_file, kMethods[i]);
553
554 // Can't check private and static with foo, as it's in the virtual list and gives a
555 // different error.
556 if (((GetMethodFlags(dex_file, kMethods[i]) & kAccPublic) != 0) &&
557 ((kAbstractDisallowed[j] & (kAccPrivate | kAccStatic)) != 0)) {
558 // Use another breaking flag.
559 OrMaskToMethodFlags(dex_file, kMethods[i], kAccAbstract | kAccFinal);
560 } else {
561 OrMaskToMethodFlags(dex_file, kMethods[i], kAccAbstract | kAbstractDisallowed[j]);
562 }
563 },
564 "has disallowed access flags");
565 }
566
567 // Only one of public-private-protected.
568 for (size_t j = 1; j < 8; ++j) {
569 if (POPCOUNT(j) < 2) {
570 continue;
571 }
572 // Technically the flags match, but just be defensive here.
573 uint32_t mask = ((j & 1) != 0 ? kAccPrivate : 0) |
574 ((j & 2) != 0 ? kAccProtected : 0) |
575 ((j & 4) != 0 ? kAccPublic : 0);
576 VerifyModification(
577 kMethodFlagsTestDex,
578 "method_flags_one_of_ppp",
579 [&](DexFile* dex_file) {
580 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
581 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
582
583 ApplyMaskToMethodFlags(dex_file, kMethods[i], ~kAccPublic);
584 OrMaskToMethodFlags(dex_file, kMethods[i], mask);
585 },
586 "Method may have only one of public/protected/private");
587 }
588 }
589}
590
591TEST_F(DexFileVerifierTest, MethodAccessFlagsIgnoredOK) {
592 constexpr const char* kMethods[] = { "<clinit>", "<init>", "foo", "bar"};
593 for (size_t i = 0; i < arraysize(kMethods); ++i) {
594 // All interesting method flags, other flags are to be ignored.
595 constexpr uint32_t kAllMethodFlags =
596 kAccPublic |
597 kAccPrivate |
598 kAccProtected |
599 kAccStatic |
600 kAccFinal |
601 kAccSynchronized |
602 kAccBridge |
603 kAccVarargs |
604 kAccNative |
605 kAccAbstract |
606 kAccStrict |
607 kAccSynthetic;
608 constexpr uint32_t kIgnoredMask = ~kAllMethodFlags & 0xFFFF;
609 VerifyModification(
610 kMethodFlagsTestDex,
611 "method_flags_ignored",
612 [&](DexFile* dex_file) {
613 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
614 ApplyMaskToMethodFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
615
616 OrMaskToMethodFlags(dex_file, kMethods[i], kIgnoredMask);
617 },
618 nullptr);
619 }
620}
621
Vladimir Marko59399ab2016-05-03 16:31:52 +0100622TEST_F(DexFileVerifierTest, B28552165) {
623 // Regression test for bad error string retrieval in different situations.
624 // Using invalid access flags to trigger the error.
625 VerifyModification(
626 kMethodFlagsTestDex,
627 "b28552165",
628 [](DexFile* dex_file) {
629 OrMaskToMethodFlags(dex_file, "foo", kAccPublic | kAccProtected);
Vladimir Marko59399ab2016-05-03 16:31:52 +0100630 },
Orion Hodson6c4921b2016-09-21 15:41:06 +0100631 "Method may have only one of public/protected/private, LMethodFlags;.foo");
Vladimir Marko59399ab2016-05-03 16:31:52 +0100632}
633
Andreas Gampee6215c02015-08-31 18:54:38 -0700634// Set of dex files for interface method tests. As it's not as easy to mutate method names, it's
635// just easier to break up bad cases.
636
Andreas Gampee6215c02015-08-31 18:54:38 -0700637// Standard interface. Use declared-synchronized again for 3B encoding.
638//
639// .class public interface LInterfaceMethodFlags;
640// .super Ljava/lang/Object;
641//
642// .method public static constructor <clinit>()V
643// .registers 1
644// return-void
645// .end method
646//
647// .method public abstract declared-synchronized foo()V
648// .end method
649static const char kMethodFlagsInterface[] =
650 "ZGV4CjAzNQCOM0odZ5bws1d9GSmumXaK5iE/7XxFpOm8AQAAcAAAAHhWNBIAAAAAAAAAADQBAAAF"
651 "AAAAcAAAAAMAAACEAAAAAQAAAJAAAAAAAAAAAAAAAAIAAACcAAAAAQAAAKwAAADwAAAAzAAAAMwA"
652 "AADWAAAA7gAAAAIBAAAFAQAAAQAAAAIAAAADAAAAAwAAAAIAAAAAAAAAAAAAAAAAAAAAAAAABAAA"
653 "AAAAAAABAgAAAQAAAAAAAAD/////AAAAACIBAAAAAAAACDxjbGluaXQ+ABZMSW50ZXJmYWNlTWV0"
654 "aG9kRmxhZ3M7ABJMamF2YS9sYW5nL09iamVjdDsAAVYAA2ZvbwAAAAAAAAABAAAAAAAAAAAAAAAB"
655 "AAAADgAAAAEBAImABJACAYGICAAAAAALAAAAAAAAAAEAAAAAAAAAAQAAAAUAAABwAAAAAgAAAAMA"
656 "AACEAAAAAwAAAAEAAACQAAAABQAAAAIAAACcAAAABgAAAAEAAACsAAAAAiAAAAUAAADMAAAAAxAA"
657 "AAEAAAAMAQAAASAAAAEAAAAQAQAAACAAAAEAAAAiAQAAABAAAAEAAAA0AQAA";
658
659// To simplify generation of interesting "sub-states" of src_value, allow a "simple" mask to apply
660// to a src_value, such that mask bit 0 applies to the lowest set bit in src_value, and so on.
661static uint32_t ApplyMaskShifted(uint32_t src_value, uint32_t mask) {
662 uint32_t result = 0;
663 uint32_t mask_index = 0;
664 while (src_value != 0) {
665 uint32_t index = CTZ(src_value);
666 if (((src_value & (1 << index)) != 0) &&
667 ((mask & (1 << mask_index)) != 0)) {
668 result |= (1 << index);
669 }
670 src_value &= ~(1 << index);
671 mask_index++;
672 }
673 return result;
674}
675
676TEST_F(DexFileVerifierTest, MethodAccessFlagsInterfaces) {
Andreas Gampee6215c02015-08-31 18:54:38 -0700677 VerifyModification(
678 kMethodFlagsInterface,
679 "method_flags_interface_ok",
680 [](DexFile* dex_file) {
681 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
682 },
683 nullptr);
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700684 VerifyModification(
685 kMethodFlagsInterface,
686 "method_flags_interface_ok37",
687 [](DexFile* dex_file) {
688 MakeDexVersion37(dex_file);
689 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
690 },
691 nullptr);
Andreas Gampee6215c02015-08-31 18:54:38 -0700692
693 VerifyModification(
694 kMethodFlagsInterface,
695 "method_flags_interface_non_public",
696 [](DexFile* dex_file) {
697 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
698
699 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
700 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700701 nullptr); // Should be allowed in older dex versions for backwards compatibility.
702 VerifyModification(
703 kMethodFlagsInterface,
704 "method_flags_interface_non_public",
705 [](DexFile* dex_file) {
706 MakeDexVersion37(dex_file);
707 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
708
709 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
710 },
Alex Lightd7c10c22016-03-31 10:03:07 -0700711 "Interface virtual method 1(LInterfaceMethodFlags;.foo) is not public");
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700712
Andreas Gampee6215c02015-08-31 18:54:38 -0700713 VerifyModification(
714 kMethodFlagsInterface,
715 "method_flags_interface_non_abstract",
716 [](DexFile* dex_file) {
717 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
718
719 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccAbstract);
720 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800721 "Method 1(LInterfaceMethodFlags;.foo) has no code, but is not marked native or abstract");
Andreas Gampee6215c02015-08-31 18:54:38 -0700722
723 VerifyModification(
724 kMethodFlagsInterface,
725 "method_flags_interface_static",
726 [](DexFile* dex_file) {
727 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
728
729 OrMaskToMethodFlags(dex_file, "foo", kAccStatic);
730 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800731 "Direct/virtual method 1(LInterfaceMethodFlags;.foo) not in expected list 0");
Andreas Gampee6215c02015-08-31 18:54:38 -0700732 VerifyModification(
733 kMethodFlagsInterface,
734 "method_flags_interface_private",
735 [](DexFile* dex_file) {
736 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
737
738 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
739 OrMaskToMethodFlags(dex_file, "foo", kAccPrivate);
740 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800741 "Direct/virtual method 1(LInterfaceMethodFlags;.foo) not in expected list 0");
Andreas Gampee6215c02015-08-31 18:54:38 -0700742
743 VerifyModification(
744 kMethodFlagsInterface,
745 "method_flags_interface_non_public",
746 [](DexFile* dex_file) {
747 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
748
749 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
750 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700751 nullptr); // Should be allowed in older dex versions for backwards compatibility.
752 VerifyModification(
753 kMethodFlagsInterface,
754 "method_flags_interface_non_public",
755 [](DexFile* dex_file) {
756 MakeDexVersion37(dex_file);
757 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
758
759 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
760 },
Alex Lightd7c10c22016-03-31 10:03:07 -0700761 "Interface virtual method 1(LInterfaceMethodFlags;.foo) is not public");
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700762
Andreas Gampee6215c02015-08-31 18:54:38 -0700763 VerifyModification(
764 kMethodFlagsInterface,
765 "method_flags_interface_protected",
766 [](DexFile* dex_file) {
767 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
768
769 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
770 OrMaskToMethodFlags(dex_file, "foo", kAccProtected);
771 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -0700772 nullptr); // Should be allowed in older dex versions for backwards compatibility.
773 VerifyModification(
774 kMethodFlagsInterface,
775 "method_flags_interface_protected",
776 [](DexFile* dex_file) {
777 MakeDexVersion37(dex_file);
778 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
779
780 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
781 OrMaskToMethodFlags(dex_file, "foo", kAccProtected);
782 },
Alex Lightd7c10c22016-03-31 10:03:07 -0700783 "Interface virtual method 1(LInterfaceMethodFlags;.foo) is not public");
Andreas Gampee6215c02015-08-31 18:54:38 -0700784
785 constexpr uint32_t kAllMethodFlags =
786 kAccPublic |
787 kAccPrivate |
788 kAccProtected |
789 kAccStatic |
790 kAccFinal |
791 kAccSynchronized |
792 kAccBridge |
793 kAccVarargs |
794 kAccNative |
795 kAccAbstract |
796 kAccStrict |
797 kAccSynthetic;
798 constexpr uint32_t kInterfaceMethodFlags =
799 kAccPublic | kAccAbstract | kAccVarargs | kAccBridge | kAccSynthetic;
800 constexpr uint32_t kInterfaceDisallowed = kAllMethodFlags &
801 ~kInterfaceMethodFlags &
802 // Already tested, needed to be separate.
803 ~kAccStatic &
804 ~kAccPrivate &
805 ~kAccProtected;
806 static_assert(kInterfaceDisallowed != 0, "There should be disallowed flags.");
807
808 uint32_t bits = POPCOUNT(kInterfaceDisallowed);
809 for (uint32_t i = 1; i < (1u << bits); ++i) {
810 VerifyModification(
811 kMethodFlagsInterface,
812 "method_flags_interface_non_abstract",
813 [&](DexFile* dex_file) {
814 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
815
816 uint32_t mask = ApplyMaskShifted(kInterfaceDisallowed, i);
817 if ((mask & kAccProtected) != 0) {
818 mask &= ~kAccProtected;
819 ApplyMaskToMethodFlags(dex_file, "foo", ~kAccPublic);
820 }
821 OrMaskToMethodFlags(dex_file, "foo", mask);
822 },
Andreas Gampec9f0ba12016-02-09 09:21:04 -0800823 "Abstract method 1(LInterfaceMethodFlags;.foo) has disallowed access flags");
Andreas Gampee6215c02015-08-31 18:54:38 -0700824 }
825}
826
827///////////////////////////////////////////////////////////////////
828
829// Field flags.
830
831// Find the method data for the first method with the given name (from class 0). Note: the pointer
832// is to the access flags, so that the caller doesn't have to handle the leb128-encoded method-index
833// delta.
834static const uint8_t* FindFieldData(const DexFile* dex_file, const char* name) {
835 const DexFile::ClassDef& class_def = dex_file->GetClassDef(0);
836 const uint8_t* class_data = dex_file->GetClassData(class_def);
837
838 ClassDataItemIterator it(*dex_file, class_data);
839
840 const uint8_t* trailing = class_data;
841 // Need to manually decode the four entries. DataPointer() doesn't work for this, as the first
842 // element has already been loaded into the iterator.
843 DecodeUnsignedLeb128(&trailing);
844 DecodeUnsignedLeb128(&trailing);
845 DecodeUnsignedLeb128(&trailing);
846 DecodeUnsignedLeb128(&trailing);
847
848 while (it.HasNextStaticField() || it.HasNextInstanceField()) {
849 uint32_t field_index = it.GetMemberIndex();
Andreas Gampe8a0128a2016-11-28 07:38:35 -0800850 dex::StringIndex name_index = dex_file->GetFieldId(field_index).name_idx_;
Andreas Gampee6215c02015-08-31 18:54:38 -0700851 const DexFile::StringId& string_id = dex_file->GetStringId(name_index);
852 const char* str = dex_file->GetStringData(string_id);
853 if (strcmp(name, str) == 0) {
854 DecodeUnsignedLeb128(&trailing);
855 return trailing;
856 }
857
858 trailing = it.DataPointer();
859 it.Next();
860 }
861
862 return nullptr;
863}
864
865// Set the method flags to the given value.
866static void SetFieldFlags(DexFile* dex_file, const char* field, uint32_t mask) {
867 uint8_t* field_flags_ptr = const_cast<uint8_t*>(FindFieldData(dex_file, field));
868 CHECK(field_flags_ptr != nullptr) << field;
869
870 // Unroll this, as we only have three bytes, anyways.
871 uint8_t base1 = static_cast<uint8_t>(mask & 0x7F);
872 *(field_flags_ptr++) = (base1 | 0x80);
873 mask >>= 7;
874
875 uint8_t base2 = static_cast<uint8_t>(mask & 0x7F);
876 *(field_flags_ptr++) = (base2 | 0x80);
877 mask >>= 7;
878
879 uint8_t base3 = static_cast<uint8_t>(mask & 0x7F);
880 *field_flags_ptr = base3;
881}
882
883static uint32_t GetFieldFlags(DexFile* dex_file, const char* field) {
884 const uint8_t* field_flags_ptr = const_cast<uint8_t*>(FindFieldData(dex_file, field));
885 CHECK(field_flags_ptr != nullptr) << field;
886 return DecodeUnsignedLeb128(&field_flags_ptr);
887}
888
889// Apply the given mask to method flags.
890static void ApplyMaskToFieldFlags(DexFile* dex_file, const char* field, uint32_t mask) {
891 uint32_t value = GetFieldFlags(dex_file, field);
892 value &= mask;
893 SetFieldFlags(dex_file, field, value);
894}
895
896// Apply the given mask to method flags.
897static void OrMaskToFieldFlags(DexFile* dex_file, const char* field, uint32_t mask) {
898 uint32_t value = GetFieldFlags(dex_file, field);
899 value |= mask;
900 SetFieldFlags(dex_file, field, value);
901}
902
903// Standard class. Use declared-synchronized again for 3B encoding.
904//
905// .class public LFieldFlags;
906// .super Ljava/lang/Object;
907//
908// .field declared-synchronized public foo:I
909//
910// .field declared-synchronized public static bar:I
911
912static const char kFieldFlagsTestDex[] =
913 "ZGV4CjAzNQBtLw7hydbfv4TdXidZyzAB70W7w3vnYJRwAQAAcAAAAHhWNBIAAAAAAAAAAAABAAAF"
914 "AAAAcAAAAAMAAACEAAAAAAAAAAAAAAACAAAAkAAAAAAAAAAAAAAAAQAAAKAAAACwAAAAwAAAAMAA"
915 "AADDAAAA0QAAAOUAAADqAAAAAAAAAAEAAAACAAAAAQAAAAMAAAABAAAABAAAAAEAAAABAAAAAgAA"
916 "AAAAAAD/////AAAAAPQAAAAAAAAAAUkADExGaWVsZEZsYWdzOwASTGphdmEvbGFuZy9PYmplY3Q7"
917 "AANiYXIAA2ZvbwAAAAAAAAEBAAAAiYAIAYGACAkAAAAAAAAAAQAAAAAAAAABAAAABQAAAHAAAAAC"
918 "AAAAAwAAAIQAAAAEAAAAAgAAAJAAAAAGAAAAAQAAAKAAAAACIAAABQAAAMAAAAADEAAAAQAAAPAA"
919 "AAAAIAAAAQAAAPQAAAAAEAAAAQAAAAABAAA=";
920
921TEST_F(DexFileVerifierTest, FieldAccessFlagsBase) {
922 // Check that it's OK when the wrong declared-synchronized flag is removed from "foo."
923 VerifyModification(
924 kFieldFlagsTestDex,
925 "field_flags_ok",
926 [](DexFile* dex_file) {
927 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
928 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
929 },
930 nullptr);
931}
932
933TEST_F(DexFileVerifierTest, FieldAccessFlagsWrongList) {
934 // Mark the field so that it should appear in the opposite list (instance vs static).
935 VerifyModification(
936 kFieldFlagsTestDex,
937 "field_flags_wrong_list",
938 [](DexFile* dex_file) {
939 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
940 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
941
942 OrMaskToFieldFlags(dex_file, "foo", kAccStatic);
943 },
944 "Static/instance field not in expected list");
945 VerifyModification(
946 kFieldFlagsTestDex,
947 "field_flags_wrong_list",
948 [](DexFile* dex_file) {
949 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
950 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
951
952 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccStatic);
953 },
954 "Static/instance field not in expected list");
955}
956
957TEST_F(DexFileVerifierTest, FieldAccessFlagsPPP) {
958 static const char* kFields[] = { "foo", "bar" };
959 for (size_t i = 0; i < arraysize(kFields); ++i) {
960 // Should be OK to remove public.
961 VerifyModification(
962 kFieldFlagsTestDex,
963 "field_flags_non_public",
964 [&](DexFile* dex_file) {
965 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
966 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
967
968 ApplyMaskToFieldFlags(dex_file, kFields[i], ~kAccPublic);
969 },
970 nullptr);
971 constexpr uint32_t kAccFlags = kAccPublic | kAccPrivate | kAccProtected;
972 uint32_t bits = POPCOUNT(kAccFlags);
973 for (uint32_t j = 1; j < (1u << bits); ++j) {
974 if (POPCOUNT(j) < 2) {
975 continue;
976 }
977 VerifyModification(
978 kFieldFlagsTestDex,
979 "field_flags_ppp",
980 [&](DexFile* dex_file) {
981 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
982 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
983
984 ApplyMaskToFieldFlags(dex_file, kFields[i], ~kAccPublic);
985 uint32_t mask = ApplyMaskShifted(kAccFlags, j);
986 OrMaskToFieldFlags(dex_file, kFields[i], mask);
987 },
988 "Field may have only one of public/protected/private");
989 }
990 }
991}
992
993TEST_F(DexFileVerifierTest, FieldAccessFlagsIgnoredOK) {
994 constexpr const char* kFields[] = { "foo", "bar"};
995 for (size_t i = 0; i < arraysize(kFields); ++i) {
996 // All interesting method flags, other flags are to be ignored.
997 constexpr uint32_t kAllFieldFlags =
998 kAccPublic |
999 kAccPrivate |
1000 kAccProtected |
1001 kAccStatic |
1002 kAccFinal |
1003 kAccVolatile |
1004 kAccTransient |
1005 kAccSynthetic |
1006 kAccEnum;
1007 constexpr uint32_t kIgnoredMask = ~kAllFieldFlags & 0xFFFF;
1008 VerifyModification(
1009 kFieldFlagsTestDex,
1010 "field_flags_ignored",
1011 [&](DexFile* dex_file) {
1012 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1013 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
1014
1015 OrMaskToFieldFlags(dex_file, kFields[i], kIgnoredMask);
1016 },
1017 nullptr);
1018 }
1019}
1020
1021TEST_F(DexFileVerifierTest, FieldAccessFlagsVolatileFinal) {
1022 constexpr const char* kFields[] = { "foo", "bar"};
1023 for (size_t i = 0; i < arraysize(kFields); ++i) {
1024 VerifyModification(
1025 kFieldFlagsTestDex,
1026 "field_flags_final_and_volatile",
1027 [&](DexFile* dex_file) {
1028 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1029 ApplyMaskToFieldFlags(dex_file, "bar", ~kAccDeclaredSynchronized);
1030
1031 OrMaskToFieldFlags(dex_file, kFields[i], kAccVolatile | kAccFinal);
1032 },
1033 "Fields may not be volatile and final");
1034 }
1035}
1036
1037// Standard interface. Needs to be separate from class as interfaces do not allow instance fields.
1038// Use declared-synchronized again for 3B encoding.
1039//
1040// .class public interface LInterfaceFieldFlags;
1041// .super Ljava/lang/Object;
1042//
1043// .field declared-synchronized public static final foo:I
1044
1045static const char kFieldFlagsInterfaceTestDex[] =
1046 "ZGV4CjAzNQCVMHfEimR1zZPk6hl6O9GPAYqkl3u0umFkAQAAcAAAAHhWNBIAAAAAAAAAAPQAAAAE"
1047 "AAAAcAAAAAMAAACAAAAAAAAAAAAAAAABAAAAjAAAAAAAAAAAAAAAAQAAAJQAAACwAAAAtAAAALQA"
1048 "AAC3AAAAzgAAAOIAAAAAAAAAAQAAAAIAAAABAAAAAwAAAAEAAAABAgAAAgAAAAAAAAD/////AAAA"
1049 "AOwAAAAAAAAAAUkAFUxJbnRlcmZhY2VGaWVsZEZsYWdzOwASTGphdmEvbGFuZy9PYmplY3Q7AANm"
1050 "b28AAAAAAAABAAAAAJmACAkAAAAAAAAAAQAAAAAAAAABAAAABAAAAHAAAAACAAAAAwAAAIAAAAAE"
1051 "AAAAAQAAAIwAAAAGAAAAAQAAAJQAAAACIAAABAAAALQAAAADEAAAAQAAAOgAAAAAIAAAAQAAAOwA"
1052 "AAAAEAAAAQAAAPQAAAA=";
1053
1054TEST_F(DexFileVerifierTest, FieldAccessFlagsInterface) {
1055 VerifyModification(
1056 kFieldFlagsInterfaceTestDex,
1057 "field_flags_interface",
1058 [](DexFile* dex_file) {
1059 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1060 },
1061 nullptr);
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001062 VerifyModification(
1063 kFieldFlagsInterfaceTestDex,
1064 "field_flags_interface",
1065 [](DexFile* dex_file) {
1066 MakeDexVersion37(dex_file);
1067 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1068 },
1069 nullptr);
Andreas Gampee6215c02015-08-31 18:54:38 -07001070
1071 VerifyModification(
1072 kFieldFlagsInterfaceTestDex,
1073 "field_flags_interface_non_public",
1074 [](DexFile* dex_file) {
1075 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1076
1077 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1078 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001079 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1080 VerifyModification(
1081 kFieldFlagsInterfaceTestDex,
1082 "field_flags_interface_non_public",
1083 [](DexFile* dex_file) {
1084 MakeDexVersion37(dex_file);
1085 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1086
1087 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1088 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001089 "Interface field is not public final static");
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001090
Andreas Gampee6215c02015-08-31 18:54:38 -07001091 VerifyModification(
1092 kFieldFlagsInterfaceTestDex,
1093 "field_flags_interface_non_final",
1094 [](DexFile* dex_file) {
1095 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1096
1097 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccFinal);
1098 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001099 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1100 VerifyModification(
1101 kFieldFlagsInterfaceTestDex,
1102 "field_flags_interface_non_final",
1103 [](DexFile* dex_file) {
1104 MakeDexVersion37(dex_file);
1105 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1106
1107 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccFinal);
1108 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001109 "Interface field is not public final static");
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001110
Andreas Gampee6215c02015-08-31 18:54:38 -07001111 VerifyModification(
1112 kFieldFlagsInterfaceTestDex,
1113 "field_flags_interface_protected",
1114 [](DexFile* dex_file) {
1115 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1116
1117 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1118 OrMaskToFieldFlags(dex_file, "foo", kAccProtected);
1119 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001120 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1121 VerifyModification(
1122 kFieldFlagsInterfaceTestDex,
1123 "field_flags_interface_protected",
1124 [](DexFile* dex_file) {
1125 MakeDexVersion37(dex_file);
1126 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1127
1128 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1129 OrMaskToFieldFlags(dex_file, "foo", kAccProtected);
1130 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001131 "Interface field is not public final static");
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001132
Andreas Gampee6215c02015-08-31 18:54:38 -07001133 VerifyModification(
1134 kFieldFlagsInterfaceTestDex,
1135 "field_flags_interface_private",
1136 [](DexFile* dex_file) {
1137 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1138
1139 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1140 OrMaskToFieldFlags(dex_file, "foo", kAccPrivate);
1141 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001142 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1143 VerifyModification(
1144 kFieldFlagsInterfaceTestDex,
1145 "field_flags_interface_private",
1146 [](DexFile* dex_file) {
1147 MakeDexVersion37(dex_file);
1148 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1149
1150 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1151 OrMaskToFieldFlags(dex_file, "foo", kAccPrivate);
1152 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001153 "Interface field is not public final static");
1154
1155 VerifyModification(
1156 kFieldFlagsInterfaceTestDex,
1157 "field_flags_interface_synthetic",
1158 [](DexFile* dex_file) {
1159 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1160
1161 OrMaskToFieldFlags(dex_file, "foo", kAccSynthetic);
1162 },
1163 nullptr);
1164
1165 constexpr uint32_t kAllFieldFlags =
1166 kAccPublic |
1167 kAccPrivate |
1168 kAccProtected |
1169 kAccStatic |
1170 kAccFinal |
1171 kAccVolatile |
1172 kAccTransient |
1173 kAccSynthetic |
1174 kAccEnum;
1175 constexpr uint32_t kInterfaceFieldFlags = kAccPublic | kAccStatic | kAccFinal | kAccSynthetic;
1176 constexpr uint32_t kInterfaceDisallowed = kAllFieldFlags &
1177 ~kInterfaceFieldFlags &
1178 ~kAccProtected &
1179 ~kAccPrivate;
1180 static_assert(kInterfaceDisallowed != 0, "There should be disallowed flags.");
1181
1182 uint32_t bits = POPCOUNT(kInterfaceDisallowed);
1183 for (uint32_t i = 1; i < (1u << bits); ++i) {
1184 VerifyModification(
1185 kFieldFlagsInterfaceTestDex,
1186 "field_flags_interface_disallowed",
1187 [&](DexFile* dex_file) {
1188 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1189
1190 uint32_t mask = ApplyMaskShifted(kInterfaceDisallowed, i);
1191 if ((mask & kAccProtected) != 0) {
1192 mask &= ~kAccProtected;
1193 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1194 }
1195 OrMaskToFieldFlags(dex_file, "foo", mask);
1196 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001197 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1198 VerifyModification(
1199 kFieldFlagsInterfaceTestDex,
1200 "field_flags_interface_disallowed",
1201 [&](DexFile* dex_file) {
1202 MakeDexVersion37(dex_file);
1203 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1204
1205 uint32_t mask = ApplyMaskShifted(kInterfaceDisallowed, i);
1206 if ((mask & kAccProtected) != 0) {
1207 mask &= ~kAccProtected;
1208 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccPublic);
1209 }
1210 OrMaskToFieldFlags(dex_file, "foo", mask);
1211 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001212 "Interface field has disallowed flag");
1213 }
1214}
1215
1216// Standard bad interface. Needs to be separate from class as interfaces do not allow instance
1217// fields. Use declared-synchronized again for 3B encoding.
1218//
1219// .class public interface LInterfaceFieldFlags;
1220// .super Ljava/lang/Object;
1221//
1222// .field declared-synchronized public final foo:I
1223
1224static const char kFieldFlagsInterfaceBadTestDex[] =
1225 "ZGV4CjAzNQByMUnqYKHBkUpvvNp+9CnZ2VyDkKnRN6VkAQAAcAAAAHhWNBIAAAAAAAAAAPQAAAAE"
1226 "AAAAcAAAAAMAAACAAAAAAAAAAAAAAAABAAAAjAAAAAAAAAAAAAAAAQAAAJQAAACwAAAAtAAAALQA"
1227 "AAC3AAAAzgAAAOIAAAAAAAAAAQAAAAIAAAABAAAAAwAAAAEAAAABAgAAAgAAAAAAAAD/////AAAA"
1228 "AOwAAAAAAAAAAUkAFUxJbnRlcmZhY2VGaWVsZEZsYWdzOwASTGphdmEvbGFuZy9PYmplY3Q7AANm"
1229 "b28AAAAAAAAAAQAAAJGACAkAAAAAAAAAAQAAAAAAAAABAAAABAAAAHAAAAACAAAAAwAAAIAAAAAE"
1230 "AAAAAQAAAIwAAAAGAAAAAQAAAJQAAAACIAAABAAAALQAAAADEAAAAQAAAOgAAAAAIAAAAQAAAOwA"
1231 "AAAAEAAAAQAAAPQAAAA=";
1232
1233TEST_F(DexFileVerifierTest, FieldAccessFlagsInterfaceNonStatic) {
1234 VerifyModification(
1235 kFieldFlagsInterfaceBadTestDex,
1236 "field_flags_interface_non_static",
1237 [](DexFile* dex_file) {
1238 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1239 },
Andreas Gampe76ed99d2016-03-28 18:31:29 -07001240 nullptr); // Should be allowed in older dex versions for backwards compatibility.
1241 VerifyModification(
1242 kFieldFlagsInterfaceBadTestDex,
1243 "field_flags_interface_non_static",
1244 [](DexFile* dex_file) {
1245 MakeDexVersion37(dex_file);
1246 ApplyMaskToFieldFlags(dex_file, "foo", ~kAccDeclaredSynchronized);
1247 },
Andreas Gampee6215c02015-08-31 18:54:38 -07001248 "Interface field is not public final static");
Andreas Gampedf10b322014-06-11 21:46:05 -07001249}
1250
Logan Chiendd3208d2015-04-19 23:27:52 +08001251// Generated from:
1252//
1253// .class public LTest;
1254// .super Ljava/lang/Object;
1255// .source "Test.java"
1256//
1257// .method public constructor <init>()V
1258// .registers 1
1259//
1260// .prologue
1261// .line 1
1262// invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1263//
1264// return-void
1265// .end method
1266//
1267// .method public static main()V
1268// .registers 2
1269//
1270// const-string v0, "a"
1271// const-string v0, "b"
1272// const-string v0, "c"
1273// const-string v0, "d"
1274// const-string v0, "e"
1275// const-string v0, "f"
1276// const-string v0, "g"
1277// const-string v0, "h"
1278// const-string v0, "i"
1279// const-string v0, "j"
1280// const-string v0, "k"
1281//
1282// .local v1, "local_var":Ljava/lang/String;
1283// const-string v1, "test"
1284// .end method
1285
1286static const char kDebugInfoTestDex[] =
1287 "ZGV4CjAzNQCHRkHix2eIMQgvLD/0VGrlllZLo0Rb6VyUAgAAcAAAAHhWNBIAAAAAAAAAAAwCAAAU"
1288 "AAAAcAAAAAQAAADAAAAAAQAAANAAAAAAAAAAAAAAAAMAAADcAAAAAQAAAPQAAACAAQAAFAEAABQB"
1289 "AAAcAQAAJAEAADgBAABMAQAAVwEAAFoBAABdAQAAYAEAAGMBAABmAQAAaQEAAGwBAABvAQAAcgEA"
1290 "AHUBAAB4AQAAewEAAIYBAACMAQAAAQAAAAIAAAADAAAABQAAAAUAAAADAAAAAAAAAAAAAAAAAAAA"
1291 "AAAAABIAAAABAAAAAAAAAAAAAAABAAAAAQAAAAAAAAAEAAAAAAAAAPwBAAAAAAAABjxpbml0PgAG"
1292 "TFRlc3Q7ABJMamF2YS9sYW5nL09iamVjdDsAEkxqYXZhL2xhbmcvU3RyaW5nOwAJVGVzdC5qYXZh"
1293 "AAFWAAFhAAFiAAFjAAFkAAFlAAFmAAFnAAFoAAFpAAFqAAFrAAlsb2NhbF92YXIABG1haW4ABHRl"
1294 "c3QAAAABAAcOAAAAARYDARIDAAAAAQABAAEAAACUAQAABAAAAHAQAgAAAA4AAgAAAAAAAACZAQAA"
1295 "GAAAABoABgAaAAcAGgAIABoACQAaAAoAGgALABoADAAaAA0AGgAOABoADwAaABAAGgETAAAAAgAA"
1296 "gYAEpAMBCbwDAAALAAAAAAAAAAEAAAAAAAAAAQAAABQAAABwAAAAAgAAAAQAAADAAAAAAwAAAAEA"
1297 "AADQAAAABQAAAAMAAADcAAAABgAAAAEAAAD0AAAAAiAAABQAAAAUAQAAAyAAAAIAAACUAQAAASAA"
1298 "AAIAAACkAQAAACAAAAEAAAD8AQAAABAAAAEAAAAMAgAA";
1299
1300TEST_F(DexFileVerifierTest, DebugInfoTypeIdxTest) {
1301 {
1302 // The input dex file should be good before modification.
Logan Chiendd3208d2015-04-19 23:27:52 +08001303 std::string error_msg;
1304 std::unique_ptr<const DexFile> raw(OpenDexFileBase64(kDebugInfoTestDex,
David Sehre1123402018-02-01 02:46:18 -08001305 kLocationString,
Logan Chiendd3208d2015-04-19 23:27:52 +08001306 &error_msg));
1307 ASSERT_TRUE(raw.get() != nullptr) << error_msg;
1308 }
1309
Andreas Gampee6215c02015-08-31 18:54:38 -07001310 // Modify the debug information entry.
1311 VerifyModification(
1312 kDebugInfoTestDex,
1313 "debug_start_type_idx",
1314 [](DexFile* dex_file) {
1315 *(const_cast<uint8_t*>(dex_file->Begin()) + 416) = 0x14U;
1316 },
1317 "DBG_START_LOCAL type_idx");
Logan Chiendd3208d2015-04-19 23:27:52 +08001318}
1319
Andreas Gampeb512c0e2016-02-19 19:45:34 -08001320TEST_F(DexFileVerifierTest, SectionAlignment) {
1321 {
1322 // The input dex file should be good before modification. Any file is fine, as long as it
1323 // uses all sections.
Andreas Gampeb512c0e2016-02-19 19:45:34 -08001324 std::string error_msg;
1325 std::unique_ptr<const DexFile> raw(OpenDexFileBase64(kGoodTestDex,
David Sehre1123402018-02-01 02:46:18 -08001326 kLocationString,
Andreas Gampeb512c0e2016-02-19 19:45:34 -08001327 &error_msg));
1328 ASSERT_TRUE(raw.get() != nullptr) << error_msg;
1329 }
1330
1331 // Modify all section offsets to be unaligned.
1332 constexpr size_t kSections = 7;
1333 for (size_t i = 0; i < kSections; ++i) {
1334 VerifyModification(
1335 kGoodTestDex,
1336 "section_align",
1337 [&](DexFile* dex_file) {
1338 DexFile::Header* header = const_cast<DexFile::Header*>(
1339 reinterpret_cast<const DexFile::Header*>(dex_file->Begin()));
1340 uint32_t* off_ptr;
1341 switch (i) {
1342 case 0:
1343 off_ptr = &header->map_off_;
1344 break;
1345 case 1:
1346 off_ptr = &header->string_ids_off_;
1347 break;
1348 case 2:
1349 off_ptr = &header->type_ids_off_;
1350 break;
1351 case 3:
1352 off_ptr = &header->proto_ids_off_;
1353 break;
1354 case 4:
1355 off_ptr = &header->field_ids_off_;
1356 break;
1357 case 5:
1358 off_ptr = &header->method_ids_off_;
1359 break;
1360 case 6:
1361 off_ptr = &header->class_defs_off_;
1362 break;
1363
1364 static_assert(kSections == 7, "kSections is wrong");
1365 default:
1366 LOG(FATAL) << "Unexpected section";
1367 UNREACHABLE();
1368 }
1369 ASSERT_TRUE(off_ptr != nullptr);
1370 ASSERT_NE(*off_ptr, 0U) << i; // Should already contain a value (in use).
1371 (*off_ptr)++; // Add one, which should misalign it (all the sections
1372 // above are aligned by 4).
1373 },
1374 "should be aligned by 4 for");
1375 }
1376}
1377
Vladimir Marko0ca8add2016-05-03 17:17:50 +01001378// Generated from
1379//
1380// .class LOverloading;
1381//
1382// .super Ljava/lang/Object;
1383//
1384// .method public static foo()V
1385// .registers 1
1386// return-void
1387// .end method
1388//
1389// .method public static foo(I)V
1390// .registers 1
1391// return-void
1392// .end method
1393static const char kProtoOrderingTestDex[] =
1394 "ZGV4CjAzNQA1L+ABE6voQ9Lr4Ci//efB53oGnDr5PinsAQAAcAAAAHhWNBIAAAAAAAAAAFgBAAAG"
1395 "AAAAcAAAAAQAAACIAAAAAgAAAJgAAAAAAAAAAAAAAAIAAACwAAAAAQAAAMAAAAAMAQAA4AAAAOAA"
1396 "AADjAAAA8gAAAAYBAAAJAQAADQEAAAAAAAABAAAAAgAAAAMAAAADAAAAAwAAAAAAAAAEAAAAAwAA"
1397 "ABQBAAABAAAABQAAAAEAAQAFAAAAAQAAAAAAAAACAAAAAAAAAP////8AAAAASgEAAAAAAAABSQAN"
1398 "TE92ZXJsb2FkaW5nOwASTGphdmEvbGFuZy9PYmplY3Q7AAFWAAJWSQADZm9vAAAAAQAAAAAAAAAA"
1399 "AAAAAAAAAAEAAAAAAAAAAAAAAAEAAAAOAAAAAQABAAAAAAAAAAAAAQAAAA4AAAACAAAJpAIBCbgC"
1400 "AAAMAAAAAAAAAAEAAAAAAAAAAQAAAAYAAABwAAAAAgAAAAQAAACIAAAAAwAAAAIAAACYAAAABQAA"
1401 "AAIAAACwAAAABgAAAAEAAADAAAAAAiAAAAYAAADgAAAAARAAAAEAAAAUAQAAAxAAAAIAAAAcAQAA"
1402 "ASAAAAIAAAAkAQAAACAAAAEAAABKAQAAABAAAAEAAABYAQAA";
1403
1404TEST_F(DexFileVerifierTest, ProtoOrdering) {
1405 {
1406 // The input dex file should be good before modification.
Vladimir Marko0ca8add2016-05-03 17:17:50 +01001407 std::string error_msg;
1408 std::unique_ptr<const DexFile> raw(OpenDexFileBase64(kProtoOrderingTestDex,
David Sehre1123402018-02-01 02:46:18 -08001409 kLocationString,
Vladimir Marko0ca8add2016-05-03 17:17:50 +01001410 &error_msg));
1411 ASSERT_TRUE(raw.get() != nullptr) << error_msg;
1412 }
1413
1414 // Modify the order of the ProtoIds for two overloads of "foo" with the
1415 // same return type and one having longer parameter list than the other.
1416 for (size_t i = 0; i != 2; ++i) {
1417 VerifyModification(
1418 kProtoOrderingTestDex,
1419 "proto_ordering",
1420 [i](DexFile* dex_file) {
1421 uint32_t method_idx;
1422 const uint8_t* data = FindMethodData(dex_file, "foo", &method_idx);
1423 CHECK(data != nullptr);
1424 // There should be 2 methods called "foo".
1425 CHECK_LT(method_idx + 1u, dex_file->NumMethodIds());
1426 CHECK_EQ(dex_file->GetMethodId(method_idx).name_idx_,
1427 dex_file->GetMethodId(method_idx + 1).name_idx_);
1428 CHECK_EQ(dex_file->GetMethodId(method_idx).proto_idx_ + 1u,
1429 dex_file->GetMethodId(method_idx + 1).proto_idx_);
1430 // Their return types should be the same.
1431 uint32_t proto1_idx = dex_file->GetMethodId(method_idx).proto_idx_;
1432 const DexFile::ProtoId& proto1 = dex_file->GetProtoId(proto1_idx);
1433 const DexFile::ProtoId& proto2 = dex_file->GetProtoId(proto1_idx + 1u);
1434 CHECK_EQ(proto1.return_type_idx_, proto2.return_type_idx_);
1435 // And the first should not have any parameters while the second should have some.
1436 CHECK(!DexFileParameterIterator(*dex_file, proto1).HasNext());
1437 CHECK(DexFileParameterIterator(*dex_file, proto2).HasNext());
1438 if (i == 0) {
1439 // Swap the proto parameters and shorties to break the ordering.
1440 std::swap(const_cast<uint32_t&>(proto1.parameters_off_),
1441 const_cast<uint32_t&>(proto2.parameters_off_));
Andreas Gampe8a0128a2016-11-28 07:38:35 -08001442 std::swap(const_cast<dex::StringIndex&>(proto1.shorty_idx_),
1443 const_cast<dex::StringIndex&>(proto2.shorty_idx_));
Vladimir Marko0ca8add2016-05-03 17:17:50 +01001444 } else {
1445 // Copy the proto parameters and shorty to create duplicate proto id.
1446 const_cast<uint32_t&>(proto1.parameters_off_) = proto2.parameters_off_;
Andreas Gampe8a0128a2016-11-28 07:38:35 -08001447 const_cast<dex::StringIndex&>(proto1.shorty_idx_) = proto2.shorty_idx_;
Vladimir Marko0ca8add2016-05-03 17:17:50 +01001448 }
1449 },
1450 "Out-of-order proto_id arguments");
1451 }
1452}
1453
Roland Levillain621b5ea2016-05-18 11:41:33 +01001454// To generate a base64 encoded Dex file version 037 from Smali files, use:
1455//
Ben Gruver14fc9db2017-04-28 15:30:49 -07001456// smali assemble --api 24 -o classes.dex class1.smali [class2.smali ...]
Roland Levillain621b5ea2016-05-18 11:41:33 +01001457// base64 classes.dex >classes.dex.base64
1458
1459// Dex file version 037 generated from:
1460//
1461// .class public LB28685551;
1462// .super LB28685551;
1463
1464static const char kClassExtendsItselfTestDex[] =
1465 "ZGV4CjAzNwDeGbgRg1kb6swszpcTWrrOAALB++F4OPT0AAAAcAAAAHhWNBIAAAAAAAAAAKgAAAAB"
1466 "AAAAcAAAAAEAAAB0AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAAAHgAAABcAAAAmAAAAJgA"
1467 "AAAAAAAAAAAAAAEAAAAAAAAAAAAAAP////8AAAAAAAAAAAAAAAALTEIyODY4NTU1MTsAAAAABgAA"
1468 "AAAAAAABAAAAAAAAAAEAAAABAAAAcAAAAAIAAAABAAAAdAAAAAYAAAABAAAAeAAAAAIgAAABAAAA"
1469 "mAAAAAAQAAABAAAAqAAAAA==";
1470
1471TEST_F(DexFileVerifierTest, ClassExtendsItself) {
1472 VerifyModification(
1473 kClassExtendsItselfTestDex,
1474 "class_extends_itself",
1475 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1476 "Class with same type idx as its superclass: '0'");
1477}
1478
1479// Dex file version 037 generated from:
1480//
1481// .class public LFoo;
1482// .super LBar;
1483//
1484// and:
1485//
1486// .class public LBar;
1487// .super LFoo;
1488
1489static const char kClassesExtendOneAnotherTestDex[] =
1490 "ZGV4CjAzNwBXHSrwpDMwRBkg+L+JeQCuFNRLhQ86duEcAQAAcAAAAHhWNBIAAAAAAAAAANAAAAAC"
1491 "AAAAcAAAAAIAAAB4AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAgAAAIAAAABcAAAAwAAAAMAA"
1492 "AADHAAAAAAAAAAEAAAABAAAAAQAAAAAAAAAAAAAA/////wAAAAAAAAAAAAAAAAAAAAABAAAAAQAA"
1493 "AAAAAAD/////AAAAAAAAAAAAAAAABUxCYXI7AAVMRm9vOwAAAAYAAAAAAAAAAQAAAAAAAAABAAAA"
1494 "AgAAAHAAAAACAAAAAgAAAHgAAAAGAAAAAgAAAIAAAAACIAAAAgAAAMAAAAAAEAAAAQAAANAAAAA=";
1495
1496TEST_F(DexFileVerifierTest, ClassesExtendOneAnother) {
1497 VerifyModification(
1498 kClassesExtendOneAnotherTestDex,
1499 "classes_extend_one_another",
1500 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1501 "Invalid class definition ordering: class with type idx: '1' defined before"
1502 " superclass with type idx: '0'");
1503}
1504
1505// Dex file version 037 generated from:
1506//
1507// .class public LAll;
1508// .super LYour;
1509//
1510// and:
1511//
1512// .class public LYour;
1513// .super LBase;
1514//
1515// and:
1516//
1517// .class public LBase;
1518// .super LAll;
1519
1520static const char kCircularClassInheritanceTestDex[] =
1521 "ZGV4CjAzNwBMJxgP0SJz6oLXnKfl+J7lSEORLRwF5LNMAQAAcAAAAHhWNBIAAAAAAAAAAAABAAAD"
1522 "AAAAcAAAAAMAAAB8AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAwAAAIgAAABkAAAA6AAAAOgA"
1523 "AADvAAAA9wAAAAAAAAABAAAAAgAAAAEAAAABAAAAAAAAAAAAAAD/////AAAAAAAAAAAAAAAAAgAA"
1524 "AAEAAAABAAAAAAAAAP////8AAAAAAAAAAAAAAAAAAAAAAQAAAAIAAAAAAAAA/////wAAAAAAAAAA"
1525 "AAAAAAVMQWxsOwAGTEJhc2U7AAZMWW91cjsAAAYAAAAAAAAAAQAAAAAAAAABAAAAAwAAAHAAAAAC"
1526 "AAAAAwAAAHwAAAAGAAAAAwAAAIgAAAACIAAAAwAAAOgAAAAAEAAAAQAAAAABAAA=";
1527
1528TEST_F(DexFileVerifierTest, CircularClassInheritance) {
1529 VerifyModification(
1530 kCircularClassInheritanceTestDex,
1531 "circular_class_inheritance",
1532 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1533 "Invalid class definition ordering: class with type idx: '1' defined before"
1534 " superclass with type idx: '0'");
1535}
1536
1537// Dex file version 037 generated from:
1538//
1539// .class public abstract interface LInterfaceImplementsItself;
1540// .super Ljava/lang/Object;
1541// .implements LInterfaceImplementsItself;
1542
1543static const char kInterfaceImplementsItselfTestDex[] =
1544 "ZGV4CjAzNwCKKrjatp8XbXl5S/bEVJnqaBhjZkQY4440AQAAcAAAAHhWNBIAAAAAAAAAANwAAAAC"
1545 "AAAAcAAAAAIAAAB4AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAAAIAAAACUAAAAoAAAAKAA"
1546 "AAC9AAAAAAAAAAEAAAAAAAAAAQYAAAEAAADUAAAA/////wAAAAAAAAAAAAAAABtMSW50ZXJmYWNl"
1547 "SW1wbGVtZW50c0l0c2VsZjsAEkxqYXZhL2xhbmcvT2JqZWN0OwAAAAABAAAAAAAAAAcAAAAAAAAA"
1548 "AQAAAAAAAAABAAAAAgAAAHAAAAACAAAAAgAAAHgAAAAGAAAAAQAAAIAAAAACIAAAAgAAAKAAAAAB"
1549 "EAAAAQAAANQAAAAAEAAAAQAAANwAAAA=";
1550
1551TEST_F(DexFileVerifierTest, InterfaceImplementsItself) {
1552 VerifyModification(
1553 kInterfaceImplementsItselfTestDex,
1554 "interface_implements_itself",
1555 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1556 "Class with same type idx as implemented interface: '0'");
1557}
1558
1559// Dex file version 037 generated from:
1560//
1561// .class public abstract interface LPing;
1562// .super Ljava/lang/Object;
1563// .implements LPong;
1564//
1565// and:
1566//
1567// .class public abstract interface LPong;
1568// .super Ljava/lang/Object;
1569// .implements LPing;
1570
1571static const char kInterfacesImplementOneAnotherTestDex[] =
1572 "ZGV4CjAzNwD0Kk9sxlYdg3Dy1Cff0gQCuJAQfEP6ohZUAQAAcAAAAHhWNBIAAAAAAAAAAPwAAAAD"
1573 "AAAAcAAAAAMAAAB8AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAgAAAIgAAACMAAAAyAAAAMgA"
1574 "AADQAAAA2AAAAAAAAAABAAAAAgAAAAEAAAABBgAAAgAAAOwAAAD/////AAAAAAAAAAAAAAAAAAAA"
1575 "AAEGAAACAAAA9AAAAP////8AAAAAAAAAAAAAAAAGTFBpbmc7AAZMUG9uZzsAEkxqYXZhL2xhbmcv"
1576 "T2JqZWN0OwABAAAAAAAAAAEAAAABAAAABwAAAAAAAAABAAAAAAAAAAEAAAADAAAAcAAAAAIAAAAD"
1577 "AAAAfAAAAAYAAAACAAAAiAAAAAIgAAADAAAAyAAAAAEQAAACAAAA7AAAAAAQAAABAAAA/AAAAA==";
1578
1579TEST_F(DexFileVerifierTest, InterfacesImplementOneAnother) {
1580 VerifyModification(
1581 kInterfacesImplementOneAnotherTestDex,
1582 "interfaces_implement_one_another",
1583 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1584 "Invalid class definition ordering: class with type idx: '1' defined before"
1585 " implemented interface with type idx: '0'");
1586}
1587
1588// Dex file version 037 generated from:
1589//
1590// .class public abstract interface LA;
1591// .super Ljava/lang/Object;
1592// .implements LB;
1593//
1594// and:
1595//
1596// .class public abstract interface LB;
1597// .super Ljava/lang/Object;
1598// .implements LC;
1599//
1600// and:
1601//
1602// .class public abstract interface LC;
1603// .super Ljava/lang/Object;
1604// .implements LA;
1605
1606static const char kCircularInterfaceImplementationTestDex[] =
1607 "ZGV4CjAzNwCzKmD5Fol6XAU6ichYHcUTIP7Z7MdTcEmEAQAAcAAAAHhWNBIAAAAAAAAAACwBAAAE"
1608 "AAAAcAAAAAQAAACAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAwAAAJAAAACUAAAA8AAAAPAA"
1609 "AAD1AAAA+gAAAP8AAAAAAAAAAQAAAAIAAAADAAAAAgAAAAEGAAADAAAAHAEAAP////8AAAAAAAAA"
1610 "AAAAAAABAAAAAQYAAAMAAAAUAQAA/////wAAAAAAAAAAAAAAAAAAAAABBgAAAwAAACQBAAD/////"
1611 "AAAAAAAAAAAAAAAAA0xBOwADTEI7AANMQzsAEkxqYXZhL2xhbmcvT2JqZWN0OwAAAQAAAAIAAAAB"
1612 "AAAAAAAAAAEAAAABAAAABwAAAAAAAAABAAAAAAAAAAEAAAAEAAAAcAAAAAIAAAAEAAAAgAAAAAYA"
1613 "AAADAAAAkAAAAAIgAAAEAAAA8AAAAAEQAAADAAAAFAEAAAAQAAABAAAALAEAAA==";
1614
1615TEST_F(DexFileVerifierTest, CircularInterfaceImplementation) {
1616 VerifyModification(
1617 kCircularInterfaceImplementationTestDex,
1618 "circular_interface_implementation",
1619 [](DexFile* dex_file ATTRIBUTE_UNUSED) { /* empty */ },
1620 "Invalid class definition ordering: class with type idx: '2' defined before"
1621 " implemented interface with type idx: '0'");
1622}
1623
Aart Bik37d6a3b2016-06-21 18:30:10 -07001624TEST_F(DexFileVerifierTest, Checksum) {
1625 size_t length;
Alex Light9c20a142016-08-23 15:05:12 -07001626 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kGoodTestDex, &length));
Aart Bik37d6a3b2016-06-21 18:30:10 -07001627 CHECK(dex_bytes != nullptr);
1628 // Note: `dex_file` will be destroyed before `dex_bytes`.
1629 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1630 std::string error_msg;
1631
1632 // Good checksum: all pass.
1633 EXPECT_TRUE(DexFileVerifier::Verify(dex_file.get(),
1634 dex_file->Begin(),
1635 dex_file->Size(),
1636 "good checksum, no verify",
1637 /*verify_checksum*/ false,
1638 &error_msg));
1639 EXPECT_TRUE(DexFileVerifier::Verify(dex_file.get(),
1640 dex_file->Begin(),
1641 dex_file->Size(),
1642 "good checksum, verify",
1643 /*verify_checksum*/ true,
1644 &error_msg));
1645
1646 // Bad checksum: !verify_checksum passes verify_checksum fails.
1647 DexFile::Header* header = reinterpret_cast<DexFile::Header*>(
1648 const_cast<uint8_t*>(dex_file->Begin()));
1649 header->checksum_ = 0;
1650 EXPECT_TRUE(DexFileVerifier::Verify(dex_file.get(),
1651 dex_file->Begin(),
1652 dex_file->Size(),
1653 "bad checksum, no verify",
1654 /*verify_checksum*/ false,
1655 &error_msg));
1656 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1657 dex_file->Begin(),
1658 dex_file->Size(),
1659 "bad checksum, verify",
1660 /*verify_checksum*/ true,
1661 &error_msg));
1662 EXPECT_NE(error_msg.find("Bad checksum"), std::string::npos) << error_msg;
1663}
1664
Orion Hodson6c4921b2016-09-21 15:41:06 +01001665TEST_F(DexFileVerifierTest, BadStaticMethodName) {
1666 // Generated DEX file version (037) from:
1667 //
1668 // .class public LBadName;
1669 // .super Ljava/lang/Object;
1670 //
1671 // .method public static <bad_name> (II)V
1672 // .registers 2
1673 // .prologue
1674 // return-void
1675 // .end method
1676 //
1677 // .method public constructor <init>()V
1678 // .registers 1
1679 // .prologue
1680 // .line 1
1681 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1682 // return-void
1683 // .end method
1684 //
1685 static const char kDexBase64[] =
1686 "ZGV4CjAzNwC2NYlwyxEc/h6hv+hMeUVQPtiX6MQBcfgwAgAAcAAAAHhWNBIAAAAAAAAAAJABAAAI"
1687 "AAAAcAAAAAQAAACQAAAAAgAAAKAAAAAAAAAAAAAAAAMAAAC4AAAAAQAAANAAAABAAQAA8AAAAPAA"
1688 "AAD8AAAABAEAABIBAAAVAQAAIAEAADQBAAA3AQAAAwAAAAQAAAAFAAAABgAAAAYAAAADAAAAAAAA"
1689 "AAcAAAADAAAAPAEAAAEAAQAAAAAAAQAAAAEAAAACAAAAAQAAAAEAAAABAAAAAgAAAAAAAAACAAAA"
1690 "AAAAAIABAAAAAAAACjxiYWRfbmFtZT4ABjxpbml0PgAMQmFkTmFtZS5qYXZhAAFJAAlMQmFkTmFt"
1691 "ZTsAEkxqYXZhL2xhbmcvT2JqZWN0OwABVgADVklJAAIAAAAAAAAAAAAAAAACAAAHAAEABw4AAAIA"
1692 "AgAAAAAASAEAAAEAAAAOAAAAAQABAAEAAABOAQAABAAAAHAQAgAAAA4AAAACAAAJ1AIBgYAE6AIA"
1693 "AA0AAAAAAAAAAQAAAAAAAAABAAAACAAAAHAAAAACAAAABAAAAJAAAAADAAAAAgAAAKAAAAAFAAAA"
1694 "AwAAALgAAAAGAAAAAQAAANAAAAACIAAACAAAAPAAAAABEAAAAQAAADwBAAADEAAAAQAAAEQBAAAD"
1695 "IAAAAgAAAEgBAAABIAAAAgAAAFQBAAAAIAAAAQAAAIABAAAAEAAAAQAAAJABAAA=";
1696
1697 size_t length;
1698 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
1699 CHECK(dex_bytes != nullptr);
1700 // Note: `dex_file` will be destroyed before `dex_bytes`.
1701 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1702 std::string error_msg;
1703 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1704 dex_file->Begin(),
1705 dex_file->Size(),
1706 "bad static method name",
1707 /*verify_checksum*/ true,
1708 &error_msg));
1709}
1710
1711TEST_F(DexFileVerifierTest, BadVirtualMethodName) {
1712 // Generated DEX file version (037) from:
1713 //
1714 // .class public LBadVirtualName;
1715 // .super Ljava/lang/Object;
1716 //
1717 // .method public <bad_name> (II)V
1718 // .registers 2
1719 // return-void
1720 // .end method
1721 //
1722 // .method public constructor <init>()V
1723 // .registers 1
1724 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1725 // return-void
1726 // .end method
1727 //
1728 static const char kDexBase64[] =
1729 "ZGV4CjAzNwDcPC8B2E7kYTZmeHX2u2IqrpWV9EXBHpE8AgAAcAAAAHhWNBIAAAAAAAAAAJwBAAAI"
1730 "AAAAcAAAAAQAAACQAAAAAgAAAKAAAAAAAAAAAAAAAAMAAAC4AAAAAQAAANAAAABMAQAA8AAAAPAA"
1731 "AAD8AAAABAEAABkBAAAcAQAALgEAAEIBAABFAQAAAwAAAAQAAAAFAAAABgAAAAYAAAADAAAAAAAA"
1732 "AAcAAAADAAAATAEAAAEAAQAAAAAAAQAAAAEAAAACAAAAAQAAAAEAAAABAAAAAgAAAAAAAAACAAAA"
1733 "AAAAAI4BAAAAAAAACjxiYWRfbmFtZT4ABjxpbml0PgATQmFkVmlydHVhbE5hbWUuamF2YQABSQAQ"
1734 "TEJhZFZpcnR1YWxOYW1lOwASTGphdmEvbGFuZy9PYmplY3Q7AAFWAANWSUkAAAACAAAAAAAAAAAA"
1735 "AAABAAcOAAACAAAHAAABAAEAAQAAAFgBAAAEAAAAcBACAAAADgADAAMAAAAAAF0BAAABAAAADgAA"
1736 "AAEBAYGABOQCAAH8Ag0AAAAAAAAAAQAAAAAAAAABAAAACAAAAHAAAAACAAAABAAAAJAAAAADAAAA"
1737 "AgAAAKAAAAAFAAAAAwAAALgAAAAGAAAAAQAAANAAAAACIAAACAAAAPAAAAABEAAAAQAAAEwBAAAD"
1738 "EAAAAQAAAFQBAAADIAAAAgAAAFgBAAABIAAAAgAAAGQBAAAAIAAAAQAAAI4BAAAAEAAAAQAAAJwB"
1739 "AAA=";
1740
1741 size_t length;
1742 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
1743 CHECK(dex_bytes != nullptr);
1744 // Note: `dex_file` will be destroyed before `dex_bytes`.
1745 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1746 std::string error_msg;
1747 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1748 dex_file->Begin(),
1749 dex_file->Size(),
1750 "bad virtual method name",
1751 /*verify_checksum*/ true,
1752 &error_msg));
1753}
1754
1755TEST_F(DexFileVerifierTest, BadClinitSignature) {
1756 // Generated DEX file version (037) from:
1757 //
1758 // .class public LOneClinitBadSig;
1759 // .super Ljava/lang/Object;
1760 //
1761 // .method public static constructor <clinit>(II)V
1762 // .registers 2
1763 // return-void
1764 // .end method
1765 //
1766 // .method public constructor <init>()V
1767 // .registers 1
1768 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1769 // return-void
1770 // .end method
1771 //
1772 static const char kDexBase64[] =
1773 "ZGV4CjAzNwBNOwTbfJmWq5eMOlxUY4EICGiEGJMVg8RAAgAAcAAAAHhWNBIAAAAAAAAAAKABAAAI"
1774 "AAAAcAAAAAQAAACQAAAAAgAAAKAAAAAAAAAAAAAAAAMAAAC4AAAAAQAAANAAAABQAQAA8AAAAPAA"
1775 "AAD6AAAAAgEAAAUBAAAYAQAALAEAAEIBAABFAQAAAgAAAAMAAAAEAAAABgAAAAYAAAADAAAAAAAA"
1776 "AAcAAAADAAAATAEAAAEAAQAAAAAAAQAAAAEAAAACAAAAAQAAAAEAAAABAAAAAgAAAAAAAAAFAAAA"
1777 "AAAAAJABAAAAAAAACDxjbGluaXQ+AAY8aW5pdD4AAUkAEUxPbmVDbGluaXRCYWRTaWc7ABJMamF2"
1778 "YS9sYW5nL09iamVjdDsAFE9uZUNsaW5pdEJhZFNpZy5qYXZhAAFWAANWSUkAAAACAAAAAAAAAAAA"
1779 "AAAAAgAABwABAAcOAAACAAIAAAAAAFgBAAABAAAADgAAAAEAAQABAAAAXgEAAAQAAABwEAIAAAAO"
1780 "AAAAAgAAiYAE5AIBgYAE+AINAAAAAAAAAAEAAAAAAAAAAQAAAAgAAABwAAAAAgAAAAQAAACQAAAA"
1781 "AwAAAAIAAACgAAAABQAAAAMAAAC4AAAABgAAAAEAAADQAAAAAiAAAAgAAADwAAAAARAAAAEAAABM"
1782 "AQAAAxAAAAEAAABUAQAAAyAAAAIAAABYAQAAASAAAAIAAABkAQAAACAAAAEAAACQAQAAABAAAAEA"
1783 "AACgAQAA";
1784
1785 size_t length;
1786 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
1787 CHECK(dex_bytes != nullptr);
1788 // Note: `dex_file` will be destroyed before `dex_bytes`.
1789 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1790 std::string error_msg;
1791 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1792 dex_file->Begin(),
1793 dex_file->Size(),
1794 "bad clinit signature",
1795 /*verify_checksum*/ true,
1796 &error_msg));
1797}
1798
1799TEST_F(DexFileVerifierTest, BadClinitSignatureAgain) {
1800 // Generated DEX file version (037) from:
1801 //
1802 // .class public LOneClinitBadSigAgain;
1803 // .super Ljava/lang/Object;
1804 //
1805 // .method public static constructor <clinit>()I
1806 // .registers 1
1807 // const/4 v0, 1
1808 // return v0
1809 // .end method
1810 //
1811 // .method public constructor <init>()V
1812 // .registers 1
1813 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1814 // return-void
1815 // .end method
1816 //
1817 static const char kDexBase64[] =
1818 "ZGV4CjAzNwBfPcPu5NVwKUqZIu/YR8xqVlVD5UzTk0gEAgAAcAAAAHhWNBIAAAAAAAAAAIgBAAAH"
1819 "AAAAcAAAAAQAAACMAAAAAgAAAJwAAAAAAAAAAAAAAAMAAAC0AAAAAQAAAMwAAAAYAQAA7AAAAOwA"
1820 "AAD2AAAA/gAAAAEBAAAZAQAALQEAAEgBAAACAAAAAwAAAAQAAAAGAAAAAgAAAAAAAAAAAAAABgAA"
1821 "AAMAAAAAAAAAAQAAAAAAAAABAAEAAQAAAAIAAQABAAAAAQAAAAEAAAACAAAAAAAAAAUAAAAAAAAA"
1822 "eAEAAAAAAAAIPGNsaW5pdD4ABjxpbml0PgABSQAWTE9uZUNsaW5pdEJhZFNpZ0FnYWluOwASTGph"
1823 "dmEvbGFuZy9PYmplY3Q7ABlPbmVDbGluaXRCYWRTaWdBZ2Fpbi5qYXZhAAFWAAABAAAAAAAAAAAA"
1824 "AAACAAAAEhAPAAEAAQABAAAAAAAAAAQAAABwEAIAAAAOAAAAAgAAiYAEzAIBgYAE4AIKAAAAAAAA"
1825 "AAEAAAAAAAAAAQAAAAcAAABwAAAAAgAAAAQAAACMAAAAAwAAAAIAAACcAAAABQAAAAMAAAC0AAAA"
1826 "BgAAAAEAAADMAAAAAiAAAAcAAADsAAAAASAAAAIAAABMAQAAACAAAAEAAAB4AQAAABAAAAEAAACI"
1827 "AQAA";
1828
1829 size_t length;
1830 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
1831 CHECK(dex_bytes != nullptr);
1832 // Note: `dex_file` will be destroyed before `dex_bytes`.
1833 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1834 std::string error_msg;
1835 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1836 dex_file->Begin(),
1837 dex_file->Size(),
1838 "bad clinit signature",
1839 /*verify_checksum*/ true,
1840 &error_msg));
1841}
1842
1843TEST_F(DexFileVerifierTest, BadInitSignature) {
1844 // Generated DEX file version (037) from:
1845 //
1846 // .class public LBadInitSig;
1847 // .super Ljava/lang/Object;
1848 //
1849 // .method public constructor <init>()I
1850 // .registers 1
1851 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
1852 // const v0, 1
1853 // return v0
1854 // .end method
1855 //
1856 static const char kDexBase64[] =
1857 "ZGV4CjAzNwCdMdeh1KoHWamF2Prq32LF39YZ78fV7q+wAQAAcAAAAHhWNBIAAAAAAAAAADQBAAAF"
1858 "AAAAcAAAAAQAAACEAAAAAgAAAJQAAAAAAAAAAAAAAAIAAACsAAAAAQAAALwAAADUAAAA3AAAANwA"
1859 "AADkAAAA5wAAAPUAAAAJAQAAAQAAAAIAAAADAAAABAAAAAEAAAAAAAAAAAAAAAQAAAADAAAAAAAA"
1860 "AAEAAAAAAAAAAgABAAAAAAABAAAAAQAAAAIAAAAAAAAA/////wAAAAAqAQAAAAAAAAY8aW5pdD4A"
1861 "AUkADExCYWRJbml0U2lnOwASTGphdmEvbGFuZy9PYmplY3Q7AAFWAAEAAQABAAAAAAAAAAcAAABw"
1862 "EAEAAAAUAAEAAAAPAAAAAQAAgYAEjAIKAAAAAAAAAAEAAAAAAAAAAQAAAAUAAABwAAAAAgAAAAQA"
1863 "AACEAAAAAwAAAAIAAACUAAAABQAAAAIAAACsAAAABgAAAAEAAAC8AAAAAiAAAAUAAADcAAAAASAA"
1864 "AAEAAAAMAQAAACAAAAEAAAAqAQAAABAAAAEAAAA0AQAA";
1865
1866 size_t length;
1867 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
1868 CHECK(dex_bytes != nullptr);
1869 // Note: `dex_file` will be destroyed before `dex_bytes`.
1870 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
1871 std::string error_msg;
1872 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
1873 dex_file->Begin(),
1874 dex_file->Size(),
1875 "bad init signature",
1876 /*verify_checksum*/ true,
1877 &error_msg));
1878}
1879
Orion Hodson12f4ff42017-01-13 16:43:12 +00001880static const char* kInvokeCustomDexFiles[] = {
1881 // TODO(oth): Revisit this test when we have smali / dx support.
1882 // https://cs.corp.google.com/android/toolchain/jack/jack-tests/tests/com/android/jack/java7/invokecustom/test001/Tests.java
1883 "ZGV4CjAzOAAEj12s/acmmdGuDL92SWSBh6iLBjxgomWkCAAAcAAAAHhWNBIAAAAAAAAAALwHAAAx"
1884 "AAAAcAAAABYAAAA0AQAACQAAAIwBAAADAAAA+AEAAAsAAAAQAgAAAQAAAHACAAAMBgAAmAIAAMID"
1885 "AADKAwAAzQMAANIDAADhAwAA5AMAAOoDAAAfBAAAUgQAAIMEAAC4BAAA1AQAAOsEAAD+BAAAEgUA"
1886 "ACYFAAA6BQAAUQUAAG4FAACTBQAAtAUAAN0FAAD/BQAAHgYAADgGAABKBgAAVgYAAFkGAABdBgAA"
1887 "YgYAAGYGAAB7BgAAgAYAAI8GAACdBgAAtAYAAMMGAADSBgAA3gYAAPIGAAD4BgAABgcAAA4HAAAU"
1888 "BwAAGgcAAB8HAAAoBwAANAcAADoHAAABAAAABgAAAAcAAAAIAAAACQAAAAoAAAALAAAADAAAAA0A"
1889 "AAAOAAAADwAAABAAAAARAAAAEgAAABMAAAAUAAAAFQAAABYAAAAXAAAAGAAAABoAAAAeAAAAAgAA"
1890 "AAAAAACMAwAABQAAAAwAAACUAwAABQAAAA4AAACgAwAABAAAAA8AAAAAAAAAGgAAABQAAAAAAAAA"
1891 "GwAAABQAAACsAwAAHAAAABQAAACMAwAAHQAAABQAAAC0AwAAHQAAABQAAAC8AwAAAwADAAMAAAAE"
1892 "AAwAJAAAAAoABgAsAAAABAAEAAAAAAAEAAAAHwAAAAQAAQAoAAAABAAIACoAAAAEAAQALwAAAAYA"
1893 "BQAtAAAACAAEAAAAAAANAAcAAAAAAA8AAgAlAAAAEAADACkAAAASAAYAIQAAAJYHAACWBwAABAAA"
1894 "AAEAAAAIAAAAAAAAABkAAABkAwAAnQcAAAAAAAAEAAAAAgAAAAEAAABjBwAAAQAAAIsHAAACAAAA"
1895 "iwcAAJMHAAABAAEAAQAAAEEHAAAEAAAAcBAGAAAADgADAAIAAAAAAEYHAAADAAAAkAABAg8AAAAF"
1896 "AAMABAAAAE0HAAAQAAAAcQAJAAAADAAcAQQAbkAIABBDDAAiAQ0AcCAHAAEAEQEEAAEAAgAAAFYH"
1897 "AAAMAAAAYgACABIhEjL8IAAAIQAKAW4gBQAQAA4AAwABAAIAAABdBwAACwAAABIgEjH8IAEAEAAK"
1898 "ABJRcSAKAAEADgAAAAAAAAAAAAAAAwAAAAAAAAABAAAAmAIAAAIAAACgAgAABAAAAKgCAAACAAAA"
1899 "AAAAAAMAAAAPAAkAEQAAAAMAAAAHAAkAEQAAAAEAAAAAAAAAAQAAAA4AAAABAAAAFQAGPGluaXQ+"
1900 "AAFJAANJSUkADUlOVk9LRV9TVEFUSUMAAUwABExMTEwAM0xjb20vYW5kcm9pZC9qYWNrL2Fubm90"
1901 "YXRpb25zL0NhbGxlZEJ5SW52b2tlQ3VzdG9tOwAxTGNvbS9hbmRyb2lkL2phY2svYW5ub3RhdGlv"
1902 "bnMvTGlua2VyTWV0aG9kSGFuZGxlOwAvTGNvbS9hbmRyb2lkL2phY2svYW5ub3RhdGlvbnMvTWV0"
1903 "aG9kSGFuZGxlS2luZDsAM0xjb20vYW5kcm9pZC9qYWNrL2phdmE3L2ludm9rZWN1c3RvbS90ZXN0"
1904 "MDAxL1Rlc3RzOwAaTGRhbHZpay9hbm5vdGF0aW9uL1Rocm93czsAFUxqYXZhL2lvL1ByaW50U3Ry"
1905 "ZWFtOwARTGphdmEvbGFuZy9DbGFzczsAEkxqYXZhL2xhbmcvT2JqZWN0OwASTGphdmEvbGFuZy9T"
1906 "dHJpbmc7ABJMamF2YS9sYW5nL1N5c3RlbTsAFUxqYXZhL2xhbmcvVGhyb3dhYmxlOwAbTGphdmEv"
1907 "bGFuZy9pbnZva2UvQ2FsbFNpdGU7ACNMamF2YS9sYW5nL2ludm9rZS9Db25zdGFudENhbGxTaXRl"
1908 "OwAfTGphdmEvbGFuZy9pbnZva2UvTWV0aG9kSGFuZGxlOwAnTGphdmEvbGFuZy9pbnZva2UvTWV0"
1909 "aG9kSGFuZGxlcyRMb29rdXA7ACBMamF2YS9sYW5nL2ludm9rZS9NZXRob2RIYW5kbGVzOwAdTGph"
1910 "dmEvbGFuZy9pbnZva2UvTWV0aG9kVHlwZTsAGExqdW5pdC9mcmFtZXdvcmsvQXNzZXJ0OwAQTG9y"
1911 "Zy9qdW5pdC9UZXN0OwAKVGVzdHMuamF2YQABVgACVkkAA1ZJSQACVkwAE1tMamF2YS9sYW5nL1N0"
1912 "cmluZzsAA2FkZAANYXJndW1lbnRUeXBlcwAMYXNzZXJ0RXF1YWxzABVlbWl0dGVyOiBqYWNrLTQu"
1913 "MC1lbmcADWVuY2xvc2luZ1R5cGUADWZpZWxkQ2FsbFNpdGUACmZpbmRTdGF0aWMAEmludm9rZU1l"
1914 "dGhvZEhhbmRsZQAEa2luZAAMbGlua2VyTWV0aG9kAAZsb29rdXAABG1haW4ABG5hbWUAA291dAAH"
1915 "cHJpbnRsbgAKcmV0dXJuVHlwZQAEdGVzdAAFdmFsdWUAIgAHDgAvAgAABw4ANQMAAAAHDqUAPwEA"
1916 "Bw60ADsABw6lAAABBCAcAhgAGAAmHAEdAgQgHAMYDxgJGBEjGAQnGwArFygrFx8uGAACBQEwHAEY"
1917 "CwETAAMWABcfFQABAAQBAQkAgYAEtAUBCswFAQrkBQEJlAYEAbwGAAAAEwAAAAAAAAABAAAAAAAA"
1918 "AAEAAAAxAAAAcAAAAAIAAAAWAAAANAEAAAMAAAAJAAAAjAEAAAQAAAADAAAA+AEAAAUAAAALAAAA"
1919 "EAIAAAcAAAACAAAAaAIAAAYAAAABAAAAcAIAAAgAAAABAAAAkAIAAAMQAAADAAAAmAIAAAEgAAAF"
1920 "AAAAtAIAAAYgAAABAAAAZAMAAAEQAAAGAAAAjAMAAAIgAAAxAAAAwgMAAAMgAAAFAAAAQQcAAAQg"
1921 "AAADAAAAYwcAAAUgAAABAAAAlgcAAAAgAAABAAAAnQcAAAAQAAABAAAAvAcAAA==",
1922 // https://cs.corp.google.com/android/toolchain/jack/jack-tests/tests/com/android/jack/java7/invokecustom/test002/Tests.java
1923 "ZGV4CjAzOAAzq3aGAwKhT4QQj4lqNfZJAO8Tm24uTyNICQAAcAAAAHhWNBIAAAAAAAAAAGAIAAA2"
1924 "AAAAcAAAABgAAABIAQAACQAAAKgBAAAEAAAAFAIAAA0AAAA0AgAAAQAAAKQCAAB8BgAAzAIAACYE"
1925 "AAAwBAAAOAQAAEQEAABHBAAATAQAAE8EAABVBAAAigQAALwEAADtBAAAIgUAAD4FAABVBQAAaAUA"
1926 "AH0FAACRBQAApQUAALkFAADQBQAA7QUAABIGAAAzBgAAXAYAAH4GAACdBgAAtwYAAMkGAADPBgAA"
1927 "2wYAAN4GAADiBgAA5wYAAOsGAAD/BgAAFAcAABkHAAAoBwAANgcAAE0HAABcBwAAawcAAH4HAACK"
1928 "BwAAkAcAAJgHAACeBwAAqgcAALAHAAC1BwAAxgcAAM8HAADbBwAA4QcAAAMAAAAHAAAACAAAAAkA"
1929 "AAAKAAAACwAAAAwAAAANAAAADgAAAA8AAAAQAAAAEQAAABIAAAATAAAAFAAAABUAAAAWAAAAFwAA"
1930 "ABgAAAAZAAAAGgAAAB0AAAAhAAAAIgAAAAQAAAAAAAAA8AMAAAYAAAAPAAAA+AMAAAUAAAAQAAAA"
1931 "AAAAAAYAAAASAAAABAQAAB0AAAAVAAAAAAAAAB4AAAAVAAAAEAQAAB8AAAAVAAAA8AMAACAAAAAV"
1932 "AAAAGAQAACAAAAAVAAAAIAQAAAMAAwACAAAABAANACgAAAAIAAcAGwAAAAsABgAwAAAABAAEAAAA"
1933 "AAAEAAQAAQAAAAQAAAAjAAAABAAIAC0AAAAEAAQANAAAAAYABQAyAAAACQAEAAEAAAAMAAQAMQAA"
1934 "AA4ABwABAAAAEAABACoAAAARAAIALAAAABIAAwAuAAAAEwAGACUAAAA4CAAAOAgAAAQAAAABAAAA"
1935 "CQAAAAAAAAAcAAAA0AMAAD8IAAAAAAAAAQAAAAEAAAABAAAADggAAAIAAAAtCAAANQgAAAgAAAAE"
1936 "AAEA6AcAACoAAABxAAoAAAAMABwBBAAbAiMAAABiAwIAYgQCABIVI1UWAGIGAgASB00GBQdxMAsA"
1937 "QwUMA25ACQAQMgwAIgEOAHAgCAABAGkBAQAOAA0AbhAHAAAAKPsAAAAAJAABAAEBDCUBAAEAAQAA"
1938 "APUHAAAEAAAAcBAGAAAADgADAAIAAAAAAPoHAAADAAAAkAABAg8AAAAEAAEAAgAAAAEIAAAMAAAA"
1939 "YgADABIhEjL8IAAAIQAKAW4gBQAQAA4AAwABAAIAAAAICAAACwAAABIgEjH8IAEAEAAKABJRcSAM"
1940 "AAEADgAAAAAAAAAAAAAAAgAAAAAAAAACAAAAzAIAAAQAAADUAgAAAgAAAAAAAAADAAAABwAKABIA"
1941 "AAADAAAABwAHABYAAAABAAAAAAAAAAEAAAAPAAAAAQAAABcACDxjbGluaXQ+AAY8aW5pdD4ACkdF"
1942 "VF9TVEFUSUMAAUkAA0lJSQABTAAETExMTAAzTGNvbS9hbmRyb2lkL2phY2svYW5ub3RhdGlvbnMv"
1943 "Q2FsbGVkQnlJbnZva2VDdXN0b207ADBMY29tL2FuZHJvaWQvamFjay9hbm5vdGF0aW9ucy9MaW5r"
1944 "ZXJGaWVsZEhhbmRsZTsAL0xjb20vYW5kcm9pZC9qYWNrL2Fubm90YXRpb25zL01ldGhvZEhhbmRs"
1945 "ZUtpbmQ7ADNMY29tL2FuZHJvaWQvamFjay9qYXZhNy9pbnZva2VjdXN0b20vdGVzdDAwMi9UZXN0"
1946 "czsAGkxkYWx2aWsvYW5ub3RhdGlvbi9UaHJvd3M7ABVMamF2YS9pby9QcmludFN0cmVhbTsAEUxq"
1947 "YXZhL2xhbmcvQ2xhc3M7ABNMamF2YS9sYW5nL0ludGVnZXI7ABJMamF2YS9sYW5nL09iamVjdDsA"
1948 "EkxqYXZhL2xhbmcvU3RyaW5nOwASTGphdmEvbGFuZy9TeXN0ZW07ABVMamF2YS9sYW5nL1Rocm93"
1949 "YWJsZTsAG0xqYXZhL2xhbmcvaW52b2tlL0NhbGxTaXRlOwAjTGphdmEvbGFuZy9pbnZva2UvQ29u"
1950 "c3RhbnRDYWxsU2l0ZTsAH0xqYXZhL2xhbmcvaW52b2tlL01ldGhvZEhhbmRsZTsAJ0xqYXZhL2xh"
1951 "bmcvaW52b2tlL01ldGhvZEhhbmRsZXMkTG9va3VwOwAgTGphdmEvbGFuZy9pbnZva2UvTWV0aG9k"
1952 "SGFuZGxlczsAHUxqYXZhL2xhbmcvaW52b2tlL01ldGhvZFR5cGU7ABhManVuaXQvZnJhbWV3b3Jr"
1953 "L0Fzc2VydDsAEExvcmcvanVuaXQvVGVzdDsABFRZUEUAClRlc3RzLmphdmEAAVYAAlZJAANWSUkA"
1954 "AlZMABJbTGphdmEvbGFuZy9DbGFzczsAE1tMamF2YS9sYW5nL1N0cmluZzsAA2FkZAANYXJndW1l"
1955 "bnRUeXBlcwAMYXNzZXJ0RXF1YWxzABVlbWl0dGVyOiBqYWNrLTQuMC1lbmcADWVuY2xvc2luZ1R5"
1956 "cGUADWZpZWxkQ2FsbFNpdGUAEWZpZWxkTWV0aG9kSGFuZGxlAApmaW5kU3RhdGljAARraW5kAAZs"
1957 "b29rdXAABG1haW4ACm1ldGhvZFR5cGUABG5hbWUAA291dAAPcHJpbnRTdGFja1RyYWNlAAdwcmlu"
1958 "dGxuAApyZXR1cm5UeXBlAAR0ZXN0AAV2YWx1ZQAoAAcOAR0PAnh3Jh4AIQAHDgA2AgAABw4APwEA"
1959 "Bw60ADsABw6lAAABBCQcAhgAGAApHAEdAgMnGAQrGwAvFygvFyMzGAACBQE1HAEYDAEUAAMWABcj"
1960 "FQABAAQBAQkAiIAE4AUBgYAE0AYBCugGAQmABwQBqAcAAAATAAAAAAAAAAEAAAAAAAAAAQAAADYA"
1961 "AABwAAAAAgAAABgAAABIAQAAAwAAAAkAAACoAQAABAAAAAQAAAAUAgAABQAAAA0AAAA0AgAABwAA"
1962 "AAIAAACcAgAABgAAAAEAAACkAgAACAAAAAEAAADEAgAAAxAAAAIAAADMAgAAASAAAAUAAADgAgAA"
1963 "BiAAAAEAAADQAwAAARAAAAYAAADwAwAAAiAAADYAAAAmBAAAAyAAAAUAAADoBwAABCAAAAMAAAAO"
1964 "CAAABSAAAAEAAAA4CAAAACAAAAEAAAA/CAAAABAAAAEAAABgCAAA",
1965 // https://cs.corp.google.com/android/toolchain/jack/jack-tests/tests/com/android/jack/java7/invokecustom/test003/Tests.java
1966 "ZGV4CjAzOABjnhkFatj30/7cHTCJsfr7vAjz9/p+Y+TcCAAAcAAAAHhWNBIAAAAAAAAAAPQHAAAx"
1967 "AAAAcAAAABYAAAA0AQAACQAAAIwBAAADAAAA+AEAAAsAAAAQAgAAAQAAAHACAABEBgAAmAIAAOoD"
1968 "AADyAwAA9QMAAP4DAAANBAAAEAQAABYEAABLBAAAfgQAAK8EAADkBAAAAAUAABcFAAAqBQAAPgUA"
1969 "AFIFAABmBQAAfQUAAJoFAAC/BQAA4AUAAAkGAAArBgAASgYAAGQGAAB2BgAAggYAAIUGAACJBgAA"
1970 "jgYAAJIGAACnBgAArAYAALsGAADJBgAA4AYAAO8GAAD+BgAACgcAAB4HAAAkBwAAMgcAADoHAABA"
1971 "BwAARgcAAEsHAABUBwAAYAcAAGYHAAABAAAABgAAAAcAAAAIAAAACQAAAAoAAAALAAAADAAAAA0A"
1972 "AAAOAAAADwAAABAAAAARAAAAEgAAABMAAAAUAAAAFQAAABYAAAAXAAAAGAAAABoAAAAeAAAAAgAA"
1973 "AAAAAACkAwAABQAAAAwAAAC0AwAABQAAAA4AAADAAwAABAAAAA8AAAAAAAAAGgAAABQAAAAAAAAA"
1974 "GwAAABQAAADMAwAAHAAAABQAAADUAwAAHQAAABQAAADcAwAAHQAAABQAAADkAwAAAwADAAMAAAAE"
1975 "AAwAJAAAAAoABgAsAAAABAAEAAAAAAAEAAAAHwAAAAQAAQAoAAAABAAIACoAAAAEAAQALwAAAAYA"
1976 "BQAtAAAACAAEAAAAAAANAAcAAAAAAA8AAgAlAAAAEAADACkAAAASAAYAIQAAAM4HAADOBwAABAAA"
1977 "AAEAAAAIAAAAAAAAABkAAAB8AwAA1QcAAAAAAAAEAAAAAgAAAAEAAACTBwAAAQAAAMMHAAACAAAA"
1978 "wwcAAMsHAAABAAEAAQAAAG0HAAAEAAAAcBAGAAAADgAHAAYAAAAAAHIHAAAHAAAAkAABArAwsECw"
1979 "ULBgDwAAAAUAAwAEAAAAfQcAABAAAABxAAkAAAAMABwBBABuQAgAEEMMACIBDQBwIAcAAQARAQgA"
1980 "AQACAAAAhgcAABAAAABiBgIAEhASIRIyEkMSVBJl/QYAAAAACgBuIAUABgAOAAcAAQACAAAAjQcA"
1981 "ABAAAAASEBIhEjISQxJUEmX9BgEAAAAKABMBFQBxIAoAAQAOAAAAAAAAAAAAAwAAAAAAAAABAAAA"
1982 "mAIAAAIAAACgAgAABAAAAKgCAAAGAAAAAAAAAAAAAAAAAAAAAwAAAA8ACQARAAAAAwAAAAcACQAR"
1983 "AAAAAQAAAAAAAAACAAAAAAAAAAEAAAAOAAAAAQAAABUABjxpbml0PgABSQAHSUlJSUlJSQANSU5W"
1984 "T0tFX1NUQVRJQwABTAAETExMTAAzTGNvbS9hbmRyb2lkL2phY2svYW5ub3RhdGlvbnMvQ2FsbGVk"
1985 "QnlJbnZva2VDdXN0b207ADFMY29tL2FuZHJvaWQvamFjay9hbm5vdGF0aW9ucy9MaW5rZXJNZXRo"
1986 "b2RIYW5kbGU7AC9MY29tL2FuZHJvaWQvamFjay9hbm5vdGF0aW9ucy9NZXRob2RIYW5kbGVLaW5k"
1987 "OwAzTGNvbS9hbmRyb2lkL2phY2svamF2YTcvaW52b2tlY3VzdG9tL3Rlc3QwMDMvVGVzdHM7ABpM"
1988 "ZGFsdmlrL2Fubm90YXRpb24vVGhyb3dzOwAVTGphdmEvaW8vUHJpbnRTdHJlYW07ABFMamF2YS9s"
1989 "YW5nL0NsYXNzOwASTGphdmEvbGFuZy9PYmplY3Q7ABJMamF2YS9sYW5nL1N0cmluZzsAEkxqYXZh"
1990 "L2xhbmcvU3lzdGVtOwAVTGphdmEvbGFuZy9UaHJvd2FibGU7ABtMamF2YS9sYW5nL2ludm9rZS9D"
1991 "YWxsU2l0ZTsAI0xqYXZhL2xhbmcvaW52b2tlL0NvbnN0YW50Q2FsbFNpdGU7AB9MamF2YS9sYW5n"
1992 "L2ludm9rZS9NZXRob2RIYW5kbGU7ACdMamF2YS9sYW5nL2ludm9rZS9NZXRob2RIYW5kbGVzJExv"
1993 "b2t1cDsAIExqYXZhL2xhbmcvaW52b2tlL01ldGhvZEhhbmRsZXM7AB1MamF2YS9sYW5nL2ludm9r"
1994 "ZS9NZXRob2RUeXBlOwAYTGp1bml0L2ZyYW1ld29yay9Bc3NlcnQ7ABBMb3JnL2p1bml0L1Rlc3Q7"
1995 "AApUZXN0cy5qYXZhAAFWAAJWSQADVklJAAJWTAATW0xqYXZhL2xhbmcvU3RyaW5nOwADYWRkAA1h"
1996 "cmd1bWVudFR5cGVzAAxhc3NlcnRFcXVhbHMAFWVtaXR0ZXI6IGphY2stNC4wLWVuZwANZW5jbG9z"
1997 "aW5nVHlwZQANZmllbGRDYWxsU2l0ZQAKZmluZFN0YXRpYwASaW52b2tlTWV0aG9kSGFuZGxlAARr"
1998 "aW5kAAxsaW5rZXJNZXRob2QABmxvb2t1cAAEbWFpbgAEbmFtZQADb3V0AAdwcmludGxuAApyZXR1"
1999 "cm5UeXBlAAR0ZXN0AAV2YWx1ZQAiAAcOAC8GAAAAAAAABw4ANQMAAAAHDqUAPwEABw7wADsABw7w"
2000 "AAABBCAcBhgAGAAYABgAGAAYACYcAR0CBCAcAxgPGAkYESMYBCcbACsXKCsXHy4YAAIFATAcARgL"
2001 "ARMAAxYAFx8VAAEABAEBCQCBgAS0BQEKzAUBCuwFAQmcBgQBzAYAAAATAAAAAAAAAAEAAAAAAAAA"
2002 "AQAAADEAAABwAAAAAgAAABYAAAA0AQAAAwAAAAkAAACMAQAABAAAAAMAAAD4AQAABQAAAAsAAAAQ"
2003 "AgAABwAAAAIAAABoAgAABgAAAAEAAABwAgAACAAAAAEAAACQAgAAAxAAAAMAAACYAgAAASAAAAUA"
2004 "AAC0AgAABiAAAAEAAAB8AwAAARAAAAcAAACkAwAAAiAAADEAAADqAwAAAyAAAAUAAABtBwAABCAA"
2005 "AAMAAACTBwAABSAAAAEAAADOBwAAACAAAAEAAADVBwAAABAAAAEAAAD0BwAA",
2006 // https://cs.corp.google.com/android/toolchain/jack/jack-tests/tests/com/android/jack/java7/invokecustom/test004/Tests.java
2007 "ZGV4CjAzOABvUVfbV74qWbSOEsgKP+EzahlNQLW2/8TMDAAAcAAAAHhWNBIAAAAAAAAAAOQLAABS"
2008 "AAAAcAAAAB8AAAC4AQAAEAAAADQCAAADAAAA9AIAABIAAAAMAwAAAQAAAKQDAAAACQAAzAMAANYF"
2009 "AADZBQAA4QUAAOkFAADsBQAA7wUAAPIFAAD1BQAA/AUAAP8FAAAEBgAAEwYAABYGAAAZBgAAHwYA"
2010 "AC8GAABkBgAAjQYAAMAGAADxBgAAJgcAAEUHAABhBwAAeAcAAIoHAACdBwAAsQcAAMUHAADZBwAA"
2011 "8AcAAA0IAAAyCAAAUwgAAHwIAACeCAAAvQgAANcIAADpCAAA7AgAAPgIAAD7CAAAAAkAAAYJAAAM"
2012 "CQAAEAkAABUJAAAaCQAAHgkAACMJAAAnCQAAKgkAADMJAABICQAATQkAAFwJAABqCQAAdgkAAIQJ"
2013 "AACPCQAAmgkAAKYJAACzCQAAygkAANkJAADoCQAA9AkAAAAKAAAKCgAAHgoAACQKAAAyCgAAPQoA"
2014 "AEUKAABLCgAAYgoAAGgKAABtCgAAdgoAAIIKAACOCgAAmwoAAKEKAAADAAAABAAAAAUAAAAGAAAA"
2015 "CAAAAAsAAAAPAAAAEAAAABEAAAASAAAAEwAAABQAAAAVAAAAFgAAABgAAAAZAAAAGgAAABsAAAAc"
2016 "AAAAHQAAAB4AAAAfAAAAIAAAACEAAAAiAAAAIwAAACQAAAAlAAAAJwAAADEAAAAzAAAACQAAAAQA"
2017 "AABMBQAADgAAABMAAABUBQAADQAAABUAAAB0BQAADAAAABYAAAAAAAAAJwAAABwAAAAAAAAAKAAA"
2018 "ABwAAACABQAAKQAAABwAAACIBQAAKgAAABwAAACUBQAAKwAAABwAAACgBQAALAAAABwAAABMBQAA"
2019 "LQAAABwAAACoBQAALwAAABwAAACwBQAALwAAABwAAAC4BQAALgAAABwAAADABQAAMAAAABwAAADI"
2020 "BQAALgAAABwAAADQBQAACQAJAAoAAAAKABMAPwAAABEADQBLAAAACgAEAAIAAAAKAAAANAAAAAoA"
2021 "AQBFAAAACgAPAEgAAAAKAAQAUAAAAA0ACABMAAAADwAEAAIAAAAUAA0AAgAAABYAAgBAAAAAFwAD"
2022 "AEcAAAAZAAUANgAAABkABgA2AAAAGQAHADYAAAAZAAkANgAAABkACgA2AAAAGQALADYAAAAZAAwA"
2023 "NgAAABkADgA3AAAAnQsAAJ0LAAAKAAAAAQAAAA8AAAAAAAAAJgAAACQFAADGCwAAAAAAAAQAAAAC"
2024 "AAAAAQAAAN4KAAACAAAAegsAAJILAAACAAAAkgsAAJoLAAABAAEAAQAAAKgKAAAEAAAAcBAGAAAA"
2025 "DgADAAIAAAAAAK0KAAADAAAAkAABAg8AAAAYAA8ABgAAALQKAABTAAAAcRARAAwAEhJxIA0A0gAT"
2026 "AmEAcSAKAOIAEwIABHEgDQDyABISAgAQAHEgDQACABICFAOamTFBAgARAHEwDAADAhYGAAAYApqZ"
2027 "mZmZmQFABQQSAHcGCwACABsCBwAAAAgAFABxIBAAAgAcAgoACAAVAHEgDwACABcCFc1bBwUAFgBx"
2028 "QA4AMhBxAAkAAAAMAhwDCgBuQAgAMroMAiIDFABwIAcAIwARAwAABAABAAIAAADRCgAADAAAAGIA"
2029 "AgASIRIy/CAAACEACgFuIAUAEAAOAAMAAQACAAAA2AoAAAsAAAASIBIx/CABABAACgASUXEgDQAB"
2030 "AA4AAAAAAAAAAAAAAAMAAAAAAAAAAQAAAMwDAAACAAAA1AMAAAQAAADgAwAAAgAAAAQABAANAAAA"
2031 "FgAQABgAHQAAAAEAGwAEAAMAAgAQAA4ABQAAAAMAAAAOABAAGAAAAAIAAAABAAEAAwAAAAIAAgAC"
2032 "AAAAAwAAAAMAAwADAAAAAQAAAAQAAAACAAAABQAFAAIAAAAPAA8AAgAAABAAEAABAAAAFQAAAAEA"
2033 "AAAdAAAAAQAAAB4AASgABjwqPjtKKQAGPGluaXQ+AAFCAAFDAAFEAAFGAAVIZWxsbwABSQADSUlJ"
2034 "AA1JTlZPS0VfU1RBVElDAAFKAAFMAARMTExMAA5MTExMWkJDU0lGRExMSgAzTGNvbS9hbmRyb2lk"
2035 "L2phY2svYW5ub3RhdGlvbnMvQ2FsbGVkQnlJbnZva2VDdXN0b207ACdMY29tL2FuZHJvaWQvamFj"
2036 "ay9hbm5vdGF0aW9ucy9Db25zdGFudDsAMUxjb20vYW5kcm9pZC9qYWNrL2Fubm90YXRpb25zL0xp"
2037 "bmtlck1ldGhvZEhhbmRsZTsAL0xjb20vYW5kcm9pZC9qYWNrL2Fubm90YXRpb25zL01ldGhvZEhh"
2038 "bmRsZUtpbmQ7ADNMY29tL2FuZHJvaWQvamFjay9qYXZhNy9pbnZva2VjdXN0b20vdGVzdDAwNC9U"
2039 "ZXN0czsAHUxkYWx2aWsvYW5ub3RhdGlvbi9TaWduYXR1cmU7ABpMZGFsdmlrL2Fubm90YXRpb24v"
2040 "VGhyb3dzOwAVTGphdmEvaW8vUHJpbnRTdHJlYW07ABBMamF2YS9sYW5nL0NsYXNzABFMamF2YS9s"
2041 "YW5nL0NsYXNzOwASTGphdmEvbGFuZy9PYmplY3Q7ABJMamF2YS9sYW5nL1N0cmluZzsAEkxqYXZh"
2042 "L2xhbmcvU3lzdGVtOwAVTGphdmEvbGFuZy9UaHJvd2FibGU7ABtMamF2YS9sYW5nL2ludm9rZS9D"
2043 "YWxsU2l0ZTsAI0xqYXZhL2xhbmcvaW52b2tlL0NvbnN0YW50Q2FsbFNpdGU7AB9MamF2YS9sYW5n"
2044 "L2ludm9rZS9NZXRob2RIYW5kbGU7ACdMamF2YS9sYW5nL2ludm9rZS9NZXRob2RIYW5kbGVzJExv"
2045 "b2t1cDsAIExqYXZhL2xhbmcvaW52b2tlL01ldGhvZEhhbmRsZXM7AB1MamF2YS9sYW5nL2ludm9r"
2046 "ZS9NZXRob2RUeXBlOwAYTGp1bml0L2ZyYW1ld29yay9Bc3NlcnQ7ABBMb3JnL2p1bml0L1Rlc3Q7"
2047 "AAFTAApUZXN0cy5qYXZhAAFWAANWQ0MABFZEREQABFZGRkYAAlZJAANWSUkAA1ZKSgACVkwAA1ZM"
2048 "TAACVloAAVoAB1pCQ1NJRkQAE1tMamF2YS9sYW5nL1N0cmluZzsAA2FkZAANYXJndW1lbnRUeXBl"
2049 "cwAMYXNzZXJ0RXF1YWxzAAphc3NlcnRUcnVlAAxib29sZWFuVmFsdWUACWJ5dGVWYWx1ZQAJY2hh"
2050 "clZhbHVlAApjbGFzc1ZhbHVlAAtkb3VibGVWYWx1ZQAVZW1pdHRlcjogamFjay00LjAtZW5nAA1l"
2051 "bmNsb3NpbmdUeXBlAA1maWVsZENhbGxTaXRlAApmaW5kU3RhdGljAApmbG9hdFZhbHVlAAhpbnRW"
2052 "YWx1ZQASaW52b2tlTWV0aG9kSGFuZGxlAARraW5kAAxsaW5rZXJNZXRob2QACWxvbmdWYWx1ZQAG"
2053 "bG9va3VwAARtYWluABVtZXRob2RIYW5kbGVFeHRyYUFyZ3MABG5hbWUAA291dAAHcHJpbnRsbgAK"
2054 "cmV0dXJuVHlwZQAKc2hvcnRWYWx1ZQALc3RyaW5nVmFsdWUABHRlc3QABXZhbHVlACMABw4ANwIA"
2055 "AAcOAD4NAAAAAAAAAAAAAAAAAAcOPEtaWmmWw4d4h6UAUgEABw60AE4ABw6lAAAGBTUcAhgEGARD"
2056 "HAEdCAQ1HA0YFhgQGBgYHRgAGAEYGxgEGAMYAhgQGA4YBT4YCkQbAEoXRUkcCh0HATgcAT8dBwE5"
2057 "HAEAAR0HATocAQNhHQcBThwBIgAEHQcBQhwBBAEdBwFBHAFwmpkxQR0HATwcAfGamZmZmZkBQB0H"
2058 "AU8cARcHHQcBOxwBGAodBwFGHAFmFc1bB0oXNE0YBAILAVEcCRcAFyAXGhciFzIXGhcXFwEXHQIM"
2059 "AVEcARgSARoADRYAFzQVAAQBBAEEYSQABAQBcJqZMUHxmpmZmZmZAUAXBxgKZhXNWwcBAAQBAQkA"
2060 "gYAE7AcBCoQIAQqcCAEJ1AkEAfwJAAATAAAAAAAAAAEAAAAAAAAAAQAAAFIAAABwAAAAAgAAAB8A"
2061 "AAC4AQAAAwAAABAAAAA0AgAABAAAAAMAAAD0AgAABQAAABIAAAAMAwAABwAAAAIAAACcAwAABgAA"
2062 "AAEAAACkAwAACAAAAAEAAADEAwAAAxAAAAMAAADMAwAAASAAAAUAAADsAwAABiAAAAEAAAAkBQAA"
2063 "ARAAAA0AAABMBQAAAiAAAFIAAADWBQAAAyAAAAUAAACoCgAABCAAAAQAAADeCgAABSAAAAEAAACd"
2064 "CwAAACAAAAEAAADGCwAAABAAAAEAAADkCwAA"
2065};
2066
2067TEST_F(DexFileVerifierTest, InvokeCustomDexSamples) {
2068 for (size_t i = 0; i < arraysize(kInvokeCustomDexFiles); ++i) {
2069 size_t length;
2070 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kInvokeCustomDexFiles[i], &length));
2071 CHECK(dex_bytes != nullptr);
2072 // Note: `dex_file` will be destroyed before `dex_bytes`.
2073 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
2074 std::string error_msg;
2075 EXPECT_TRUE(DexFileVerifier::Verify(dex_file.get(),
2076 dex_file->Begin(),
2077 dex_file->Size(),
2078 "good checksum, verify",
2079 /*verify_checksum*/ true,
2080 &error_msg));
2081 // TODO(oth): Test corruptions (b/35308502)
2082 }
2083}
2084
Jeff Hao326c1a22017-05-04 14:12:56 -07002085TEST_F(DexFileVerifierTest, BadStaticFieldInitialValuesArray) {
2086 // Generated DEX file version (037) from:
2087 //
2088 // .class public LBadStaticFieldInitialValuesArray;
2089 // .super Ljava/lang/Object;
2090 //
2091 // # static fields
2092 // .field static final c:C = 'c'
2093 // .field static final i:I = 0x1
2094 // .field static final s:Ljava/lang/String; = "s"
2095 //
2096 // # direct methods
2097 // .method public constructor <init>()V
2098 // .registers 1
2099 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
2100 // return-void
2101 // .end method
2102 //
2103 // Output file was hex edited so that static field "i" has string typing in initial values array.
2104 static const char kDexBase64[] =
2105 "ZGV4CjAzNQBrMi4cCPcMvvXNRw0uI6RRubwMPwgEYXIsAgAAcAAAAHhWNBIAAAAAAAAAAIwBAAAL"
2106 "AAAAcAAAAAYAAACcAAAAAQAAALQAAAADAAAAwAAAAAIAAADYAAAAAQAAAOgAAAAkAQAACAEAACAB"
2107 "AAAoAQAAMAEAADMBAAA2AQAAOwEAAE8BAABjAQAAZgEAAGkBAABsAQAAAgAAAAMAAAAEAAAABQAA"
2108 "AAYAAAAHAAAABwAAAAUAAAAAAAAAAgAAAAgAAAACAAEACQAAAAIABAAKAAAAAgAAAAAAAAADAAAA"
2109 "AAAAAAIAAAABAAAAAwAAAAAAAAABAAAAAAAAAHsBAAB0AQAAAQABAAEAAABvAQAABAAAAHAQAQAA"
2110 "AA4ABjxpbml0PgAGQS5qYXZhAAFDAAFJAANMQTsAEkxqYXZhL2xhbmcvT2JqZWN0OwASTGphdmEv"
2111 "bGFuZy9TdHJpbmc7AAFWAAFjAAFpAAFzAAEABw4AAwNjFwoXCgMAAQAAGAEYARgAgYAEiAIADQAA"
2112 "AAAAAAABAAAAAAAAAAEAAAALAAAAcAAAAAIAAAAGAAAAnAAAAAMAAAABAAAAtAAAAAQAAAADAAAA"
2113 "wAAAAAUAAAACAAAA2AAAAAYAAAABAAAA6AAAAAEgAAABAAAACAEAAAIgAAALAAAAIAEAAAMgAAAB"
2114 "AAAAbwEAAAUgAAABAAAAdAEAAAAgAAABAAAAewEAAAAQAAABAAAAjAEAAA==";
2115
2116 size_t length;
2117 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
2118 CHECK(dex_bytes != nullptr);
2119 // Note: `dex_file` will be destroyed before `dex_bytes`.
2120 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
2121 std::string error_msg;
2122 EXPECT_FALSE(DexFileVerifier::Verify(dex_file.get(),
2123 dex_file->Begin(),
2124 dex_file->Size(),
2125 "bad static field initial values array",
2126 /*verify_checksum*/ true,
2127 &error_msg));
2128}
2129
2130TEST_F(DexFileVerifierTest, GoodStaticFieldInitialValuesArray) {
2131 // Generated DEX file version (037) from:
2132 //
2133 // .class public LGoodStaticFieldInitialValuesArray;
2134 // .super Ljava/lang/Object;
2135 //
2136 // # static fields
2137 // .field static final b:B = 0x1t
2138 // .field static final c:C = 'c'
2139 // .field static final d:D = 0.6
2140 // .field static final f:F = 0.5f
2141 // .field static final i:I = 0x3
2142 // .field static final j:J = 0x4L
2143 // .field static final l1:Ljava/lang/String;
2144 // .field static final l2:Ljava/lang/String; = "s"
2145 // .field static final l3:Ljava/lang/Class; = Ljava/lang/String;
2146 // .field static final s:S = 0x2s
2147 // .field static final z:Z = true
2148 //
2149 // # direct methods
2150 // .method public constructor <init>()V
2151 // .registers 1
2152 // invoke-direct {p0}, Ljava/lang/Object;-><init>()V
2153 // return-void
2154 // .end method
2155 static const char kDexBase64[] =
2156 "ZGV4CjAzNQAwWxLbdhFa1NGiFWjsy5fhUCHxe5QHtPY8AwAAcAAAAHhWNBIAAAAAAAAAAJwCAAAZ"
2157 "AAAAcAAAAA0AAADUAAAAAQAAAAgBAAALAAAAFAEAAAIAAABsAQAAAQAAAHwBAACgAQAAnAEAAJwB"
2158 "AACkAQAApwEAAKoBAACtAQAAsAEAALMBAAC2AQAA2wEAAO4BAAACAgAAFgIAABkCAAAcAgAAHwIA"
2159 "ACICAAAlAgAAKAIAACsCAAAuAgAAMQIAADUCAAA5AgAAPQIAAEACAAABAAAAAgAAAAMAAAAEAAAA"
2160 "BQAAAAYAAAAHAAAACAAAAAkAAAAKAAAACwAAAAwAAAANAAAADAAAAAsAAAAAAAAABgAAAA4AAAAG"
2161 "AAEADwAAAAYAAgAQAAAABgADABEAAAAGAAQAEgAAAAYABQATAAAABgAJABQAAAAGAAkAFQAAAAYA"
2162 "BwAWAAAABgAKABcAAAAGAAwAGAAAAAYAAAAAAAAACAAAAAAAAAAGAAAAAQAAAAgAAAAAAAAA////"
2163 "/wAAAAB8AgAARAIAAAY8aW5pdD4AAUIAAUMAAUQAAUYAAUkAAUoAI0xHb29kU3RhdGljRmllbGRJ"
2164 "bml0aWFsVmFsdWVzQXJyYXk7ABFMamF2YS9sYW5nL0NsYXNzOwASTGphdmEvbGFuZy9PYmplY3Q7"
2165 "ABJMamF2YS9sYW5nL1N0cmluZzsAAVMAAVYAAVoAAWIAAWMAAWQAAWYAAWkAAWoAAmwxAAJsMgAC"
2166 "bDMAAXMAAXoAAAsAAQNj8TMzMzMzM+M/ED8EAwYEHhcXGAkCAj8AAAAAAQABAAEAAAAAAAAABAAA"
2167 "AHAQAQAAAA4ACwABAAAYARgBGAEYARgBGAEYARgBGAEYARgAgYAE5AQNAAAAAAAAAAEAAAAAAAAA"
2168 "AQAAABkAAABwAAAAAgAAAA0AAADUAAAAAwAAAAEAAAAIAQAABAAAAAsAAAAUAQAABQAAAAIAAABs"
2169 "AQAABgAAAAEAAAB8AQAAAiAAABkAAACcAQAABSAAAAEAAABEAgAAAxAAAAEAAABgAgAAASAAAAEA"
2170 "AABkAgAAACAAAAEAAAB8AgAAABAAAAEAAACcAgAA";
2171
2172 size_t length;
2173 std::unique_ptr<uint8_t[]> dex_bytes(DecodeBase64(kDexBase64, &length));
2174 CHECK(dex_bytes != nullptr);
2175 // Note: `dex_file` will be destroyed before `dex_bytes`.
2176 std::unique_ptr<DexFile> dex_file(GetDexFile(dex_bytes.get(), length));
2177 std::string error_msg;
2178 EXPECT_TRUE(DexFileVerifier::Verify(dex_file.get(),
2179 dex_file->Begin(),
2180 dex_file->Size(),
2181 "good static field initial values array",
2182 /*verify_checksum*/ true,
2183 &error_msg));
2184}
2185
Andreas Gampedf10b322014-06-11 21:46:05 -07002186} // namespace art