How to write a piece of code in Java to trigger a memory leak

Source: Internet
Author: User
Tags deflater

Q: I was in the interview just now, and the interviewer asked me how to write out the Java code that would be leaking memory. I have no idea of this problem, it's embarrassing.

A1: memory leaks can be easily generated by the following steps (program code cannot access some objects, but they are still in memory):

    1. The application creates a long-running thread (or, using a thread pool, a memory leak occurs faster).
    2. A thread loads a class from a class loader (which can be customized).
    3. This class allocates large chunks of memory (such as New byte[1000000]), stores a strong reference in a static variable, and then stores its own reference in Threadlocal. Allocating additional memory new byte[1000000] is optional (class instance leaks are sufficient), but this can make memory leaks faster.
    4. The thread cleans up the custom class or loads the class loader for that class.
    5. Repeat the above steps.

Because there is no reference to the class and ClassLoader, the storage in threadlocal cannot be accessed. Threadlocal holds a reference to the object, which also holds a reference to the class and its classloader, which holds all references to the classes it loads, so that the GC cannot reclaim memory stored in threadlocal. In many JVM implementations, the Java class and ClassLoader are assigned directly to the PermGen zone without performing a GC, which results in a more serious memory leak.

One of the variants of this leak pattern is that if you frequently redeploy applications that use threadlocal in any form, application containers (such as Tomcat) are prone to memory leaks (because the application container uses the same thread as previously described, the new classloader will be used each time the app is redeployed).

A2:

Static variable Reference Object

1 classMemorableClass {
2     staticfinal ArrayList list = newArrayList(100);
3 }

that calls a long string of String.intern ()

1 String str=readString(); // read lengthy string any source db,textbox/jsp etc..
2 // This will place the string in memory pool from which you cant remove
3 str.intern();

Open stream is not closed (file, network, etc.)

1 try{
2     BufferedReader br = newBufferedReader(newFileReader(inputFile));
3     ...
4     ...
5 } catch(Exception e) {
6     e.printStacktrace();
7 }

Connection not closed

1 try{
2     Connection conn = ConnectionFactory.getConnection();
3     ...
4     ...
5 } catch(Exception e) {
6     e.printStacktrace();
7 }

GC Unreachable zone for JVM

For example, the memory allocated through the native method.

Web application objects in the application scope, application not restarted or not explicitly removed

Getservletcontext (). SetAttribute ("Some_map", MAP);

Web Application object in session scope, not invalidated or not explicitly removed

Session.setattribute ("Some_map", MAP);

Incorrect or inappropriate JVM options

IBM JDK NOCLASSGC, for example, prevents garbage collection of useless classes

A3: If the hashset is not implemented correctly (or is not implemented) Hashcode () or Equals () will cause the collection to continue to increase "copy". If the collection cannot ignore the elements it should ignore, it will only grow in size and cannot delete the elements.

If you want to generate incorrect key-value pairs, you can do the following:

1 classBadKey {
2    // no hashCode or equals();
3    publicfinalString key;
4    publicBadKey(String key) { this.key = key; }
5 }
6
7 Map map = System.getProperties();
8 map.put(newBadKey("key"), "value"); // Memory leak even if your threads die.

A4: except for forgotten listeners, static references, key errors/modifications in HashMap, or thread blocking cannot end a typical memory leak scenario such as a life cycle, here are some less obvious cases of memory leaks in Java, mainly thread-related.

  • Runtime.addshutdownhook is not removed, even if Removeshutdownhook is used, the Threadgroup class may not be reclaimed due to a bug that does not start the thread, resulting in a memory leak threadgroup.
  • The thread was created but not started, as is the case above
  • Create threads that inherit Contextclassloader and AccessControlContext, Threadgroup and inheritedthreadlocal, all of which are potential leaks, And all classes loaded by the ClassLoader, all static references, and so on. The impact of the Threadfactory interface as an important constituent element throughout the J.u.c.executor framework (java.util.concurrent) is obvious, and many developers are not aware of its potential dangers. And many libraries will start the thread as requested.
  • Threadlocal caching, in many cases is not a good practice. There are many implementations of a simple cache based on threadlocal, but if a thread continues to run outside its expected life cycle contextclassloader will leak. Do not use the threadlocal cache unless it is really necessary.
  • Call Threadgroup.destroy () when Threadgroup itself has no threads but still has child thread groups. A memory leak occurs that causes the thread group to not be removed from its parent thread group and cannot enumerate the child thread groups.
  • Using Weakhashmap,value to refer to key directly (indirectly) is a difficult situation to find. This also applies to classes that inherit weak/softreference that may hold strong references to protected objects.
  • Download resources using the HTTP (s) protocol Java.net.URL. Keepalivecache creates a new thread in the system Threadgroup, causing the current thread's context class loader memory to leak. A thread is created on the first request when there is no surviving thread, so a leak is most likely to occur. (It has been fixed in Java7 that the code to create the thread reasonably removes the context ClassLoader.) )
  • Use Inflaterinputstream to pass new Java.util.zip.Inflater () in a constructor (such as Pngimagedecoder) without invoking the end () of Inflater. Only new words are very safe, but if you create the class as a constructor parameter, the call flow's close () cannot turn off Inflater, a memory leak can occur. This is not a real memory leak because it will be released by finalizer. But this consumes a lot of native memory, causing the Linux oom_killer to kill the process. So the lesson here is: release native resources as early as possible.
  • Java.util.zip.Deflater, too, the situation is even more serious. A good place may be seldom used to deflater. If you create a deflater or inflater, remember that you must call end ().

Original: http://www.open-open.com/bbs/view/1409626364853

How to write a piece of code in Java to cause a memory leak

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.