Write in front:
recently began to summarize memory aspects of things, have summed up some of the previously encountered memory case sharing under, Then there are a few, then process/thread-related, gradually forming my knowledge system tree
If you are interested, you can comb this information together at the end of the article in the public number QR code.
oom problem is generally manual code errors, most in fact, in the review phase should be able to exclude, this article is mainly to record the memory snapshot troubleshooting OOM of a process
Scenario : The system's interactive security is completely dependent on a variety of encryption do (do not session, complete Web stateless, this design can be said later), so encryption becomes very important, but because of the new encryption introduced Bouncycastleprovider. So there is a modification, test machine a machine on-line after a period of time, after running for a period of time, the system becomes very slow, and finally appeared oom, resulting in a memory snapshot file.
Analysis:
JVM Memory Analysis: observe JVM memory and discover that a large number of OUs are being used to cause frequent GC, resulting in slow system (basic not available)
memory Snapshots Analyze the reason for Oom , the best way for this kind of memory analysis is to dump two copies, a normal one, which is a comparison of when oom occurs.
Failure Recurrence:
First give 1G memory to Tomcat, and when oom outputs the log, the JVM parameters are configured as follows:
After normal startup, the dump is normal for the back of the analysis (the snapshot generated after the oom and the normal snapshot of the comparison can be very convenient to find the leaking object)
file Import Eclipse Memory Analyzer
Found that basically finalizer is taking up memory
Description: When Java creates an object, a new additional finalizer object is created to point to the newly created object. In the case of recycling, at least two GC is required, so this is a normal memory
Then began to test, 2000 times after the request, the system later found more and more slow, basic unavailable, view the GC, found that basic all the memory is full, has been in the GC
Continue to say the snapshot, then the memory dump down to import, contrast
Open the snapshot, from the global view has been obviously able to find the problem, memory is jcesecurity occupied 861M, can be determined to be jcesecurity problem.
Further analysis, generally use the following 3 reports
1. View Global Memory
2, Memory leak analysis
3, large object sort
This is the 2nd one to view the leak analysis report.
96% of the memory is jcesecurity this class takes up
After you find the problem object, review the details
Shows the basic situation of this class,
is the shortest path through which the GC is root, which can be traced back to the structure of the class tree of the problem code, and find the final referenced code
Can finally find a direct reference to the class, where there is finally a class javax.crypto.jceSecurity variable, verificationresults inside
2, see the contents of Verificationresults
Description
With outgoning references see what it refers to and can be seen as what the collection contains
With incomming references see the class that references it
Description
Shallow heap is the size of an object's own footprint
Retained Heap is the total size of the object that contains the content
Found that the memory is basically occupied by a bouncycastleprovider inside it.
Finally, according to the snapshot can be drawn:
The place that causes the problem is the org.bouncycastle.jce.provider.BouncyCastleProvider of the variable verificationresults in the class javax.crypto.jceSecurity
Code Search:
Find the class Cryptoutil in your project based on the code found above that is useful to org.bouncycastle.jce.provider.BouncyCastleProvider.
Tools to extract the class;
The point is, every time a new bouncycastleprovider.
Cipher Cipher = cipher.getinstance (Constants.crypoto_name, New Bouncycastleprovider ());
This class, code from 7U40-B43
Get in from Cipher.init.
This section is used to verify that the provider object that provides security is a jar that can be trusted by JCE and caches the results of the cache and caches the provider when the key is stored in a static map, so it can be understood that an old area is not recycled.
Validation of Verificationresults
It is worth noting that if this is hashmap and not identivhashmap, then it is not a memory leak, why do you say so?
If it is hashmap, it is not as new as how many Bouncycastleprovider, in HashMap is also a, code confirmed under:
/** * Small test, used to illustrate the difference between the next provider and IDENTITYHASHMAP special treatment * @author bun (He Jinbin) 2017.01.20 * */public class Test {public static void Main (string[] args) { Map hashmap=new hashMap (); Hashmap.put (New Bouncycastleprovider (), "Provoder1"); Hashmap.put (New Bouncycastleprovider (), "Provoder2"); System.out.println (Hashmap.size ()); The output is 1 Map identitymap=new identityhashmap (); Identitymap.put (New Bouncycastleprovider (), "Provoder1"); Identitymap.put (New Bouncycastleprovider (), "Provoder2"); System.out.println (Identitymap.size ()); Output is 2 }}
The reasons are as follows:
1, Java.security.Provider's hashcode and equals methods are handled in a special way, in provider, as long as the key is equal, the comparison of two provider is equal
2,identivhashmap The main difference between this class and HashMap is that when put, it is used to determine whether two keys are equal = =
The Identivhashmap code is as follows:
And the HashMap here is:
HashMap is used if (E.hash = = Hash && (k = e.key) = = Key | | key.equals (k)), comparing hashcode with equals
Solve
1. in fact, as long as the designated way by
Cipher Cipher = cipher.getinstance (Constants.crypoto_name, New Bouncycastleprovider ());
Change into
Security.addprovider (New Org.bouncycastle.jce.provider.BouncyCastleProvider ());
2, change the Bouncycastleprovider to a single case mode
Q 1:
As to why it is to be specified with Bouncycastleprovider
http://blog.csdn.net/defonds/article/details/42775183
OK, or simply delete the unspecified
Q 2:
In fact, you can print the survival of the object, Jmap-histo 7276 > Dump.txt, has been able to see some clues
Continuously update message questions, answer questions
Welcome to my public number, reproduce the bug on the line and build our knowledge system together.
Or search the "Bun Lab."
Memory Snapshot Troubleshooting Oom, encryption Error method specifies an oom caused by an provider method error