When working with Apache Tomcat, one might occasionally come across the error message java.lang.OutOfMemoryError: PermGen space. This is an issue related to memory allocation in the Java Virtual Machine (JVM). In this article, we will delve into the details of this error, its causes, and how to fix it.
Caused by: java.lang.OutOfMemoryError: PermGen space
at java.lang.ClassLoader.defineClass1(Native Method)
at java.lang.ClassLoader.defineClass(ClassLoader.java:800)
at java.security.AccessController.doPrivileged(Native Method)
What is PermGen Space?
PermGen, short for Permanent Generation, is a memory pool that was part of the JVM’s memory, specifically in the HotSpot JVM, up to Java 7. This memory space was reserved for JVM metadata for the classes and methods you use in Java. It includes things like class metadata, internalized strings, and other JVM internals.
Unlike the heap space, which can grow dynamically (to an extent) based on your program’s needs, the PermGen space has a fixed maximum size. If this size is exceeded, it results in the infamous OutOfMemoryError: PermGen space.
Why Does This Error Occur?
- Too Many Classes: Every time a class is loaded in the JVM, it takes up some space in the PermGen. If a large number of classes are loaded, more space is required than the default setting.
- Class Leaks: Similar to memory leaks, class leaks happen when the ClassLoaders, especially webapp classloaders in containers like Tomcat, load classes but don’t clean them up after undeploying a web application. This continuous non-release can fill up the PermGen space.
- Frequent Redeployment: Continuous or frequent redeployment of web applications without restarting Tomcat can lead to this error, especially if the applications are large or have a memory leak.
How to Resolve the Error
By default, Tomcat is assigned a minimal amount of PermGen memory for its running processes. To address this limitation, you can increase the PermGen memory allocation. This can be done by adjusting the Java Virtual Machine (JVM) options as follows:
- -XX:PermSize<size<: This option sets the initial PermGen size.
- -XX:MaxPermSize<size>: This option sets the maximum PermGen size.
Next, let’s explore how to set these JVM options in Tomcat for both Windows and Linux environments.
For Linux:
Create a file named setenv.sh manually and place it in the ${tomcat-folder}\bin\ directory.
In setenv.sh, add the following:
export JAVA_OPTS="-Dfile.encoding=UTF-8 -Xms128m -Xmx1024m -XX:PermSize=64m -XX:MaxPermSize=256m"
For Windows:
Create a file named setenv.bat manually and place it in the ${tomcat-folder}\bin directory.
In setenv.bat, add the following:
set JAVA_OPTS=-Dfile.encoding=UTF-8 -Xms128m -Xmx1024m -XX:PermSize=64m -XX:MaxPermSize=256m
Final Step:
Restart Tomcat to apply the changes.
After these modifications, Tomcat should have a more generous PermGen space allocation, reducing the chances of encountering java.lang.OutOfMemoryError: PermGen space errors.
Conclusion
While the java.lang.OutOfMemoryError: PermGen space error can be daunting at first, understanding its origins and the methods to combat it can help developers and system administrators keep their Tomcat servers running smoothly. For those still using Java versions up to 7, a consideration for an upgrade could be beneficial in the long run.