Что происходит, когда недостаточно памяти для выдачи OutOfMemoryError?

Я знаю, что каждый объект требует памяти кучи, а каждый примитив / ссылка в стеке требует памяти стека.

Когда я пытаюсь создать объект в куче, а памяти для этого недостаточно, JVM создает ошибку java.lang.OutOfMemoryError в куче и передает ее мне.

Таким образом, неявно это означает, что JVM зарезервировала некоторую память при запуске.

Что происходит, когда эта зарезервированная память израсходована (она определенно будет израсходована, читайте обсуждение ниже) и JVM не имеет достаточно памяти в куче для создания экземпляра java.lang.OutOfMemoryError ?

Просто зависает? Или он выдаст мне ноль , поскольку нет памяти для нового экземпляра OOM?

try {
    Object o = new Object();
    // and operations which require memory (well.. that's like everything)
} catch (java.lang.OutOfMemoryError e) {
    // JVM had insufficient memory to create an instance of java.lang.OutOfMemoryError to throw to us
    // what next? hangs here, stuck forever?
    // or would the machine decide to throw us a "null" ? (since it doesn't have memory to throw us anything more useful than a null)
    e.printStackTrace(); // e.printStackTrace() requires memory too.. =X
}

==

Почему JVM не может зарезервировать достаточно памяти?

Независимо от того, сколько памяти зарезервировано, эта память все еще может быть использована, если JVM не имеет способа «вернуть» эту память:

try {
    Object o = new Object();
} catch (java.lang.OutOfMemoryError e) {
    // JVM had 100 units of "spare memory". 1 is used to create this OOM.
    try {
        e.printStackTrace();
    } catch (java.lang.OutOfMemoryError e2) {
        // JVM had 99 units of "spare memory". 1 is used to create this OOM.
        try {
            e.printStackTrace();
        } catch (java.lang.OutOfMemoryError e3) {
            // JVM had 98 units of "spare memory". 1 is used to create this OOM.
            try {
                e.printStackTrace();
            } catch (java.lang.OutOfMemoryError e4) {
                // JVM had 97 units of "spare memory". 1 is used to create this OOM.
                try {
                    e.printStackTrace();
                } catch (java.lang.OutOfMemoryError e5) {
                    // JVM had 96 units of "spare memory". 1 is used to create this OOM.
                    try {
                        e.printStackTrace();
                    } catch (java.lang.OutOfMemoryError e6) {
                        // JVM had 95 units of "spare memory". 1 is used to create this OOM.
                        e.printStackTrace();
                        //........the JVM can't have infinite reserved memory, he's going to run out in the end
                    }
                }
            }
        }
    }
}

Или более кратко:

private void OnOOM(java.lang.OutOfMemoryError e) {
    try {
        e.printStackTrace();
    } catch (java.lang.OutOfMemoryError e2) {
        OnOOM(e2);
    }
}

206
задан Keith Pinson 13 February 2012 в 05:25
поделиться