Sie sind auf Seite 1von 27

CodePro Profiler Tutorial

Table of Contents
Discovering Performance Bottlenecks.................................................................................................... 2 Profiled Application ................................................................................................................. 2 Discovering Performance Bottlenecks .................................................................................... 2 Memory Optimization .............................................................................................................................. 4 Profiled Application ................................................................................................................. 4 Memory Optimization .............................................................................................................. 4 Memory Optimization Using Allocation Tracking and Object Lifetime Profiling .................................... 8 Profiled Application ................................................................................................................. 8 Memory Optimization .............................................................................................................. 8 Discovering Memory Leaks................................................................................................................... 12 Profiled Application ................................................................................................................12 Discovering Memory Leaks................................................................................................... 12 Finding Memory Leak Candidates ........................................................................................ 15 Deadlock Detection ............................................................................................................................... 19 Profiled Application ............................................................................................................... 19 Detecting Deadlocks ............................................................................................................. 19 Profiling J2EE Applications ................................................................................................................... 21 Profiled Application ............................................................................................................... 21 Prerequisites ......................................................................................................................... 21 Profiling J2EE Application ..................................................................................................... 21

CodePro Profiler Discovering Performance Bottlenecks


Profiled Application
Profiled application: PointEvaluator Project: com.instantiations.sample.bottleneck Description: The application generates 100,000 points in a three-dimensional space in a random manner (all coordinates ranging between 0.0 and 1.0). Each point has a mass associated with it. The center of mass is computed and all points distant from the center of mass by less than 0.5 are removed from the set. The execution time of the application is shown in the console after finishing. Each point is represented as an instance of the class Point. During the processing, the points are stored in an ArrayList.

Discovering Performance Bottlenecks


1. Launch the application in profile mode. Choose CPU sampling. 2. Wait until the application finishes. 3. Estimate the execution time of the application by looking in the Console. The execution time is more than 44 seconds, which is too much for this application. 4. Take a CPU snapshot and open it. 5. Look at the Hot Spots view. Sort the methods by Self Time.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 2

The method that consumed the greatest amount of CPU time is the method remove in the class java.util.ArrayList. This method is being invoked every time we need to remove a point because we chose to use an ArrayList to store the collection of points we are working with. While we cannot change the implementation of remove, we should still try to understand why so much of the time is being spent in it. There are two possible reasons, both of which are true in this case. The first reason is the number of times its being invoked. If we assume a random distribution of points, then about 50% of them should be getting removed. Thats around 50,000 invocations of the remove method. The second reason is the amount of time spent in remove each time its called. A list is a good choice of data structure when the number of elements is relatively small or when you dont need to search it, but the remove method needs to search the list to find the index of the element to be removed every time it is invoked. It does so using a linear search, which is fairly slow when there are between 100,000 and 50,000 items in the list. There are two possible solutions. The first is to change the algorithm so that we dont need to remove points from the list, possibly by creating a second list and adding the points were keeping to it. The second solution is to use a data structure from which the points can be removed in less time. Well choose the second solution because it requires fewer changes to the existing code. 6. Change the type of collection from ArrayList to HashSet (see the comparison of files PointSystem.java in the projects com.instantiations.sample.bottleneck and com.instantiations.sample.bottleneck.solved). 7. Profile the changed application. 8. Note that the execution time is less than 1 second, which is much more reasonable.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 3

Memory Optimization
Profiled Application
Profiled application: ThingsTest Project: com.instantiations.sample.memory Description: The application generates 50,000 instances of the class Thing (things have a name, a value, and a collection of named properties) and sets the property Broken to true for approximately 5% of the created things. It doesnt set any properties on the other things. The type of collection of things is ArrayList. The type of the field properties is HashMap.

Memory Optimization
1. Launch the application in the profile mode. 2. Watch the Memory Telemetry view.

The amount of used heap memory is more than 8 MB, which is too much for this application. 3. Take a memory snapshot and open it. 4. Look at the Biggest Objects view.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 4

The biggest object which can interest us is an instance of java.util.ArrayList. 5. Use java.util.ArrayList as a name filter and open the Class List view.

