jmap and jstack - getting a heap dump and stack trace from a running JVM

February 21st, 2008 Nick Posted in java, unix No Comments »

The project I’m working on currently has many server side java components running on linux. One of these in particular has been experiencing severe memory leaks when running in our production environment (but not UAT, surprisingly!)

It turns out there is a tool provided with sun’s jdk 1.5 + which will allow you to get a snapshot of the heap for a running process, without you having to have started the jvm with any particular options set. This tool is called jmap

running:
jmap -histo pid
where pid is the process id on a linux box

will give you a snapshot of the heap which looks like the below:

java -histo pid

Object Histogram:

Size    Count       Class description
-------------------------------------------------------
77928   583        char[]
55696   131        byte[]
8816    29  * ObjArrayKlassKlass
8520    355 java.lang.String
8272    215 java.lang.Object[]
4080    85  java.nio.HeapByteBuffer
3984    83  java.nio.HeapCharBuffer
3608    41  java.lang.Class
2456    19  int[]
1368    57  java.util.Hashtable$Entry
1288    16  * ConstMethodKlass
1208    31  java.lang.String[]
1120    14  java.util.HashMap$Entry[]
1040    10  java.util.Hashtable$Entry[]
1008    14  java.lang.reflect.Field
960     3    * InstanceKlassKlass
etc.

The most useful thing here is probably the object class count. There is a chance this could help you identify an area of your app which is producing an unexpected number of instances of a given class. Other jmap options give you a dump file in different formats - so this is worth investigating too.

There is an equivalent tool jstack (jstack pid), which dumps stack information for each of the running threads. Probably useful for diagnosing deadlocks etc.

The nice thing about both of these tools is that you don’t need to have started the jvm with any specific options. These tools just connect and work - so you don’t need to have planned your memory leak in advance :)

They only work on unix right now, unfortunately.
There is a good article on new tools with jdk1.6 here

nb. if jstack fails you may be able to get a thread dump on unix using kill -3 {pid}
Here is another useful link for suggestions on diagnosing performance problems

And here is a good link to help diagnose java app problems in general

AddThis Social Bookmark Button

Making shell scripts robust by checking command exit values

April 12th, 2007 Nick Posted in unix No Comments »

One great thing about unix is the ability to automate common operations with simple shell scripts - however there are risks.
One such risk is that in the case a command fails, the script can plough on regardless.

If your script does something like the following..

cp -r mydir backup
rm -rf mydir

..you should really check that the copy command was successful before deleting the directory

The following solution should work in the Korn shell and Bash

A solution is found in the built in shell variable $?
This variable contains the exit code from the last command executed.
You can use it to check the exit code for each command and terminate the script early if something goes wrong.

In my scripts, I declare the following function to do this.
It checks the $? variable, and if the exit code was anything other than zero (success) it terminates the script with an error message

function fn_exitIfError
{
  if [ $? -ne 0 ] ; then
    echo $1 1>&2
    exit 1
  fi
}

This function takes a parameter ($1) which determines the error message written to standard error if an error occurred.
You use it like this:

function fn_exitIfError
{
  if [ $? -ne 0 ] ; then
    echo $1 1>&2
    exit 1
  fi
}

cp -r mydir backup
fn_exitIfError "Failed to copy mydir to backup"

rm -rf mydir
fn_exitIfError "Failed to delete mydir"

There are alternatives to the above –>

Alternatively you can call set -e at the top of your script.
This will make the script exit if any command returns a non zero status.

In the Korn shell, you can also combine set -e with trap ERR, and implement some custom handling if something goes wrong.

However, neither of these approaches will give you a very specific error message, which is why I prefer to use the function above, even if it is more verbose.



AddThis Social Bookmark Button

Find files modified after a date

April 11th, 2007 Nick Posted in unix No Comments »

How do you find the files which have been sneakily changed following a release?

The find -newer command can list files which were modified after another file
But I’m not sure there is a way to pass dates in directly?

The workaround is to create a temporary file with the required date, using touch

eg. for files modified after Christmas day 2006 (YYYYMMDDhhmm)

touch -t 200612250000 mydate
find . -type f -newer mydate



here is a quick shell script to automate finding files modified today, from the current directory:

#!/bin/sh
touch -t `date +%Y%m%d0000` /tmp/todaytimestamp
find . -type f -newer /tmp/todaytimestamp

AddThis Social Bookmark Button