aboutsummaryrefslogtreecommitdiff
path: root/vm/Jni.cpp
Commit message (Collapse)AuthorAgeFilesLines
* dalvik: Fix leak in error condition in FindClassIvan Evlogiev2014-01-281-0/+1
| | | | | | Release trackedLoader for all exit points in FindClass Change-Id: I2da26ed6253c2b1b9381bff394596245b993602c
* Support apps that pass JNI_VERSION_1_1 to GetEnv.Elliott Hughes2013-09-061-1/+3
| | | | | | | | Bug: 10649815 (cherry picked from commit 89ee8af81cfe231ed3cd21b050ec16fbcf419683) Change-Id: If28fab8c87222a9d182398a4deca167a8ca5c677
* Check JNI versions handed to JNI and JII functions.Elliott Hughes2013-08-021-2/+16
| | | | | Bug: https://code.google.com/p/android/issues/detail?id=58012 Change-Id: I7b062564573107df54f9e8d71df0e1583d83d421
* Throw NoSuchMethodError if RegisterNatives fails.Elliott Hughes2013-08-011-0/+7
| | | | | Bug: 9963858 Change-Id: I5b3ce3d3dbdc949e69f3389e2df19bcca5648d7e
* Disable -Xjnigreflimit.Elliott Hughes2013-07-021-48/+10
| | | | | | | | | | | This was supposed to help find bugs, but in practice (unlike the locale reference limit and the pinned array limit) doesn't. What it does do is cause well-behaved code to fail if its allocation rate is high. This has caused trouble for both audio and graphics code running on eng builds. Bug: 7903975 Change-Id: If475cb51c9cab13270a83a60d6d0aecfab758e88
* Fix minor leaks caused by failed initialization in JNI_CreateJavaVMYou Kim2013-04-041-0/+3
| | | | Change-Id: I97e4b162fa729c97a1e71786b696f2befed56835
* Fix a cast in JniEnv::NewDirectByteBuffer.Elliott Hughes2013-03-291-1/+1
| | | | Change-Id: I8692b31c6ce64efc68124df02117b6e4529dfe98
* Track 64-bit nio changes.Elliott Hughes2013-03-291-1/+1
| | | | Change-Id: Id7a11af5f94b8ba82d42e1e7045302aca533f31a
* Track libcore DirectByteBuffer cleanup.Elliott Hughes2013-03-271-3/+3
| | | | | Bug: https://code.google.com/p/android/issues/detail?id=53637 Change-Id: I7acd990a2a48b41dacb5b09f6410b4634dd60438
* Check JavaVMAttachArgs::version in CheckJNI.Elliott Hughes2013-03-131-2/+0
| | | | | Bug: 8363798 Change-Id: I314bf6d5d64a1e27ad2c1580532133859031c623
* Fix a forecopy/forcecopy typo.Elliott Hughes2012-12-211-1/+1
| | | | Change-Id: Ic8f8d6fdf278bfa41e54586bc187c0ba42248700
* Add JNI statistics to the SIGQUIT output.Elliott Hughes2012-12-211-0/+26
| | | | | Bug: 7903975 Change-Id: Ibc011ef73c8632fec42b846fcdee20c970951757
* Change NewDirectByteBuffer to allow NULL if capacity == 0.Elliott Hughes2012-12-191-18/+28
| | | | | | | Also make the diagnostics more uniform. Bug: 7892060 Change-Id: Ib3ca0d6241a5958d2c8681337b1883fc3d74cb54
* Fix ALOGV bit rot.Elliott Hughes2012-08-061-1/+1
| | | | Change-Id: Ia182af8f5ca3967a21003b3d1513145f8e6e5db0
* Throw ArrayStoreException instead of corrupting the heap.Elliott Hughes2012-04-051-1/+10
| | | | | | | | Protect against bad calls to SetObjectArrayElement. Found while debugging a Chrome crash. (This will make Chrome fail at the point where it does the invalid operation rather than later, but we already merged the fix upstream.) Change-Id: Ie7b2238d99f2ee4dde46342eb77cfec0495a30e7
* Replace malloc() followed by memset() to zero with calloc()Iliyan Malchev2012-02-161-2/+1
| | | | | | | | | | | Bionic's calloc() is smart enough to not zero out memory if it gets that memory from an anonyous mmap. Thus, if we use malloc for large allocations, we cause unnecessary memory duplication by following the malloc() with a memset(). An even better approach would be to replace the known large calloc() calls with dvmAllocRegion() allocation. Change-Id: Id308f541c9a040d5929bf991b6c2bfdefb823c3c
* Rename (IF_)LOGE(_IF) to (IF_)ALOGE(_IF) DO NOT MERGESteve Block2012-01-081-19/+19
| | | | | | | | | See https://android-git.corp.google.com/g/#/c/157220 Also fix an occurrence of LOGW missed in an earlier change. Bug: 5449033 Change-Id: I2e3b23839e6dcd09015d6402280e9300c75e3406
* Rename (IF_)LOGW(_IF) to (IF_)ALOGW(_IF) DO NOT MERGESteve Block2012-01-061-14/+14
| | | | | | | See https://android-git.corp.google.com/g/157065 Bug: 5449033 Change-Id: Ia5d301248024df26c2a29dabdfe738e39ec87c82
* Rename (IF_)LOGI(_IF) to (IF_)ALOGI(_IF) DO NOT MERGESteve Block2012-01-051-18/+18
| | | | | | | See https://android-git.corp.google.com/g/156801 Bug: 5449033 Change-Id: Ic558031c75b3702d90eb78bd730501ae5d3c077b
* Rename (IF_)LOGD(_IF) to (IF_)ALOGD(_IF) DO NOT MERGESteve Block2012-01-031-12/+12
| | | | | | | See https://android-git.corp.google.com/g/156016 Bug: 5449033 Change-Id: Ic663376d1ad6a6cb14bf81405ad9afd247cf2f60
* am 50e01501: Merge "Knock ::self() out of the ParseXml profile." into ics-mr1Elliott Hughes2011-11-051-225/+160
|\ | | | | | | | | * commit '50e015017f091118f0147d02d23140ff9f88daec': Knock ::self() out of the ParseXml profile.
| * Knock ::self() out of the ParseXml profile.Elliott Hughes2011-11-031-225/+160
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | New profile (>=0.6, which is where the original seems to have cut off): 47 11.0070 dvmCallJNIMethod(unsigned int const*, JValue*, Method const*, Thread*) 30 7.0258 dvmChangeStatus(Thread*, ThreadStatus) 29 6.7916 addLocalReference(Thread*, Object*) 26 6.0890 dexDecodeDebugInfo(DexFile const*, DexCode const*, char const*, unsigned int, unsigned int, int (*)(void*, unsigned int, unsigned int), void (*)(void*, unsigned short, unsigned int, unsigned int, char const*, char const*, char const*), void*) 22 5.1522 dalvik_inst 15 3.5129 lockMonitor(Thread*, Monitor*) 14 3.2787 dvmLineNumFromPC 13 3.0445 javaLangString_equals(unsigned int, unsigned int, unsigned int, unsigned int, JValue*) 13 3.0445 scanObject(Object const*, GcMarkContext*) 12 2.8103 ScopedJniThreadState::ScopedJniThreadState(_JNIEnv*) 12 2.8103 common_invokeMethodNoRange 12 2.8103 dvmDecodeIndirectRef(Thread*, _jobject*) 9 2.1077 IndirectRefTable::add(unsigned int, Object*) 9 2.1077 ReleasePrimitiveArrayCritical(_JNIEnv*, _jarray*, void*, int) 9 2.1077 markObjectNonNull(Object const*, GcMarkContext*, bool) 9 2.1077 unpinPrimitiveArray(ArrayObject*) 8 1.8735 getCodeAddrCommon(unsigned short const*, bool) 7 1.6393 dexStringByTypeIdx(DexFile const*, unsigned int) 7 1.6393 dvmHeapSourceAlloc(unsigned int) 6 1.4052 GetPrimitiveArrayCritical(_JNIEnv*, _jarray*, unsigned char*) 6 1.4052 dvmPlatformInvoke 6 1.4052 pinPrimitiveArray(ArrayObject*) 6 1.4052 readUnsignedLeb128(unsigned char const**) 6 1.4052 scanFields(Object const*, GcMarkContext*) 5 1.1710 IndirectRefTable::get(void*) const 5 1.1710 dvmFindInReferenceTable(ReferenceTable const*, Object**, Object*) 4 0.9368 common_returnFromMethod 4 0.9368 dvmAddToReferenceTable(ReferenceTable*, Object*) 4 0.9368 dvmHeapBitmapScanWalk(HeapBitmap*, void (*)(Object*, void*, void*), void*) 4 0.9368 dvmInterpret(Thread*, Method const*, JValue*) 4 0.9368 dvmLockObject 4 0.9368 dvmMalloc(unsigned int, int) 4 0.9368 findPackedSwitchIndex(unsigned short const*, int, int) 4 0.9368 readStringIdx(DexFile const*, unsigned char const**) 4 0.9368 unlockMonitor(Thread*, Monitor*) 3 0.7026 dvmSetFinalizable Change-Id: Ic5c36859f6810413bd0b48aad1d99da7daa6e8ba
| * DO NOT MERGE: Optimize IndirectRefTable.Jeff Brown2011-10-311-1/+3
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Removed unused debugging code that maintained pointers to the 4 previous objects in each slot. Promoted the serial number property of a slot to be first class. This is a sufficiently cheap and useful check to perform that we might as well always do it. Changed get() and remove() so they check the validity of the references at the same time as they retrieve them. They're also a bit smarter about checking the reference kind given that they can assume that the table will only contain references of one kind. The checks are now much more consistent. For example, remove() used to check whether an index was stale only in the case where it was not removing the top entry (now it always checks). Made add() return NULL instead of dvmAbort()'ing in the case where the table overflowed and ensure we don't blow away the table in that cases. This change resolves an issue with TestIndirectRefTable.cpp which deliberately overflows the table and expects add() to return NULL (as documented!). As it happens, the add() method is called in exactly 3 places in Jni.cpp. In each of those cases, the code was written to handle a NULL result and only in the case of adding a weak global reference did it not abort. Fixed the weak global reference case to be consistent with the others. Changed the signature of contains() to take an Object* since that's what we're actually looking for inside the table. Added a couple of calls to dump() in TestIndirectRefTable.cpp for visual inspection of its correctness. Performance as measured by TestIndirectRefTable on same hardware. Old implementation: - Add/remove 100 objects FIFO order, 100000 iterations, 0.023ms / iteration - Add/remove 100 objects LIFO order, 100000 iterations, 0.020ms / iteration - Get 100 objects, 100000 iterations, 0.009ms / iteration New implementation: - Add/remove 100 objects FIFO order, 100000 iterations, 0.010ms / iteration - Add/remove 100 objects LIFO order, 100000 iterations, 0.009ms / iteration - Get 100 objects, 100000 iterations, 0.002ms / iteration Cherry-pick from master. Conflicts: vm/IndirectRefTable.cpp Change-Id: I157f3c1ba598137222878b8e6a5890efb744fe76
* | Optimize IndirectRefTable.Jeff Brown2011-10-271-1/+3
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Removed unused debugging code that maintained pointers to the 4 previous objects in each slot. Promoted the serial number property of a slot to be first class. This is a sufficiently cheap and useful check to perform that we might as well always do it. Changed get() and remove() so they check the validity of the references at the same time as they retrieve them. They're also a bit smarter about checking the reference kind given that they can assume that the table will only contain references of one kind. The checks are now much more consistent. For example, remove() used to check whether an index was stale only in the case where it was not removing the top entry (now it always checks). Made add() return NULL instead of dvmAbort()'ing in the case where the table overflowed and ensure we don't blow away the table in that cases. This change resolves an issue with TestIndirectRefTable.cpp which deliberately overflows the table and expects add() to return NULL (as documented!). As it happens, the add() method is called in exactly 3 places in Jni.cpp. In each of those cases, the code was written to handle a NULL result and only in the case of adding a weak global reference did it not abort. Fixed the weak global reference case to be consistent with the others. Changed the signature of contains() to take an Object* since that's what we're actually looking for inside the table. Added a couple of calls to dump() in TestIndirectRefTable.cpp for visual inspection of its correctness. Performance as measured by TestIndirectRefTable on same hardware. Old implementation: - Add/remove 100 objects FIFO order, 100000 iterations, 0.023ms / iteration - Add/remove 100 objects LIFO order, 100000 iterations, 0.020ms / iteration - Get 100 objects, 100000 iterations, 0.009ms / iteration New implementation: - Add/remove 100 objects FIFO order, 100000 iterations, 0.010ms / iteration - Add/remove 100 objects LIFO order, 100000 iterations, 0.009ms / iteration - Get 100 objects, 100000 iterations, 0.002ms / iteration Change-Id: I1c904eb03bc8dd9822e6d9cce702c696e976974e
* | Rename (IF_)LOGV(_IF) to (IF_)ALOGV(_IF) DO NOT MERGESteve Block2011-10-261-8/+8
|/ | | | | | | See https://android-git.corp.google.com/g/#/c/143865 Bug: 5449033 Change-Id: I8bd96961e369a08e86ff78b82d90f20f42787eb1
* Don't use dvmIsValidObject outside the GC.Elliott Hughes2011-07-191-3/+1
| | | | | | | | Use dvmIsHeapPointer outside the GC. (This still isn't safe because there's no synchronization when dealing with the HeapSource.) Bug: 5049447 Change-Id: Ie0b325ef0a92687ea1eaf1491a4bb832298893c5
* Fix the jweak implementation.Elliott Hughes2011-07-111-15/+5
| | | | | | | | | | | | | We need to distinguish between "cleared weak global" and "deleted weak global". Previously we used NULL for both. Now we add a magic value for cleared weak globals. I've also switched the GC over to using iterators, so IndirectRefTable itself becomes responsible for not showing bad pointers to the GC. I've also improved the reference table dumping to cope with the new scheme and to be a bit easier to read (through extra indentation). Bug: 4260055 Change-Id: I26af301fb2b46d014c6f6b0915a8f8a7fb6d7c5b
* Add JNI app bug workarounds.Elliott Hughes2011-07-101-5/+16
| | | | | | | | | Specifically, this hands out direct pointers for all local references, and lets you use a JNIEnv* on the wrong thread. This is off by default, but enabled for apps that don't have ICS as their targetSdkVersion. Bug: 4772166 Change-Id: I20c403a8e63481a35d579d2bd3b121c80ec08f89
* Remove dead code/unused variables to avoid gcc-4.6 warnings.Doug Kwan2011-07-071-2/+0
| | | | Change-Id: I291fd42e91085c51772f560d424334874bef8add
* Improve a comment.Elliott Hughes2011-07-071-1/+2
| | | | Change-Id: If6636879dcdc15a33a083a19284de5fe8056e797
* Don't abort when a weak global's referent is cleared.Elliott Hughes2011-07-061-10/+20
| | | | | | | | | This also makes us less likely to output spurious warnings when dealing with nulled-out weak globals, and lets us provide more helpful warnings when warnings are called for. Bug: 4991942 Change-Id: I99b88e66e07f79562da2cd9d594b93bff218d595
* Fix native method logging to show local references rather than direct pointers.Elliott Hughes2011-06-301-186/+167
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This is necessary (but not sufficient) for debugging third-party JNI bugs. It's the second half of the logging story, but still doesn't address the question of "how does the developer turn on the logging?". This removes the variant JNI bridges at the cost of adding a couple of booleans to struct Method. Performance is about the same, except synchronized native methods are quite a bit faster after the change. Before: benchmark ns linear runtime _emptyJniMethod0 333 ========== _emptyJniMethod6 367 =========== _emptyJniMethod6L 921 ============================== _emptyJniStaticMethod0 259 ======== _emptyJniStaticMethod6 287 ========= _emptyJniStaticMethod6L 873 ============================ _emptyJniStaticSynchronizedMethod0 404 ============= _emptyJniSynchronizedMethod0 452 ============== After: benchmark ns linear runtime _emptyJniMethod0 344 ========== _emptyJniMethod6 348 ========== _emptyJniMethod6L 969 ============================== _emptyJniStaticMethod0 265 ======== _emptyJniStaticMethod6 293 ========= _emptyJniStaticMethod6L 968 ============================= _emptyJniStaticSynchronizedMethod0 265 ======== _emptyJniSynchronizedMethod0 323 ========== A better optimization for the case where there are reference arguments would be to keep a list of argument indexes in the struct Method, so we could iterate directly over those arguments that need converting to local references. That would also let us do something about the overhead of repeatedly looking up which local reference table and cookie to use. But now is not the time. Change-Id: Ie32daca1b31be057a44f1ed4b5d28d1634380e1d
* Add two new JNI debugging options.Elliott Hughes2011-06-301-16/+45
| | | | | | | | The alwaysCheckThread option provides some backwards compatibility for apps that misuse JNIEnv*s across threads. The logThirdPartyJni is a step towards making it easier for third-party developers to debug their JNI errors. Change-Id: I134374da0fe94f3fbc6b6d5aef52e3eef658aff9
* Improve -verbose:jni.Elliott Hughes2011-06-281-3/+16
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | The old output just told you what functions were being called and made no attempt to show you their arguments. The new output was sufficient to debug an actual problem with an app we don't have the source to. Still to do: 0. an easier way for third-party developers to enable this. 1. the primitive type arguments to SetIntField and so forth. 2. return values. A few examples of the new output... A decoded jclass: JNI: libcore.io.Posix.readBytes called IsInstanceOf((JNIEnv*)0x9618470, 0x28100015, java.lang.Class<byte[]>) A decoded jfieldID: JNI: libcore.io.Posix.ioctlInt called GetIntField((JNIEnv*)0x9618470, 0x5cb00011, java.io.FileDescriptor.descriptor) A decoded jmethodID (the FileDescriptor constructor): JNI: libcore.io.Posix.open called NewObject((JNIEnv*)0x9780480, java.lang.Class<java.io.FileDescriptor>, java.io.FileDescriptor.<init>()V, ...) A const char*: JNI: libcore.io.Posix.getsockoptLinger called NewStringUTF((JNIEnv*)0x9618470, "getsockopt") A jint release mode: JNI: libcore.io.Posix.writeBytes called ReleaseByteArrayElements((JNIEnv*)0x9780480, 0x2700009, (void*) 0xf5f623c4, JNI_ABORT) The -verbose:jni option now turns on a bit more output about JNI_OnLoad calls but no longer causes any logging of calls to JNIEnv or JavaVM functions. The old -Xjnitrace: option has been extended to enable this new tracing for the native methods that it covers. They go very well together for debugging purposes. I've also made us a bit more verbose if we fail to initialize. In the longer term I think we want to just abort if we hit any failure during startup, but my extra logging will save us a bit of time next time we have one of these failures (this one was caused for me by only having one half of the finalizer watchdog change; I was missing the libcore side). (Cherry pick of 6734b8224fb869c94e42e704ec03f2ce8483af2b from dalvik-dev.) Change-Id: I69b7620b20620e9f06576da244520d9d83f89ab8
* Throw NullPointerExceptions with detail messages.Elliott Hughes2011-06-231-1/+1
| | | | | Bug: 4905110 Change-Id: Iebcc45049c1ea14ceef6d44a19dd8cb618392101
* resolved conflicts for merge of cc8c750a to masterElliott Hughes2011-06-231-1/+3
| | | | | | (The transition to C++ requires an additional cast.) Change-Id: I736f6533511d5ab2d1f05903b06d8f333adba492
* Fix native methods that weren't registered via RegisterNatives.Elliott Hughes2011-06-231-7/+7
| | | | | | Cherry pick of a64af4aabf261d34eac8b5a9d92992ee70051829. Change-Id: I43df4e33e39ccaf9e26c842f22da3391cfa17e2b
* Clean up IndirectRefTable a bit.Elliott Hughes2011-06-211-48/+36
| | | | | | | The main purpose here was to have slightly less unclear warnings for JNI local reference abuse. Change-Id: I2c6378dd0a94d8afb96a8e409f7460205e3cd315
* Make some of the StringObject functions member functions.Elliott Hughes2011-06-171-18/+24
| | | | Change-Id: I72ed13c16f0cb24498772c453ba268a0f65f208a
* Better comments for yesterday's change.Elliott Hughes2011-06-151-1/+6
| | | | Change-Id: I1e05fb0e209d44874101b5ca8b7c8efec6810d5f
* Allow native methods to declare they don't need a JNIEnv*.Elliott Hughes2011-06-141-9/+35
| | | | | Bug: 3069458 Change-Id: Ic9a6c562c5abf9607dd4c8a71b0d1e389e6d340b
* Fix an issue regarding FindClass and threads without native methods.Carl Shapiro2011-06-091-1/+2
| | | | | | | | | | | | | Chapter 4 of the JNI specification states that when FindClass is called through the Invocation Interface and there is no associated method, the result of ClassLoader.getBaseClassLoader() is used as the class loader. Previously, the case where FindClass is called from a main thread was special cased to ensure this behavior. However, threads which attach to the VM but are not the main thread require similar treatment. With this change those threads are similarly treated as a special case. Change-Id: Idbe33e02a10d248262b9e9f089b033ffe05c4706
* Establish a subclass relationships among the field types.Carl Shapiro2011-05-061-4/+4
| | | | Change-Id: Id349b359489bb6b1bbb4ab78d29d85c0e6b33799
* Establish a subclass relationship between ArrayObject and Object.Carl Shapiro2011-05-031-2/+2
| | | | Change-Id: I9f9fe52bd4ceebb6dde48251a89190ba6bb00ce4
* Type the reference member of JValue as an Object pointer.Carl Shapiro2011-04-291-9/+9
| | | | | | | | | | | Previously this had been a void pointer. To avoid adding lots of casts from the logical Object subtypes to Object the RETURN_PTR macro silently casts its argument to an Object* before performing an assignment to the JValue return value. After an inheritance relationship is established between Object and its subtypes this cast can be removed. Change-Id: Id05e5c11e57e2a9afd12bad0be095f1dfe9e1f51
* Remove the old forcecopy in favor of the new.Elliott Hughes2011-04-271-33/+33
| | | | | | | | | Also remove some more half-baked multi-VM cruft, fix command-line parsing (so -Xforcecopy-fuck-yeah won't work any more), and remove an unused #define. Bug: 3412449 Change-Id: If914e23dd3bbcf0ac113a445777e0f550ca05703
* Add -Xjniopts:forcecopy-unmap to catch more errors than forcecopy.Elliott Hughes2011-04-261-69/+47
| | | | | | | | | In particular, this spots the BreakIterator bug that forcecopy didn't. It's about 2x slower than regular forcecopy mode, so I've added a new option rather than just replace the fast-but-less-effective forcecopy. Bug: 3412449 Change-Id: I1f226ceeab2508dff607ba25b0afee51cf9c3f83
* Consolidate curFrame fields in thread storagebuzbee2011-04-221-6/+7
| | | | | | | We ended up with two locations in the Thread structure for saved Dalvik frame pointer. This change consolidates them. Change-Id: I78f288e4e57e232f29663be930101e775bfe370f
* Remove dvmAllocObjectArray and all of its uses.Carl Shapiro2011-04-181-5/+5
| | | | | | | | This replaces uses of dvmAllocObjectArray with equivalent but safer calls to dvmAllocArrayByClass. dvmAllocObjectArray performed no type checking of its arguments and was easy to use incorrectly. Change-Id: Ia82fe73cb9d73bbb27f5961242ad5961f9f9924c
* Start actually using C++ in the JNI implementation.Elliott Hughes2011-04-151-373/+228
| | | | Change-Id: I9ed07e71d00de4caf314845c4e11201112bd65be