1 /*
2 * Copyright (C) 2012 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 "common_throws.h"
18
19 #include <sstream>
20
21 #include <android-base/logging.h>
22 #include <android-base/stringprintf.h>
23
24 #include "art_field-inl.h"
25 #include "art_method-inl.h"
26 #include "art_method.h"
27 #include "class_linker-inl.h"
28 #include "debug_print.h"
29 #include "dex/dex_file-inl.h"
30 #include "dex/dex_instruction-inl.h"
31 #include "dex/invoke_type.h"
32 #include "mirror/class-alloc-inl.h"
33 #include "mirror/method_type.h"
34 #include "mirror/object-inl.h"
35 #include "mirror/object_array-inl.h"
36 #include "nativehelper/scoped_local_ref.h"
37 #include "obj_ptr-inl.h"
38 #include "thread.h"
39 #include "well_known_classes-inl.h"
40
41 namespace art HIDDEN {
42
43 using android::base::StringAppendV;
44 using android::base::StringPrintf;
45
AddReferrerLocation(std::ostream & os,ObjPtr<mirror::Class> referrer)46 static void AddReferrerLocation(std::ostream& os, ObjPtr<mirror::Class> referrer)
47 REQUIRES_SHARED(Locks::mutator_lock_) {
48 if (referrer != nullptr) {
49 std::string location(referrer->GetLocation());
50 if (!location.empty()) {
51 os << " (declaration of '" << referrer->PrettyDescriptor()
52 << "' appears in " << location << ")";
53 }
54 }
55 }
56
ThrowException(const char * exception_descriptor)57 static void ThrowException(const char* exception_descriptor) REQUIRES_SHARED(Locks::mutator_lock_) {
58 Thread* self = Thread::Current();
59 self->ThrowNewException(exception_descriptor, nullptr);
60 }
61
ThrowException(const char * exception_descriptor,ObjPtr<mirror::Class> referrer,const char * fmt,va_list * args=nullptr)62 static void ThrowException(const char* exception_descriptor,
63 ObjPtr<mirror::Class> referrer,
64 const char* fmt,
65 va_list* args = nullptr)
66 REQUIRES_SHARED(Locks::mutator_lock_) {
67 std::ostringstream msg;
68 if (args != nullptr) {
69 std::string vmsg;
70 StringAppendV(&vmsg, fmt, *args);
71 msg << vmsg;
72 } else {
73 msg << fmt;
74 }
75 AddReferrerLocation(msg, referrer);
76 Thread* self = Thread::Current();
77 self->ThrowNewException(exception_descriptor, msg.str().c_str());
78 }
79
ThrowWrappedException(const char * exception_descriptor,ObjPtr<mirror::Class> referrer,const char * fmt,va_list * args=nullptr)80 static void ThrowWrappedException(const char* exception_descriptor,
81 ObjPtr<mirror::Class> referrer,
82 const char* fmt,
83 va_list* args = nullptr)
84 REQUIRES_SHARED(Locks::mutator_lock_) {
85 std::ostringstream msg;
86 if (args != nullptr) {
87 std::string vmsg;
88 StringAppendV(&vmsg, fmt, *args);
89 msg << vmsg;
90 } else {
91 msg << fmt;
92 }
93 AddReferrerLocation(msg, referrer);
94 Thread* self = Thread::Current();
95 self->ThrowNewWrappedException(exception_descriptor, msg.str().c_str());
96 }
97
98 // AbstractMethodError
99
ThrowAbstractMethodError(ArtMethod * method,ObjPtr<mirror::Object> receiver)100 void ThrowAbstractMethodError(ArtMethod* method, ObjPtr<mirror::Object> receiver) {
101 std::string klass = (receiver == nullptr)
102 ? "null"
103 : mirror::Class::PrettyClass(receiver->GetClass());
104 ThrowException("Ljava/lang/AbstractMethodError;", nullptr,
105 StringPrintf("abstract method \"%s\" on receiver %s",
106 ArtMethod::PrettyMethod(method).c_str(),
107 klass.c_str()).c_str());
108 }
109
ThrowAbstractMethodError(uint32_t method_idx,const DexFile & dex_file,ObjPtr<mirror::Object> receiver)110 void ThrowAbstractMethodError(uint32_t method_idx,
111 const DexFile& dex_file,
112 ObjPtr<mirror::Object> receiver) {
113 std::string klass = (receiver == nullptr)
114 ? "null"
115 : mirror::Class::PrettyClass(receiver->GetClass());
116 ThrowException("Ljava/lang/AbstractMethodError;", /* referrer= */ nullptr,
117 StringPrintf("abstract method \"%s\" on receiver %s",
118 dex_file.PrettyMethod(method_idx,
119 /* with_signature= */ true).c_str(),
120 klass.c_str()).c_str());
121 }
122
123 // ArithmeticException
124
ThrowArithmeticExceptionDivideByZero()125 void ThrowArithmeticExceptionDivideByZero() {
126 ThrowException("Ljava/lang/ArithmeticException;", nullptr, "divide by zero");
127 }
128
129 // ArrayIndexOutOfBoundsException
130
ThrowArrayIndexOutOfBoundsException(int index,int length)131 void ThrowArrayIndexOutOfBoundsException(int index, int length) {
132 ThrowException("Ljava/lang/ArrayIndexOutOfBoundsException;", nullptr,
133 StringPrintf("length=%d; index=%d", length, index).c_str());
134 }
135
136 // ArrayStoreException
137
ThrowArrayStoreException(ObjPtr<mirror::Class> element_class,ObjPtr<mirror::Class> array_class)138 void ThrowArrayStoreException(ObjPtr<mirror::Class> element_class,
139 ObjPtr<mirror::Class> array_class) {
140 ThrowException("Ljava/lang/ArrayStoreException;", nullptr,
141 StringPrintf("%s cannot be stored in an array of type %s",
142 mirror::Class::PrettyDescriptor(element_class).c_str(),
143 mirror::Class::PrettyDescriptor(array_class).c_str()).c_str());
144 }
145
146 // BootstrapMethodError
147
ThrowBootstrapMethodError(const char * fmt,...)148 void ThrowBootstrapMethodError(const char* fmt, ...) {
149 va_list args;
150 va_start(args, fmt);
151 ThrowException("Ljava/lang/BootstrapMethodError;", nullptr, fmt, &args);
152 va_end(args);
153 }
154
ThrowWrappedBootstrapMethodError(const char * fmt,...)155 void ThrowWrappedBootstrapMethodError(const char* fmt, ...) {
156 va_list args;
157 va_start(args, fmt);
158 ThrowWrappedException("Ljava/lang/BootstrapMethodError;", nullptr, fmt, &args);
159 va_end(args);
160 }
161
162 // ClassCastException
163
ThrowClassCastException(ObjPtr<mirror::Class> dest_type,ObjPtr<mirror::Class> src_type)164 void ThrowClassCastException(ObjPtr<mirror::Class> dest_type, ObjPtr<mirror::Class> src_type) {
165 ThrowException("Ljava/lang/ClassCastException;", nullptr,
166 StringPrintf("%s cannot be cast to %s",
167 mirror::Class::PrettyDescriptor(src_type).c_str(),
168 mirror::Class::PrettyDescriptor(dest_type).c_str()).c_str());
169 }
170
ThrowClassCastException(const char * msg)171 void ThrowClassCastException(const char* msg) {
172 ThrowException("Ljava/lang/ClassCastException;", nullptr, msg);
173 }
174
175 // ClassCircularityError
176
ThrowClassCircularityError(ObjPtr<mirror::Class> c)177 void ThrowClassCircularityError(ObjPtr<mirror::Class> c) {
178 std::ostringstream msg;
179 msg << mirror::Class::PrettyDescriptor(c);
180 ThrowException("Ljava/lang/ClassCircularityError;", c, msg.str().c_str());
181 }
182
ThrowClassCircularityError(ObjPtr<mirror::Class> c,const char * fmt,...)183 void ThrowClassCircularityError(ObjPtr<mirror::Class> c, const char* fmt, ...) {
184 va_list args;
185 va_start(args, fmt);
186 ThrowException("Ljava/lang/ClassCircularityError;", c, fmt, &args);
187 va_end(args);
188 }
189
190 // ClassFormatError
191
ThrowClassFormatError(ObjPtr<mirror::Class> referrer,const char * fmt,...)192 void ThrowClassFormatError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
193 va_list args;
194 va_start(args, fmt);
195 ThrowException("Ljava/lang/ClassFormatError;", referrer, fmt, &args);
196 va_end(args);
197 }
198
199 // IllegalAccessError
200
ThrowIllegalAccessErrorClass(ObjPtr<mirror::Class> referrer,ObjPtr<mirror::Class> accessed)201 void ThrowIllegalAccessErrorClass(ObjPtr<mirror::Class> referrer, ObjPtr<mirror::Class> accessed) {
202 std::ostringstream msg;
203 msg << "Illegal class access: '" << mirror::Class::PrettyDescriptor(referrer)
204 << "' attempting to access '" << mirror::Class::PrettyDescriptor(accessed) << "'";
205 ThrowException("Ljava/lang/IllegalAccessError;", referrer, msg.str().c_str());
206 }
207
ThrowIllegalAccessErrorClassForMethodDispatch(ObjPtr<mirror::Class> referrer,ObjPtr<mirror::Class> accessed,ArtMethod * called,InvokeType type)208 void ThrowIllegalAccessErrorClassForMethodDispatch(ObjPtr<mirror::Class> referrer,
209 ObjPtr<mirror::Class> accessed,
210 ArtMethod* called,
211 InvokeType type) {
212 std::ostringstream msg;
213 msg << "Illegal class access ('" << mirror::Class::PrettyDescriptor(referrer)
214 << "' attempting to access '"
215 << mirror::Class::PrettyDescriptor(accessed) << "') in attempt to invoke " << type
216 << " method " << ArtMethod::PrettyMethod(called).c_str();
217 ThrowException("Ljava/lang/IllegalAccessError;", referrer, msg.str().c_str());
218 }
219
ThrowIllegalAccessErrorMethod(ObjPtr<mirror::Class> referrer,ArtMethod * accessed)220 void ThrowIllegalAccessErrorMethod(ObjPtr<mirror::Class> referrer, ArtMethod* accessed) {
221 std::ostringstream msg;
222 msg << "Method '" << ArtMethod::PrettyMethod(accessed) << "' is inaccessible to class '"
223 << mirror::Class::PrettyDescriptor(referrer) << "'";
224 ThrowException("Ljava/lang/IllegalAccessError;", referrer, msg.str().c_str());
225 }
226
ThrowIllegalAccessErrorField(ObjPtr<mirror::Class> referrer,ArtField * accessed)227 void ThrowIllegalAccessErrorField(ObjPtr<mirror::Class> referrer, ArtField* accessed) {
228 std::ostringstream msg;
229 msg << "Field '" << ArtField::PrettyField(accessed, false) << "' is inaccessible to class '"
230 << mirror::Class::PrettyDescriptor(referrer) << "'";
231 ThrowException("Ljava/lang/IllegalAccessError;", referrer, msg.str().c_str());
232 }
233
ThrowIllegalAccessErrorFinalField(ArtMethod * referrer,ArtField * accessed)234 void ThrowIllegalAccessErrorFinalField(ArtMethod* referrer, ArtField* accessed) {
235 std::ostringstream msg;
236 msg << "Final field '" << ArtField::PrettyField(accessed, false)
237 << "' cannot be written to by method '" << ArtMethod::PrettyMethod(referrer) << "'";
238 ThrowException("Ljava/lang/IllegalAccessError;",
239 referrer != nullptr ? referrer->GetDeclaringClass() : nullptr,
240 msg.str().c_str());
241 }
242
ThrowIllegalAccessError(ObjPtr<mirror::Class> referrer,const char * fmt,...)243 void ThrowIllegalAccessError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
244 va_list args;
245 va_start(args, fmt);
246 ThrowException("Ljava/lang/IllegalAccessError;", referrer, fmt, &args);
247 va_end(args);
248 }
249
ThrowIllegalAccessErrorForImplementingMethod(ObjPtr<mirror::Class> klass,ArtMethod * implementation_method,ArtMethod * interface_method)250 void ThrowIllegalAccessErrorForImplementingMethod(ObjPtr<mirror::Class> klass,
251 ArtMethod* implementation_method,
252 ArtMethod* interface_method)
253 REQUIRES_SHARED(Locks::mutator_lock_) {
254 // Note: For a non-public abstract implementing method, both `AbstractMethodError` and
255 // `IllegalAccessError` are reasonable. We now follow the RI behaviour and throw the latter,
256 // so we do not assert here that the implementation method is concrete as we did in the past.
257 DCHECK(!implementation_method->IsPublic());
258 ThrowIllegalAccessError(
259 klass,
260 "Method '%s' implementing interface method '%s' is not public",
261 implementation_method->PrettyMethod().c_str(),
262 interface_method->PrettyMethod().c_str());
263 }
264
265 // IllegalAccessException
266
ThrowIllegalAccessException(const char * msg)267 void ThrowIllegalAccessException(const char* msg) {
268 ThrowException("Ljava/lang/IllegalAccessException;", nullptr, msg);
269 }
270
271 // IllegalArgumentException
272
ThrowIllegalArgumentException(const char * msg)273 void ThrowIllegalArgumentException(const char* msg) {
274 ThrowException("Ljava/lang/IllegalArgumentException;", nullptr, msg);
275 }
276
277 // IllegalStateException
278
ThrowIllegalStateException(const char * msg)279 void ThrowIllegalStateException(const char* msg) {
280 ThrowException("Ljava/lang/IllegalStateException;", nullptr, msg);
281 }
282
283 // IncompatibleClassChangeError
284
ThrowIncompatibleClassChangeError(InvokeType expected_type,InvokeType found_type,ArtMethod * method,ArtMethod * referrer)285 void ThrowIncompatibleClassChangeError(InvokeType expected_type,
286 InvokeType found_type,
287 ArtMethod* method,
288 ArtMethod* referrer) {
289 std::ostringstream msg;
290 msg << "The method '" << ArtMethod::PrettyMethod(method) << "' was expected to be of type "
291 << expected_type << " but instead was found to be of type " << found_type;
292 ThrowException("Ljava/lang/IncompatibleClassChangeError;",
293 referrer != nullptr ? referrer->GetDeclaringClass() : nullptr,
294 msg.str().c_str());
295 }
296
ThrowIncompatibleClassChangeErrorClassForInterfaceDispatch(ArtMethod * interface_method,ObjPtr<mirror::Object> this_object,ArtMethod * referrer)297 void ThrowIncompatibleClassChangeErrorClassForInterfaceDispatch(ArtMethod* interface_method,
298 ObjPtr<mirror::Object> this_object,
299 ArtMethod* referrer) {
300 // Referrer is calling interface_method on this_object, however, the interface_method isn't
301 // implemented by this_object.
302 CHECK(this_object != nullptr);
303 std::ostringstream msg;
304 msg << "Class '" << mirror::Class::PrettyDescriptor(this_object->GetClass())
305 << "' does not implement interface '"
306 << mirror::Class::PrettyDescriptor(interface_method->GetDeclaringClass())
307 << "' in call to '" << ArtMethod::PrettyMethod(interface_method) << "'";
308 ThrowException("Ljava/lang/IncompatibleClassChangeError;",
309 referrer != nullptr ? referrer->GetDeclaringClass() : nullptr,
310 msg.str().c_str());
311 }
312
ThrowIncompatibleClassChangeErrorField(ArtField * resolved_field,bool is_static,ArtMethod * referrer)313 void ThrowIncompatibleClassChangeErrorField(ArtField* resolved_field,
314 bool is_static,
315 ArtMethod* referrer) {
316 std::ostringstream msg;
317 msg << "Expected '" << ArtField::PrettyField(resolved_field) << "' to be a "
318 << (is_static ? "static" : "instance") << " field" << " rather than a "
319 << (is_static ? "instance" : "static") << " field";
320 ThrowException("Ljava/lang/IncompatibleClassChangeError;", referrer->GetDeclaringClass(),
321 msg.str().c_str());
322 }
323
ThrowIncompatibleClassChangeError(ObjPtr<mirror::Class> referrer,const char * fmt,...)324 void ThrowIncompatibleClassChangeError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
325 va_list args;
326 va_start(args, fmt);
327 ThrowException("Ljava/lang/IncompatibleClassChangeError;", referrer, fmt, &args);
328 va_end(args);
329 }
330
ThrowIncompatibleClassChangeErrorForMethodConflict(ArtMethod * method)331 void ThrowIncompatibleClassChangeErrorForMethodConflict(ArtMethod* method) {
332 DCHECK(method != nullptr);
333 ThrowException("Ljava/lang/IncompatibleClassChangeError;",
334 /*referrer=*/nullptr,
335 StringPrintf("Conflicting default method implementations %s",
336 ArtMethod::PrettyMethod(method).c_str()).c_str());
337 }
338
339 // IndexOutOfBoundsException
340
ThrowIndexOutOfBoundsException(int index,int length)341 void ThrowIndexOutOfBoundsException(int index, int length) {
342 ThrowException("Ljava/lang/IndexOutOfBoundsException;", nullptr,
343 StringPrintf("length=%d; index=%d", length, index).c_str());
344 }
345
346 // InternalError
347
ThrowInternalError(const char * fmt,...)348 void ThrowInternalError(const char* fmt, ...) {
349 va_list args;
350 va_start(args, fmt);
351 ThrowException("Ljava/lang/InternalError;", nullptr, fmt, &args);
352 va_end(args);
353 }
354
355 // IOException
356
ThrowIOException(const char * fmt,...)357 void ThrowIOException(const char* fmt, ...) {
358 va_list args;
359 va_start(args, fmt);
360 ThrowException("Ljava/io/IOException;", nullptr, fmt, &args);
361 va_end(args);
362 }
363
ThrowWrappedIOException(const char * fmt,...)364 void ThrowWrappedIOException(const char* fmt, ...) {
365 va_list args;
366 va_start(args, fmt);
367 ThrowWrappedException("Ljava/io/IOException;", nullptr, fmt, &args);
368 va_end(args);
369 }
370
371 // LinkageError
372
ThrowLinkageError(ObjPtr<mirror::Class> referrer,const char * fmt,...)373 void ThrowLinkageError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
374 va_list args;
375 va_start(args, fmt);
376 ThrowException("Ljava/lang/LinkageError;", referrer, fmt, &args);
377 va_end(args);
378 }
379
ThrowWrappedLinkageError(ObjPtr<mirror::Class> referrer,const char * fmt,...)380 void ThrowWrappedLinkageError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
381 va_list args;
382 va_start(args, fmt);
383 ThrowWrappedException("Ljava/lang/LinkageError;", referrer, fmt, &args);
384 va_end(args);
385 }
386
387 // NegativeArraySizeException
388
ThrowNegativeArraySizeException(int size)389 void ThrowNegativeArraySizeException(int size) {
390 ThrowException("Ljava/lang/NegativeArraySizeException;", nullptr,
391 StringPrintf("%d", size).c_str());
392 }
393
ThrowNegativeArraySizeException(const char * msg)394 void ThrowNegativeArraySizeException(const char* msg) {
395 ThrowException("Ljava/lang/NegativeArraySizeException;", nullptr, msg);
396 }
397
398 // NoSuchFieldError
399
ThrowNoSuchFieldError(std::string_view scope,ObjPtr<mirror::Class> c,std::string_view type,std::string_view name)400 void ThrowNoSuchFieldError(std::string_view scope,
401 ObjPtr<mirror::Class> c,
402 std::string_view type,
403 std::string_view name) {
404 std::ostringstream msg;
405 std::string temp;
406 msg << "No " << scope << "field " << name << " of type " << type
407 << " in class " << c->GetDescriptor(&temp) << " or its superclasses";
408 ThrowException("Ljava/lang/NoSuchFieldError;", c, msg.str().c_str());
409 }
410
ThrowNoSuchFieldException(ObjPtr<mirror::Class> c,std::string_view name)411 void ThrowNoSuchFieldException(ObjPtr<mirror::Class> c, std::string_view name) {
412 std::ostringstream msg;
413 std::string temp;
414 msg << "No field " << name << " in class " << c->GetDescriptor(&temp);
415 ThrowException("Ljava/lang/NoSuchFieldException;", c, msg.str().c_str());
416 }
417
418 // NoSuchMethodError
419
ThrowNoSuchMethodError(InvokeType type,ObjPtr<mirror::Class> c,std::string_view name,const Signature & signature)420 void ThrowNoSuchMethodError(InvokeType type,
421 ObjPtr<mirror::Class> c,
422 std::string_view name,
423 const Signature& signature) {
424 std::ostringstream msg;
425 std::string temp;
426 msg << "No " << type << " method " << name << signature
427 << " in class " << c->GetDescriptor(&temp) << " or its super classes";
428 ThrowException("Ljava/lang/NoSuchMethodError;", c, msg.str().c_str());
429 }
430
ThrowNoSuchMethodError(ObjPtr<mirror::Class> c,std::string_view name,const Signature & signature)431 void ThrowNoSuchMethodError(ObjPtr<mirror::Class> c,
432 std::string_view name,
433 const Signature& signature) {
434 std::ostringstream msg;
435 std::string temp;
436 msg << "No method " << name << signature
437 << " in class " << c->GetDescriptor(&temp) << " or its super classes";
438 ThrowException("Ljava/lang/NoSuchMethodError;", c, msg.str().c_str());
439 }
440
441 // NullPointerException
442
ThrowNullPointerExceptionForFieldAccess(ArtField * field,ArtMethod * method,bool is_read)443 void ThrowNullPointerExceptionForFieldAccess(ArtField* field, ArtMethod* method, bool is_read) {
444 std::ostringstream msg;
445 msg << "Attempt to " << (is_read ? "read from" : "write to") << " field '"
446 << ArtField::PrettyField(field) << "' on a null object reference in method '"
447 << ArtMethod::PrettyMethod(method) << "'";
448 ThrowException("Ljava/lang/NullPointerException;", nullptr, msg.str().c_str());
449 }
450
ThrowNullPointerExceptionForMethodAccessImpl(uint32_t method_idx,const DexFile & dex_file,InvokeType type)451 static void ThrowNullPointerExceptionForMethodAccessImpl(uint32_t method_idx,
452 const DexFile& dex_file,
453 InvokeType type)
454 REQUIRES_SHARED(Locks::mutator_lock_) {
455 std::ostringstream msg;
456 msg << "Attempt to invoke " << type << " method '"
457 << dex_file.PrettyMethod(method_idx, true) << "' on a null object reference";
458 ThrowException("Ljava/lang/NullPointerException;", nullptr, msg.str().c_str());
459 }
460
ThrowNullPointerExceptionForMethodAccess(uint32_t method_idx,InvokeType type)461 void ThrowNullPointerExceptionForMethodAccess(uint32_t method_idx, InvokeType type) {
462 const DexFile& dex_file = *Thread::Current()->GetCurrentMethod(nullptr)->GetDexFile();
463 ThrowNullPointerExceptionForMethodAccessImpl(method_idx, dex_file, type);
464 }
465
ThrowNullPointerExceptionForMethodAccess(ArtMethod * method,InvokeType type)466 void ThrowNullPointerExceptionForMethodAccess(ArtMethod* method, InvokeType type) {
467 ThrowNullPointerExceptionForMethodAccessImpl(method->GetDexMethodIndex(),
468 *method->GetDexFile(),
469 type);
470 }
471
IsValidReadBarrierImplicitCheck(uintptr_t addr)472 static bool IsValidReadBarrierImplicitCheck(uintptr_t addr) {
473 DCHECK(gUseReadBarrier);
474 uint32_t monitor_offset = mirror::Object::MonitorOffset().Uint32Value();
475 if (kUseBakerReadBarrier &&
476 (kRuntimeISA == InstructionSet::kX86 || kRuntimeISA == InstructionSet::kX86_64)) {
477 constexpr uint32_t gray_byte_position = LockWord::kReadBarrierStateShift / kBitsPerByte;
478 monitor_offset += gray_byte_position;
479 }
480 return addr == monitor_offset;
481 }
482
IsValidImplicitCheck(uintptr_t addr,const Instruction & instr)483 static bool IsValidImplicitCheck(uintptr_t addr, const Instruction& instr)
484 REQUIRES_SHARED(Locks::mutator_lock_) {
485 if (!CanDoImplicitNullCheckOn(addr)) {
486 return false;
487 }
488
489 switch (instr.Opcode()) {
490 case Instruction::INVOKE_DIRECT:
491 case Instruction::INVOKE_DIRECT_RANGE:
492 case Instruction::INVOKE_VIRTUAL:
493 case Instruction::INVOKE_VIRTUAL_RANGE:
494 case Instruction::INVOKE_INTERFACE:
495 case Instruction::INVOKE_INTERFACE_RANGE:
496 case Instruction::INVOKE_POLYMORPHIC:
497 case Instruction::INVOKE_POLYMORPHIC_RANGE:
498 case Instruction::INVOKE_SUPER:
499 case Instruction::INVOKE_SUPER_RANGE: {
500 // Without inlining, we could just check that the offset is the class offset.
501 // However, when inlining, the compiler can (validly) merge the null check with a field access
502 // on the same object. Note that the stack map at the NPE will reflect the invoke's location,
503 // which is the caller.
504 return true;
505 }
506
507 case Instruction::IGET_OBJECT:
508 if (gUseReadBarrier && IsValidReadBarrierImplicitCheck(addr)) {
509 return true;
510 }
511 FALLTHROUGH_INTENDED;
512 case Instruction::IGET:
513 case Instruction::IGET_WIDE:
514 case Instruction::IGET_BOOLEAN:
515 case Instruction::IGET_BYTE:
516 case Instruction::IGET_CHAR:
517 case Instruction::IGET_SHORT:
518 case Instruction::IPUT:
519 case Instruction::IPUT_WIDE:
520 case Instruction::IPUT_OBJECT:
521 case Instruction::IPUT_BOOLEAN:
522 case Instruction::IPUT_BYTE:
523 case Instruction::IPUT_CHAR:
524 case Instruction::IPUT_SHORT: {
525 // We might be doing an implicit null check with an offset that doesn't correspond
526 // to the instruction, for example with two field accesses and the first one being
527 // eliminated or re-ordered.
528 return true;
529 }
530
531 case Instruction::AGET_OBJECT:
532 if (gUseReadBarrier && IsValidReadBarrierImplicitCheck(addr)) {
533 return true;
534 }
535 FALLTHROUGH_INTENDED;
536 case Instruction::AGET:
537 case Instruction::AGET_WIDE:
538 case Instruction::AGET_BOOLEAN:
539 case Instruction::AGET_BYTE:
540 case Instruction::AGET_CHAR:
541 case Instruction::AGET_SHORT:
542 case Instruction::APUT:
543 case Instruction::APUT_WIDE:
544 case Instruction::APUT_OBJECT:
545 case Instruction::APUT_BOOLEAN:
546 case Instruction::APUT_BYTE:
547 case Instruction::APUT_CHAR:
548 case Instruction::APUT_SHORT:
549 case Instruction::FILL_ARRAY_DATA:
550 case Instruction::ARRAY_LENGTH: {
551 // The length access should crash. We currently do not do implicit checks on
552 // the array access itself.
553 return (addr == 0u) || (addr == mirror::Array::LengthOffset().Uint32Value());
554 }
555
556 default: {
557 // We have covered all the cases where an NPE could occur.
558 // Note that this must be kept in sync with the compiler, and adding
559 // any new way to do implicit checks in the compiler should also update
560 // this code.
561 return false;
562 }
563 }
564 }
565
ThrowNullPointerExceptionFromDexPC(bool check_address,uintptr_t addr)566 void ThrowNullPointerExceptionFromDexPC(bool check_address, uintptr_t addr) {
567 uint32_t throw_dex_pc;
568 ArtMethod* method = Thread::Current()->GetCurrentMethod(&throw_dex_pc);
569 CodeItemInstructionAccessor accessor(method->DexInstructions());
570 CHECK_LT(throw_dex_pc, accessor.InsnsSizeInCodeUnits());
571 const Instruction& instr = accessor.InstructionAt(throw_dex_pc);
572 if (check_address && !IsValidImplicitCheck(addr, instr)) {
573 const DexFile* dex_file = method->GetDexFile();
574 LOG(FATAL) << "Invalid address for an implicit NullPointerException check: "
575 << "0x" << std::hex << addr << std::dec
576 << ", at "
577 << instr.DumpString(dex_file)
578 << " in "
579 << method->PrettyMethod();
580 }
581
582 switch (instr.Opcode()) {
583 case Instruction::INVOKE_DIRECT:
584 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_35c(), kDirect);
585 break;
586 case Instruction::INVOKE_DIRECT_RANGE:
587 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_3rc(), kDirect);
588 break;
589 case Instruction::INVOKE_VIRTUAL:
590 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_35c(), kVirtual);
591 break;
592 case Instruction::INVOKE_VIRTUAL_RANGE:
593 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_3rc(), kVirtual);
594 break;
595 case Instruction::INVOKE_SUPER:
596 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_35c(), kSuper);
597 break;
598 case Instruction::INVOKE_SUPER_RANGE:
599 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_3rc(), kSuper);
600 break;
601 case Instruction::INVOKE_INTERFACE:
602 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_35c(), kInterface);
603 break;
604 case Instruction::INVOKE_INTERFACE_RANGE:
605 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_3rc(), kInterface);
606 break;
607 case Instruction::INVOKE_POLYMORPHIC:
608 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_45cc(), kVirtual);
609 break;
610 case Instruction::INVOKE_POLYMORPHIC_RANGE:
611 ThrowNullPointerExceptionForMethodAccess(instr.VRegB_4rcc(), kVirtual);
612 break;
613 case Instruction::IGET:
614 case Instruction::IGET_WIDE:
615 case Instruction::IGET_OBJECT:
616 case Instruction::IGET_BOOLEAN:
617 case Instruction::IGET_BYTE:
618 case Instruction::IGET_CHAR:
619 case Instruction::IGET_SHORT: {
620 ArtField* field =
621 Runtime::Current()->GetClassLinker()->ResolveField(instr.VRegC_22c(), method, false);
622 Thread::Current()->ClearException(); // Resolution may fail, ignore.
623 ThrowNullPointerExceptionForFieldAccess(field, method, /* is_read= */ true);
624 break;
625 }
626 case Instruction::IPUT:
627 case Instruction::IPUT_WIDE:
628 case Instruction::IPUT_OBJECT:
629 case Instruction::IPUT_BOOLEAN:
630 case Instruction::IPUT_BYTE:
631 case Instruction::IPUT_CHAR:
632 case Instruction::IPUT_SHORT: {
633 ArtField* field = Runtime::Current()->GetClassLinker()->ResolveField(
634 instr.VRegC_22c(), method, /* is_static= */ false);
635 Thread::Current()->ClearException(); // Resolution may fail, ignore.
636 ThrowNullPointerExceptionForFieldAccess(field, method, /* is_read= */ false);
637 break;
638 }
639 case Instruction::AGET:
640 case Instruction::AGET_WIDE:
641 case Instruction::AGET_OBJECT:
642 case Instruction::AGET_BOOLEAN:
643 case Instruction::AGET_BYTE:
644 case Instruction::AGET_CHAR:
645 case Instruction::AGET_SHORT:
646 ThrowException("Ljava/lang/NullPointerException;", nullptr,
647 "Attempt to read from null array");
648 break;
649 case Instruction::APUT:
650 case Instruction::APUT_WIDE:
651 case Instruction::APUT_OBJECT:
652 case Instruction::APUT_BOOLEAN:
653 case Instruction::APUT_BYTE:
654 case Instruction::APUT_CHAR:
655 case Instruction::APUT_SHORT:
656 ThrowException("Ljava/lang/NullPointerException;", nullptr,
657 "Attempt to write to null array");
658 break;
659 case Instruction::ARRAY_LENGTH:
660 ThrowException("Ljava/lang/NullPointerException;", nullptr,
661 "Attempt to get length of null array");
662 break;
663 case Instruction::FILL_ARRAY_DATA: {
664 ThrowException("Ljava/lang/NullPointerException;", nullptr,
665 "Attempt to write to null array");
666 break;
667 }
668 case Instruction::MONITOR_ENTER:
669 case Instruction::MONITOR_EXIT: {
670 ThrowException("Ljava/lang/NullPointerException;", nullptr,
671 "Attempt to do a synchronize operation on a null object");
672 break;
673 }
674 default: {
675 const DexFile* dex_file = method->GetDexFile();
676 LOG(FATAL) << "NullPointerException at an unexpected instruction: "
677 << instr.DumpString(dex_file)
678 << " in "
679 << method->PrettyMethod();
680 UNREACHABLE();
681 }
682 }
683 }
684
ThrowNullPointerException(const char * msg)685 void ThrowNullPointerException(const char* msg) {
686 ThrowException("Ljava/lang/NullPointerException;", nullptr, msg);
687 }
688
ThrowNullPointerException()689 void ThrowNullPointerException() {
690 ThrowException("Ljava/lang/NullPointerException;");
691 }
692
693 // ReadOnlyBufferException
694
ThrowReadOnlyBufferException()695 void ThrowReadOnlyBufferException() {
696 Thread::Current()->ThrowNewException("Ljava/nio/ReadOnlyBufferException;", nullptr);
697 }
698
699 // RuntimeException
700
ThrowRuntimeException(const char * fmt,...)701 void ThrowRuntimeException(const char* fmt, ...) {
702 va_list args;
703 va_start(args, fmt);
704 ThrowException("Ljava/lang/RuntimeException;", nullptr, fmt, &args);
705 va_end(args);
706 }
707
708 // SecurityException
709
ThrowSecurityException(const char * fmt,...)710 void ThrowSecurityException(const char* fmt, ...) {
711 va_list args;
712 va_start(args, fmt);
713 ThrowException("Ljava/lang/SecurityException;", nullptr, fmt, &args);
714 va_end(args);
715 }
716
717 // Stack overflow.
718
719 template <StackType stack_type>
ThrowStackOverflowError(Thread * self)720 void ThrowStackOverflowError(Thread* self) {
721 if (self->IsHandlingStackOverflow<stack_type>()) {
722 LOG(ERROR) << "Recursive stack overflow.";
723 // We don't fail here because SetStackEndForStackOverflow will print better diagnostics.
724 }
725
726 // Allow space on the stack for constructor to execute.
727 self->SetStackEndForStackOverflow<stack_type>();
728
729 // Remove the stack overflow protection if it is set up.
730 bool implicit_stack_check = Runtime::Current()->GetImplicitStackOverflowChecks();
731 if (implicit_stack_check) {
732 if (!self->UnprotectStack<stack_type>()) {
733 LOG(ERROR) << "Unable to remove stack protection for stack overflow";
734 }
735 }
736
737 // Avoid running Java code for exception initialization.
738 // TODO: Checks to make this a bit less brittle.
739 //
740 // Note: This lambda is used to make sure the `StackOverflowError` intitialization code
741 // does not increase the frame size of `ThrowStackOverflowError()` itself. It runs
742 // with its own frame in the extended stack, which is especially important for modes
743 // with larger stack sizes (e.g., ASAN).
744 auto create_and_throw = [self]() REQUIRES_SHARED(Locks::mutator_lock_) NO_INLINE {
745 std::string msg("stack size ");
746 msg += PrettySize(self->GetUsableStackSize<stack_type>());
747
748 ScopedObjectAccessUnchecked soa(self);
749 StackHandleScope<1u> hs(self);
750
751 // Allocate an uninitialized object.
752 DCHECK(WellKnownClasses::java_lang_StackOverflowError->IsInitialized());
753 Handle<mirror::Object> exc = hs.NewHandle(
754 WellKnownClasses::java_lang_StackOverflowError->AllocObject(self));
755 if (exc == nullptr) {
756 LOG(WARNING) << "Could not allocate StackOverflowError object.";
757 return;
758 }
759
760 // "Initialize".
761 // StackOverflowError -> VirtualMachineError -> Error -> Throwable -> Object.
762 // Only Throwable has "custom" fields:
763 // String detailMessage.
764 // Throwable cause (= this).
765 // List<Throwable> suppressedExceptions (= Collections.emptyList()).
766 // Object stackState;
767 // StackTraceElement[] stackTrace;
768 // Only Throwable has a non-empty constructor:
769 // this.stackTrace = EmptyArray.STACK_TRACE_ELEMENT;
770 // fillInStackTrace();
771
772 // detailMessage.
773 {
774 ObjPtr<mirror::String> s = mirror::String::AllocFromModifiedUtf8(self, msg.c_str());
775 if (s == nullptr) {
776 LOG(WARNING) << "Could not throw new StackOverflowError because message allocation failed.";
777 return;
778 }
779 WellKnownClasses::java_lang_Throwable_detailMessage
780 ->SetObject</*kTransactionActive=*/ false>(exc.Get(), s);
781 }
782
783 // cause.
784 WellKnownClasses::java_lang_Throwable_cause
785 ->SetObject</*kTransactionActive=*/ false>(exc.Get(), exc.Get());
786
787 // suppressedExceptions.
788 {
789 ObjPtr<mirror::Class> j_u_c = WellKnownClasses::java_util_Collections.Get();
790 DCHECK(j_u_c->IsInitialized());
791 ObjPtr<mirror::Object> empty_list =
792 WellKnownClasses::java_util_Collections_EMPTY_LIST->GetObject(j_u_c);
793 CHECK(empty_list != nullptr);
794 WellKnownClasses::java_lang_Throwable_suppressedExceptions
795 ->SetObject</*kTransactionActive=*/ false>(exc.Get(), empty_list);
796 }
797
798 // stackState is set as result of fillInStackTrace. fillInStackTrace calls
799 // nativeFillInStackTrace.
800 ObjPtr<mirror::Object> stack_state_val = self->CreateInternalStackTrace(soa);
801 if (stack_state_val != nullptr) {
802 WellKnownClasses::java_lang_Throwable_stackState
803 ->SetObject</*kTransactionActive=*/ false>(exc.Get(), stack_state_val);
804
805 // stackTrace.
806 ObjPtr<mirror::Class> l_u_ea = WellKnownClasses::libcore_util_EmptyArray.Get();
807 DCHECK(l_u_ea->IsInitialized());
808 ObjPtr<mirror::Object> empty_ste =
809 WellKnownClasses::libcore_util_EmptyArray_STACK_TRACE_ELEMENT->GetObject(l_u_ea);
810 CHECK(empty_ste != nullptr);
811 WellKnownClasses::java_lang_Throwable_stackTrace
812 ->SetObject</*kTransactionActive=*/ false>(exc.Get(), empty_ste);
813 } else {
814 LOG(WARNING) << "Could not create stack trace.";
815 // Note: we'll create an exception without stack state, which is valid.
816 }
817
818 // Throw the exception.
819 self->SetException(exc->AsThrowable());
820 };
821 create_and_throw();
822 CHECK(self->IsExceptionPending());
823
824 self->ResetDefaultStackEnd<stack_type>(); // Return to default stack size.
825
826 // And restore protection if implicit checks are on.
827 if (implicit_stack_check) {
828 self->ProtectStack<stack_type>();
829 }
830 }
831
832 // Explicit instantiations to keep this definition separate to the declaration.
833 template void ThrowStackOverflowError<StackType::kHardware>(Thread* self);
834
835 // StringIndexOutOfBoundsException
836
ThrowStringIndexOutOfBoundsException(int index,int length)837 void ThrowStringIndexOutOfBoundsException(int index, int length) {
838 ThrowException("Ljava/lang/StringIndexOutOfBoundsException;", nullptr,
839 StringPrintf("length=%d; index=%d", length, index).c_str());
840 }
841
842 // UnsupportedOperationException
843
ThrowUnsupportedOperationException()844 void ThrowUnsupportedOperationException() {
845 ThrowException("Ljava/lang/UnsupportedOperationException;");
846 }
847
848 // VerifyError
849
ThrowVerifyError(ObjPtr<mirror::Class> referrer,const char * fmt,...)850 void ThrowVerifyError(ObjPtr<mirror::Class> referrer, const char* fmt, ...) {
851 va_list args;
852 va_start(args, fmt);
853 ThrowException("Ljava/lang/VerifyError;", referrer, fmt, &args);
854 va_end(args);
855 }
856
857 // WrongMethodTypeException
858
ThrowWrongMethodTypeException(ObjPtr<mirror::MethodType> expected_type,ObjPtr<mirror::MethodType> actual_type)859 void ThrowWrongMethodTypeException(ObjPtr<mirror::MethodType> expected_type,
860 ObjPtr<mirror::MethodType> actual_type) {
861 ThrowWrongMethodTypeException(expected_type->PrettyDescriptor(), actual_type->PrettyDescriptor());
862 }
863
ThrowWrongMethodTypeException(const std::string & expected_descriptor,const std::string & actual_descriptor)864 void ThrowWrongMethodTypeException(const std::string& expected_descriptor,
865 const std::string& actual_descriptor) {
866 std::ostringstream msg;
867 msg << "Expected " << expected_descriptor << " but was " << actual_descriptor;
868 ThrowException("Ljava/lang/invoke/WrongMethodTypeException;", nullptr, msg.str().c_str());
869 }
870
871 } // namespace art
872