...
In contrast with C and C++, Java does not flush unwritten buffered data or close open files when it exits, so programs must do this manually.
Noncompliant Code Example
This example creates a new file, outputs some text to it, and abruptly exits using Runtime.exit()
. Consequently, the file is closed without the text actually being written to it.
Code Block | ||
---|---|---|
| ||
public class CreateFile {
public static void main(String[] args) throws FileNotFoundException {
final PrintStream out = new PrintStream( new BufferedOutputStream(
new FileOutputStream("foo.txt")));
out.println("hello");
Runtime.getRuntime().exit(1);
}
}
|
Compliant Solution (OutputStream.close()
)
This solution explicitly closes the file before exiting
Code Block | ||
---|---|---|
| ||
public class CreateFile {
public static void main(String[] args) throws FileNotFoundException {
final PrintStream out = new PrintStream( new BufferedOutputStream(
new FileOutputStream("foo.txt")));
out.println("hello");
out.close();
Runtime.getRuntime().exit(1);
}
}
|
Compliant Solution (Shutdown Hook)
This compliant solution adds a shutdown hook to close the file. This hook is invoked by Runtime.exit()
is called before the JVM is halted.
Code Block | ||
---|---|---|
| ||
public class CreateFile {
public static void main(String[] args) throws FileNotFoundException {
final PrintStream out = new PrintStream( new BufferedOutputStream(
new FileOutputStream("foo.txt")));
Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
public void run() {
out.close();
}
}));
out.println("hello");
Runtime.getRuntime().exit(1);
}
}
|
Noncompliant Code Example (Runtime.halt()
)
This noncompliant code example calls Runtime.halt()
instead of Runtime.exit()
. Runtime.halt()
stops the JVM without invoking any shutdown hooks; consequently the file is not properly written to or closed.
Code Block | ||
---|---|---|
| ||
public class CreateFile {
public static void main(String[] args) throws FileNotFoundException {
final PrintStream out = new PrintStream( new BufferedOutputStream(
new FileOutputStream("foo.txt")));
Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
public void run() {
out.close();
}
}));
out.println("hello");
Runtime.getRuntime().halt(1);
}
}
|
Risk Assessment
Using Runtime.halt()
in place of Runtime.exit()
may not perform necessary cleanup, potentially leaving sensitive data exposed or leaving data in an inconsistent state.
...