Closed pnrobinson closed 6 years ago
Can we catch the OutOfMemoryError
and display a proper error message? On my test machine even with very simple queries, without the -Xmx
option, GOPHER immediately runs out of memory and continues to display the Creating viewpoints using ...
dialog.
It would also be possible I think to have GOPHER detect its heap size and/or try to relaunch itself with a larger heap size...
Alternatively, we could ship GOPHER with Run_GOPHER_Unix.sh
and Run_GOPHER_Win.bat
scripts (similar to FABIAN) that detect if Java 8 is installed and launch GopherGui-0.5.0.jar
with an appropriate heap option.
I have been trying to put the viewpoint creation thread in a try catch block with this
} catch (OutOfMemoryError ooem) {
MemoryMXBean memoryBean = ManagementFactory.getMemoryMXBean();
MemoryUsage heapMemory = memoryBean.getHeapMemoryUsage();
MemoryUsage nonHeapMemory = memoryBean.getNonHeapMemoryUsage();
String format = "%-15s%-15s%-15s%-15s";
StringBuilder sb = new StringBuilder();
sb.append(String.format(format, "COMMITTED", "INIT", "USED", "MAX")).append("\n");
sb.append(String.format(format,
NumberFormat.getInstance().format(heapMemory.getCommitted()),
NumberFormat.getInstance().format(heapMemory.getInit()),
NumberFormat.getInstance().format(heapMemory.getUsed()),
NumberFormat.getInstance().format(heapMemory.getMax()))).append("\n");
sb.append("NON-HEAP MEMORY").append("\n");
sb.append(String.format(format, "COMMITTED", "INIT", "USED", "MAX")).append("\n");
sb.append(String.format(format,
NumberFormat.getInstance().format(heapMemory.getCommitted()),
NumberFormat.getInstance().format(heapMemory.getInit()),
NumberFormat.getInstance().format(heapMemory.getUsed()),
NumberFormat.getInstance().format(heapMemory.getMax()))).append("\n");
ooem.printStackTrace();
System.err.println(sb.toString());
}
but it is not possible to cast an OutOfMemoryError to an Exception (for good reasons). It might be possible to have GOPHER check the alloted memory with getCommitted() and to issue a warning if it is not enough (before the user tries to run createViewpoints -- everything else does not require that much memory).
@steinha @hansenp I am having some difficulty catching the Error when I deliberately run Gopher with low memory. I have adding this to GopherMainPresenter (line 1199)
task.setOnFailed(eh -> {
if (eh.getSource() instanceof OutOfMemoryError) {
PopupFactory.displayMessage("Error",
"Out of memory error--see online documentation for how to increase memory"
);
return;
} else {
Exception exc = (Exception) eh.getSource().getException();
PopupFactory.displayException("Error",
"Exception encountered while attempting to create viewpoints",
exc);
}
});
But I get this:
java.lang.ClassCastException: java.lang.OutOfMemoryError cannot be cast to java.lang.Exception
Any ideas? I will return to this probably this afternoon....
An Error
is different from an Exception
in Java, which is why the cast does not work, I think.
A quick solution for OutOfMemoryError
is below. It will likely fail with other Errors (e.g., StackOverflowError
).
The Viewpoint creation
window is setAlwaysOnTop(true)
and can hide the error message. I close it before generating the message (window.close();
).
Finally, I opted for a simple Alert
message because the PopupFactory
did not work properly in this situation generating only blank messages (maybe it requires more memory):
task.setOnFailed(eh -> {
if (eh.getSource().getException() instanceof OutOfMemoryError) {
window.close();
Alert alert = new Alert(Alert.AlertType.ERROR);
alert.setTitle("Error");
alert.setHeaderText(null);
alert.setContentText("Out of memory error--see online documentation for how to increase memory");
alert.showAndWait();
return;
} else {
Exception exc = (Exception) eh.getSource().getException();
...
Thanks -- I implemented this and also added some documentation to the RTD.
@pnrobinson, FYI – This is what the error message looks like on Windows in the current commit:
Also on linux. The dialog is not showing text, but the title should be sufficient....
THis is a bit out of date, but we should add something like this to the trouble shooting page. http://pcgen.org/autobuilds/pcgen-docs/faqpages/faqoutofmemoryandjavaissues.html