Both the shallow size of class java.util.ArrayList and the number of instances are small compared to the retained size, which tells us that the list is probably not the problem, its more likely the elements stored in the list that are using too much memory. To confirm this, lets look at the problem from a different angle. 6. Select the Class List view and sort the classes by Shallow Size.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 5

The class with the biggest shallow size is java.util.HashMap. It is also the class with the biggest number of instances and one of the largest retained sizes. The number of instances of the class java.util.HashMap is near 50,000. The number of objects of the class java.util.HashMap$Entry is near 2,500. Because there are fewer entries than there are hash maps, it tells us that most of the hash maps must be empty (at least 47,500 of them). There is another class with almost as many instances: the class Thing. 7. Look at the implementation of the class Thing. We can see two interesting facts. First, every instance has a field named properties of type HashMap. Second, this field is initialized to an instance of HashMap when the instance of Thing is created. We know from the problem description that we are only setting the value of a property on about 5% of the instances of Thing. This suggests that a possible solution would be to leave the field properties un-initialized until we first set a property, treating a value of null as being equivalent to any empty HashMap. 8. Change the code to initialize the field property only if a property is set on the thing (see the comparison of files Thing.java in the projects com.instantiations.sample.memory and com.instantiations.sample.memory.solved). 9. Profile the changed application. 10. Take a memory snapshot and open it. 11. Look at the Class List view. Use java.util.HashMap as name filter.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 6

The number of object of class java.util.HashMap is near 2,500, which is what we would have expected. 12. Look at the Basic Telemetry section in the Session Explorer. The amount of used heap memory is now less than 3 MB.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 7

Memory Optimization Using Allocation Tracking and Object Lifetime Profiling


Profiled Application
Profiled application: ThingsTest Project: com.instantiations.sample.memory Description: The application generates 50,000 instances of the class Thing (things have a name, a value, and a collection of named properties) and sets the property Broken to true for approximately 5% of the created things. It doesnt set any properties on the other things. The type of collection of things is ArrayList. The type of the field properties is HashMap.

Memory Optimization
1. Create a profiling launch configuration. Choose BCI profiling without filters. Turn on allocation tracking and object lifetime profiling. Launch application in profile mode. 2. Watch the Memory Telemetry view.

The amount of used heap memory is more than 8 MB, which is too much for this application. 3. Take a memory snapshot. 4. Take a CPU snapshot. 5. Stop the profiling session.
COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 8

6. Open the memory snapshot. 7. Open the Class List view and sort classes by Shallow Size to find classes with the biggest amount of memory allocated to store objects of these classes.

The class with the biggest shallow size is java.util.HashMap. It is also the class with the biggest number of instances and one of the largest retained sizes. The number of instances of the class java.util.HashMap is near 50,000. The number of objects of the class java.util.HashMap$Entry is near 2,500. Because there are fewer entries than there are hash maps, it tells us that most of the hash maps must be empty (at least 47,500 of them). 8. Use java.util.HashMap as a name filter. 9. Look at the Object Lifetime view.

The Allocation hot spot method created by the biggest number of objects of java.util.HashMap class is the method com.instantiations.sample.memory.Thing.<init>. 50,000 objects of java.util.HashMap class have been created in the constructor of class Thing. 10. Open the CPU snapshot.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 9

11. Look at the Allocation Method List view sorted by Own Shallow size.

Methods with the biggest amount of shallow size are java.util.HashMap.<init>, com.instantiations.sample.memory.Thing.<init>, com.instantiations.sample.memory.ThingsTest.main. 12. Look at the Allocation Hot Spots view sorted by Shallow size.

Methods with the biggest amount of shallow size are the same three methods. 13. Open the implementation of the method com.instantiations.sample.memory.Thing.<init>.

14. Look at the implementation of the class Thing. The field named properties is initialized to an instance of HashMap when the instance of Thing is created. We know from the problem description that we are only setting the value of a property on about 5% of the instances of
COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 10

