i have sample code for increase Heap Memory.But it is not increasing Memory.
sample Code :
int mb=1024*1024;
long rt=Runtime.getRuntime().totalMemory();
int heapsize=(int) (rt/mb);
System.out.println("Heap Size : " +heapsize);
String[] cmd = {"cmd.exe", "/c", "cd/C C:\\Users\\xxxxxx\\Documents\\NetBeansProjects\\MultiThreadSample\\src\\multithreadsample && java -Xms61m -Xmx128m"};
Process exec = Runtime.getRuntime().exec(cmd);
exec.destroy();
SpawnAndChangeHeap is the class name.Can You Please Suggest Me?
java heap allocation are continuous and happens at JVM initialization. Programmatically heap size cannot be extended or modified until Xmx or Xms changed with JVM restart.
Related
I have a java program whose only function is to use about 512M RAM and be idle. Running natively it works:
java -Xmx559m MemoryEater
When I run the same program with the same memory settings in Docker, Java errors out with an out of memory error. That's java not docker killing it. I have to nearly double heap size to have a successful run.
docker run -it --rm -e JAVA_OPTIONS='-Xmx1027m' memory-eater memory-eater
Why is this? I did try setting different levels of docker --memory and --memory-swap but the 1027m heap size is always required.
Additional Info:
Error message:
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
at MemoryEater.main(MemoryEater.java:10)
Program:
import java.util.Vector;
public class MemoryEater
{
public static void main(String[] args)
{
Vector v = new Vector();
for( int i=1; i<512; i++)
{
byte b[] = new byte[1048576];
v.add(b);
Runtime rt = Runtime.getRuntime();
System.out.println( "i = " + i + " free memory: " + rt.freeMemory() + " max memory: " + rt.maxMemory() + " total memory: " + rt.totalMemory() );
}
while( true ){}
}
}
Both native and container are 64bit.
In your docker command I do not see that you are restricting memory usage in any way. That means docker will allow the container to use whatever the host is able to give. With that your JVM will (hopefully) die for memory before docker gets active.
Check out the available options:
https://docs.docker.com/config/containers/resource_constraints/
And use docker statsto display actual resource usage and limits.
https://docs.docker.com/engine/reference/commandline/stats/
I'm using Lucene v4.10.4. I have pretty big index, it could be over few GBs. So I get OutOfMemoryError on initializing IndexSearcher:
try (Directory dir = FSDirectory.open(new File(indexPath))) {
//Out of Memory here!
IndexSearcher searcher = new IndexSearcher(DirectoryReader.open(indexDir));
How to tell Lucene's DirectoryReader to not load into memory more than 256 MB at once?
Log
Caused by: java.lang.OutOfMemoryError: Java heap space
at org.apache.lucene.util.fst.BytesStore.<init>(BytesStore.java:68)
at org.apache.lucene.util.fst.FST.<init>(FST.java:386)
at org.apache.lucene.util.fst.FST.<init>(FST.java:321)
at org.apache.lucene.codecs.blocktree.FieldReader.<init>(FieldReader.java:85)
at org.apache.lucene.codecs.blocktree.BlockTreeTermsReader.<init>(BlockTreeTermsReader.java:192)
at org.apache.lucene.codecs.lucene41.Lucene41PostingsFormat.fieldsProducer(Lucene41PostingsFormat.java:441)
at org.apache.lucene.codecs.perfield.PerFieldPostingsFormat$FieldsReader.<init>(PerFieldPostingsFormat.java:197)
at org.apache.lucene.codecs.perfield.PerFieldPostingsFormat.fieldsProducer(PerFieldPostingsFormat.java:254)
at org.apache.lucene.index.SegmentCoreReaders.<init>(SegmentCoreReaders.java:120)
at org.apache.lucene.index.SegmentReader.<init>(SegmentReader.java:108)
at org.apache.lucene.index.StandardDirectoryReader$1.doBody(StandardDirectoryReader.java:62)
at org.apache.lucene.index.SegmentInfos$FindSegmentsFile.run(SegmentInfos.java:923)
at org.apache.lucene.index.StandardDirectoryReader.open(StandardDirectoryReader.java:53)
at org.apache.lucene.index.DirectoryReader.open(DirectoryReader.java:67)
First you should check the current heap size of your JVM.
java -XX:+PrintFlagsFinal -version | grep MaxHeapSize
If this number is not reasonable for your use case, you should increase it when running your program with -Xmx option of java command. A sample command to assign 8GB of heap memory would look like:
java -Xmx8g -jar your_jar_file
Hope this helps.
I am running an Rscript from Java which is having two functions one will return a data frame and other will return the column name of the data frame returned by function 1.
The code is running fine for 400 MB data but when I am testing with more than 400 MB it is throwing exception: Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
I have tried many solutions for this to increase the heap size.
The solutions I have tried are:-
I have edited the domain.xml file of glassfish.
I have tried to set fore fully Java option using "set _JAVA_OPTIONS = -Xms1025m -Xmx4gm" and export JAVA_OPT= -Xms1025m -Xmx4g.
Edited the netbeans.conf file as
netbeans_default_options="-J-Xms1025m -J-Xmx4g -J-Xss32m -J-XX:PermSize=128m -J-XX:MaxPermSize=2g -J-Xverify:none -J-Dapple.laf.useScreenMenuBar=true -J-Dapple.awt.graphics.UseQuartz=true -J-Dsun.java2d.noddraw=true -J-Dsun.java2d.dpiaware=true -J-Dsun.zip.disableMemoryMapping=true"
Crontab with Java option -Xms1025m -Xmx4gm
Changed the netbeansproject->properties->run->vmoption also.
But still getting the same error.
And when I tried to check the heap size using the below Java code. It is showing something different. I am not getting which is correct and which is wrong. The heap size is changed or not. How to know it and how to solve this?
I got this code from some website while searching for the error.
The output I am getting is
run:
JVM freeMemory: 10
JVM totalMemory also equals to initial heap size of JVM : 10
JVM maxMemory also equals to maximum heap size of JVM: 168
Used Memory in JVM: 162
freeMemory in JVM: 6
totalMemory in JVM shows current size of Java heap : 15
maxMemory in JVM: 168
JVM Bit size: amd64
Heap Size = 163123200
public class MemoryUtil
{
private static final int MegaBytes = 10241024;
public static void main(String args[]) {
long freeMemory = Runtime.getRuntime().freeMemory()/MegaBytes;
long totalMemory = Runtime.getRuntime().totalMemory()/MegaBytes;
long maxMemory = Runtime.getRuntime().maxMemory()/MegaBytes;
System.out.println("JVM freeMemory: " + freeMemory);
System.out.println("JVM totalMemory also equals to initial heap size of JVM : "
+ totalMemory);
System.out.println("JVM maxMemory also equals to maximum heap size of JVM: "
+ maxMemory);
ArrayList objects = new ArrayList();
for (int i = 0; i < 10000000; i++) {
objects.add(("" + 10 * 2710));
}
freeMemory = Runtime.getRuntime().freeMemory() / MegaBytes;
totalMemory = Runtime.getRuntime().totalMemory() / MegaBytes;
maxMemory = Runtime.getRuntime().maxMemory() / MegaBytes;
System.out.println("Used Memory in JVM: " + (maxMemory - freeMemory));
System.out.println("freeMemory in JVM: " + freeMemory);
System.out.println("totalMemory in JVM shows current size of java heap : "
+ totalMemory);
System.out.println("maxMemory in JVM: " + maxMemory);
System.out.println("JVM Bit size: " + System.getProperty("os.arch"));
long heapSize = Runtime.getRuntime().totalMemory();
//Print the jvm heap size.
System.out.println("Heap Size = " + heapSize);
}
}
To change the maximum heap size for the applications running inside Glassfish you only have to edit the setting in your domain.xml.
Stop Glassfish, open the file (/GLASSFISH_HOME/glassfish/domains/domain1/config/domain.xml for those who don't know) with a text editor and search for Xmx (the first result), it should look like this:
<jvm-options>blabla</jvm-options>
<jvm-options>-Xmx512m</jvm-options>
It may contain another value if you already touched this. Change the value to something like this:
<jvm-options>blabla</jvm-options>
<jvm-options>-Xmx4096m</jvm-options>
Note that Glassfish itself requires some memory to run, I suggest you add additional 350 MB only for Glassfish on your setting, if your hardware specs allow that.
Alternativly you can use the Glassfish Admin UI to change the setting:
I want to collect heap dump on JVM crash
So i wrote a simple code
public class Test {
private String name;
public Test(String name) {
this.name = name;
}
public void execute() {
Map<String,String> randomData = new HashMap<String,String>();
for(int i=0;i<1000000000;i++) {
randomData.put("Key:" + i,"Value:" + i);
}
}
public void addData() {
}
public static void main(String args[]) {
String myName = "Aniket";
Test tStart = new Test(myName);
tStart.execute();
}
}
and I am running it as follows
[aniket#localhost Desktop]$ java -cp . -Xms2m -Xmx2m Test
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
at Test.execute(Test.java:15)
at Test.main(Test.java:25)
I got OutOfMemoryError which I wanted but there is no heap dump in the working directory(like hs_err_pidXXXX.log which I expected). What am I missing? How do I get a heap dump?
Update :
I tried -XX:ErrorFile=. still no use. If above is not the way to get the heap dump(Crash JVM) how can I crash my JVM to get those logs?
You are confusing an exception or error being thrown as a JVM crash.
A JVM crash occurs due to an internal error in the JVM, you cannot trigger this by writing a normal Java program (or should not unless you find a bug)
What you are doing is triggering an Error which means the program continues to run until all the non daemon threads exit.
The simplest tool to examine the heap is VisualVM which comes with the JDK. If you want to trigger a heap dump on an OutOfMemoryError you can use -XX:+HeapDumpOnOutOfMemoryError
Use Jmap
jmap [options] pid
pid is the process id of application
When you see the below
Exception in thread "main" java.lang.OutOfMemoryError
It means your error or exception is handled by the exception handler. This is not a crash.
Eclipse has an awesome Heap Analyzer
Also, you can use jps to get the PID, and then jmap for the heap itself.
In case, you want to crash the JVM, your best guess would be native code.
Find the process id for which you want to take the heap dump
ps -ef | grep java
Once you get PID by running above command run below command to generate heap dump.
jmap -dump:format=b,file=<fileName> <java PID>
You can pass below JVM arguments to your application:
-XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=
This argument will automatically trigger heap dump in the specified 'file-path' when your application experiences OutOfMemoryError. There are 7 different options to take heap dumps from your application:
jmap
-XX:+HeapDumpOnOutOfMemoryError
jcmd
JVisualVM
JMX
Programmatic Approach
Administrative consoles
Details about each option can be found in this article. Once you have captured heap dump, you may use tools like Eclipse Memory Analysis tool, HeapHero to analyze the captured heap dumps.
I checked with following code in my servlet:
int mb = 1024 * 1024;
Runtime runtime = Runtime.getRuntime();
out.write("Used Memory:" + (runtime.totalMemory() - runtime.freeMemory()) / mb);
out.write("Free Memory:" + runtime.freeMemory() / mb);
out.write("Total Memory:" + runtime.totalMemory() / mb);
out.write("Max Memory:" + runtime.maxMemory() / mb);
the output is :
Used Memory:10
Free Memory:46
Total Memory:57
Max Memory:57
I want my app not to use more than 64 MB heap? I want to know - is there any way my app can use more then 64 MB heap...(Max Memory:57) ? ..will my app throw an OutOfMemoryException after 57MB?
Default Max Heap size is 64Mo, the only way to get more is to set the max size with this parameter :
-Xmx256m
While this parameter set the start value :
-Xms128m
Don't forget the "m" at the end which means Megabytes, don't give more start memory than max neither.
Furthermore, there is no setMaxHeapSize() function if it's what you are looking for.
If you are runnning your servlet inside a tomcat you should try with this :
export CATALINA_OPTS=-Xms16m -Xmx256m;
in startup.bat
If your servlet need more than JVM can allow, you will get weird errors when reaching the limit and most of the time a OutOfMemoryException, the Garbage Collector will try to avoid that though so it will crawl a bit before throwing it.
When you run your application you must also specify the max heap size.
For example if your class name is HelloWorld and if you want to set 512mb the heap size then you have to launch te following command:
java -Xmx512m HelloWorld