0

Is there any way I could find out available or free ram in machine using Java ?

Need this detail so that I could launch my JVM accordingly.

Maria
  • 452
  • 1
  • 6
  • 20
  • [Not really](https://stackoverflow.com/questions/25552/get-os-level-system-information). You could try with some OS-specific way (like reading the output of `free` on linux). – Federico klez Culloca May 14 '20 at 11:05
  • @FedericoklezCulloca, Lets say my JVM Max size for program is 2 GB. Any way I could check before hand that my JVM would be able to use atleast 2GB from available memory in machine ? If its not available, I'll not launch my JVM – Maria May 14 '20 at 11:15
  • IMHO, just lunch the JVM and make it handle the lack of memory. – Federico klez Culloca May 14 '20 at 11:17
  • But wouldn't be a dangerous ? – Maria May 14 '20 at 11:18
  • take a look at this question https://stackoverflow.com/questions/3571203/what-are-runtime-getruntime-totalmemory-and-freememory – Boris Chistov May 14 '20 at 11:40
  • 1
    There is a contradiction in our question. Getting the available RAM “using Java” doesn’t help when you want that number to “launch my JVM accordingly”. – Holger May 25 '20 at 09:46
  • @Holger, Please elaborate, how it contradicts ? JVM would lanch in RAM itself, No ? – Maria May 26 '20 at 06:13
  • 1
    To get the available RAM “using Java”, i.e. executing Java code, you need an already running JVM, which contradicts the purpose to specify these number *before* the JVM runs. When “JVM would launch in RAM itself” means to have two JVMs, well, that could work but surely is neither, simple nor efficient. – Holger May 26 '20 at 07:05
  • 1
    Anyway, it’s possible but the solution depends on the Java version. Which version do you use? – Holger May 26 '20 at 07:08
  • @Holger, 1.8 java version – Maria May 26 '20 at 07:21

1 Answers1

2

There is an API allowing to get the numbers, but it’s not part of the official API in Java 8 and depends on an optional module, jdk.management, in JDK 11.

You can use dynamic access to avoid direct code dependencies to unofficial APIs. In the common implementations, i.e. OpenJDK and Oracle’s JDK distribution, it will be available:

import java.lang.management.ManagementFactory;
import javax.management.*;

public class Memory {
    public static void main(String[] args) throws JMException {
        MBeanServer mBeanServer = ManagementFactory.getPlatformMBeanServer();
        ObjectName objectName = new ObjectName("java.lang:type=OperatingSystem");

        Long free = (Long)mBeanServer.getAttribute(objectName, "FreePhysicalMemorySize");
        Long total= (Long)mBeanServer.getAttribute(objectName, "TotalPhysicalMemorySize");

        final double gb = 0x1p-30;

        System.out.printf("%.2f GB of %.2f GB free%n", free * gb, total * gb);

        total = (Long)mBeanServer.getAttribute(objectName, "TotalSwapSpaceSize");
        free  = (Long)mBeanServer.getAttribute(objectName, "FreeSwapSpaceSize");

        System.out.printf("%.2f GB of %.2f GB swap free%n", free * gb, total * gb);
    }
}
Holger
  • 285,553
  • 42
  • 434
  • 765
  • Is it static ? "java.lang:type=OperatingSystem" – Maria May 26 '20 at 10:06
  • 1
    It’s [this constant](https://docs.oracle.com/javase/8/docs/api/constant-values.html#java.lang.management.ManagementFactory.OPERATING_SYSTEM_MXBEAN_NAME). When I wrote the answer, it just slipped my mind that these strings also have corresponding named constants you can use. So instead of `"java.lang:type=OperatingSystem"`, you can also write `ManagementFactory.OPERATING_SYSTEM_MXBEAN_NAME`. – Holger May 26 '20 at 10:30
  • Is it a good practice using linux command free -h to get free ram using java code ? In case of Initialising JVM in linux. – Maria May 26 '20 at 11:02
  • 1
    That would be more of an [operating system question](https://superuser.com/tour)… – Holger May 26 '20 at 16:39