Thing. This suggests that a possible solution would be to leave the field properties uninitialized until we first set a property, treating a value of null as being equivalent to any empty HashMap. The Allocation views confirm this. 15. Change the code to initialize the field property only if a property is set on the thing (see the comparison of files Thing.java in the projects com.instantiations.sample.memory and com.instantiations.sample.memory.solved). 16. Profile the changed application. 17. Look at the Memory Telemetry view.

The amount of used heap memory is now less than 3 MB. 18. Take a memory snapshot and open it. 19. Look at the Class List view. Use java.util.HashMap as name filter.

The number of objects of the class java.util.HashMap is close to 2,500, which is what we would have expected.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 11

Discovering Memory Leaks


Profiled Application
Profiled application: ThingsTest Project: com.instantiations.sample.memory Description: The application generates a number of instances of the class Thing (things have a name, a value, and a collection of named properties, and two things are defined to be equal if they have the same name). It sets the name of each thing where the name is the concatenation of the string Thing and a random number (0 - 999). The property Broken is set to true for approximately 5% of the created things. It doesnt set any properties on the other things. The created things are used as keys in a HashMap that maps things to their names. The expectation is that there will never be more than 1,000 things in the map at any given time because that is the number of possible names. The type of the field properties is also HashMap.

Discovering Memory Leaks


1. Launch the application in the profile mode. 2. Watch the Memory Telemetry view.

Used heap memory constantly increases. It possibly means there's a memory leak. 3. Force a garbage collection.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 12

This action hasnt affected the memory usage increase so the problem isnt uncollected garbage. 4. Take a memory snapshot. 5. Take a second memory snapshot after some period of time. 6. Open the second memory snapshot. 7. Look at the Biggest Objects view.

The biggest object is an instance of the class java.util.HashMap. 8. Look at the Class List view. Use java.util.HashMap as a name filter.

The number of instances of this class is near 33,000. Thats too high because only 1,000 different names for things are possible and only 5% of them can have a property. So the number of objects should be near 1,000. 9. Open the first memory snapshot.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 13

10. Compare these snapshots. The retained size of the class java.util.HashMap in the first snapshot (7,283,840) is much less than the retained size in the second snapshot (11,642,080). This indicates that at least one of the hash maps is probably growing without bounds, which is a common symptom of a memory leak. The most likely candidate is the hash map mapping instances of Thing to their names. This map could only be growing without bounds if two instances of the class Thing that have the same name are not comparing as equal. 11. Checking the class Thing, the problem quickly becomes apparent: the method equals was not implemented, so they are defaulting to using object identity. 12. Add the method equals (and hashCode, of course) to the class Thing (see the comparison of files Thing.java in the projects com.instantiations.sample.memory.leaks and com.instantiations.sample.memory.leaks.solved). 13. Profile the changed application. 14. Take a memory snapshot. 15. Look at the Class List view. Use java.util.HashMap as a name filter.

The number of instances of the class java.util.HashMap is near 1,000, which is what we expected. 16. Check the Memory Telemetry view to verify that the amount of memory being consumed is holding steady.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 14

Finding Memory Leak Candidates


1. Create a Profile launch configuration. Choose BCI profiling mode and enable Track object allocations and Collect object lifetime information and clear the BCI filters. Launch the application in the profile mode. 2. Watch the Memory Telemetry view.

Used heap memory constantly increases. It possibly means there's a memory leak. 3. Force a garbage collection. This action hasnt affected the memory usage increase so the problem isnt uncollected garbage. 4. Take a memory snapshot and stop the profiler. 5. Open the Memory Leak Candidates view. 6. Start Memory Leak Candidates discovering.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 15

The first found candidates with the biggest retained size are instances of the class java.util.HashMap$Entry. 7. Stop Memory Leak Candidates discovering. 8. Find path from GC root to the object java.util.HashMap$Entry.

GC root for the object java.util.HashMap$Entry is java.util.HashMap. 9. Look at the Object Lifetime view. Use java.util.HashMap as a name filter.

The number of instances of this class is near 25,000. Thats too high because only 1,000 different names for things are possible and only 5% of them can have a property. So the number of objects should be near 1,000. Besides it the average GC count for this objects is 7.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 16

10. Look at the Summary view of this snapshot. Total GC count is 15. So the average GC count for objects of class java.util.HashMap is a half of total GC count. 11. Go back to the Object Lifetime view.

Look at the allocation hot spots for the class java.util.HashMap. The constructor of class Thing has created the most of instances of the class java.util.HashMap and the lifetime of these instances is rather long. The hash map mapping instances of Thing to their names could only be growing without bounds if two instances of the class Thing that have the same name are not compared as equal. 12. Checking the class Thing, the problem quickly becomes apparent: the method equals was not implemented, so they are defaulting to using object identity. 13. Add the method equals (and hashCode, of course) to the class Thing (see the comparison of files Thing.java in the projects com.instantiations.sample.memory.leaks and com.instantiations.sample.memory.leaks.solved). 14. Profile the changed application. 15. Take a Memory snapshot. 16. Open the snapshot and look at the Object Lifetime view. Use java.util.HashMap as a name filter.

The number of instances of the class java.util.HashMap is near 1,000, which is what we expected.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 17

17. Check the Memory Telemetry view to verify that the amount of memory being consumed is holding steady. 18. Stop the profiler.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 18

Deadlock Detection
Profiled Application
Profiled application: Smorgasbord Project: com.instantiations.sample.deadlocks Description: This application implements a system of work of a smorgasbord. The menu consists of only soup. A guest should use a ladle and a spoon to eat the soup. Two guests came to the smorgasbord. While the first guest tries to eat his soup, the second one looks around.

Detecting Deadlocks
1. Create a Profiler launch configuration with the thread profiling enabled and launch the application in profile mode. 2. Watch the console view. Notice that first guest hasnt said Lunch is over. That means that he hasnt eaten. Its possible that there is a deadlock in the application. 3. Open the Deadlocks view.

One deadlock has been found. Threads First Guest and Second Guest have blocked each other.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 19

4. Open the Current Monitor Usage view.

The first class of with blocked event type is Smorgasbord$Ladle and the class with blocked event type is Smorgasbord$Spoon. The first guest has taken a ladle from the table and the second guest took his spoon. So the first guest cant finish his lunch. 5. Change the first synchronized block (ladle) for the first guest so that it closes before opening the second synchronized block (spoon). See the comparison of files Smorgasbord.java in the projects com.instantiations.sample.deadlocks and com.instantiations.sample.deadlocks.solved. 6. Profile the changed application. 7. Watch the console view. The first guest has finished his lunch because the second guest couldnt take his spoon.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 20

Profiling J2EE Applications


Profiled Application
Profiled J2EE application: DemoServlet J2EE server: Apache Tomcat v5.5 Project: com.instantiations.sample.j2ee

Prerequisites
1. Eclipse WTP to be installed. 2. Any supported J2EE server. 3. Start Eclipse. For this demo we use WTP version 2.0 and Apache Tomcat v5.5 server.

Profiling J2EE Application


9. Open Servers view in the Java EE perspective. 10. Add new Apache Tomcat v5.5 server.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 21

11. Import J2EE application com.instantiations.profiler.j2ee.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 22

12. Profile the application using Profile With CodePro As item in the context menu.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 23

Select Tomcat v5.5 Server in the list.

Profiling perspective opens after profiling has been started. 13. Take CPU snapshot after request served. 14. Open Method List view.

There are com.instantiations.sample.j2ee.DemoServlet methods in the list. Thats mean that J2EE application has been profiled.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 24

15. Lets consider another way to profile J2EE application. Start profiling of Apache Tomcat server.

Select CodePro Profiler launcher in the list.

16. Open web browser.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 25

17. Run target J2EE application via browser (use link http://localhost:8080/com.instantiations.sample.j2ee/DemoServlet).

18. Go to Eclipse window. Target application has been profiled on server. 19. Lets consider managing of profile mode launch configuration. Use Open Profile Dialog item in the profiling menu.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 26

Change settings in the launch configuration dialog.

The next profiling session will be started with updated settings.

COPYRIGHT 2007 INSTANTIATIONS, INC. ALL RIGHTS RESERVED.

PAGE 27

Das könnte Ihnen auch gefallen