FULL PRODUCT VERSION :
java version "1.8.0_45"
Java(TM) SE Runtime Environment (build 1.8.0_45-b14)
Java HotSpot(TM) 64-Bit Server VM (build 25.45-b02, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Linux <host> 3.2.45-0.6.acc.624.45.283.amzn1acc.x86_64 #1 SMP Fri Nov 21 22:39:25 UTC 2014 x86_64 x86_64 x86_64 GNU/Linux
A DESCRIPTION OF THE PROBLEM :
When writing to a file and a disk full condition occurs, the file is not properly closed and the handle is leaked even though a try-with-resources is used.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
use Files.newBufferedWriter() in a try with resources construct. Write until disk full. Check to see if file has been properly closed by checking open files.
You can check open files on Linux like this:
sudo lsof -a +L1 /
(grep for the filename)
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
File should not be open, because the try with resources construct should have closed the file.
ACTUAL -
File remains open as reported by: sudo lsof -a +L1 /
ERROR MESSAGES/STACK TRACES THAT OCCUR :
This exception is generated:
java.io.IOException: No space left on device
at sun.nio.ch.FileDispatcherImpl.write0(Native Method)
at sun.nio.ch.FileDispatcherImpl.write(FileDispatcherImpl.java:60)
at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:93)
at sun.nio.ch.IOUtil.write(IOUtil.java:65)
at sun.nio.ch.FileChannelImpl.write(FileChannelImpl.java:210)
at java.nio.channels.Channels.writeFullyImpl(Channels.java:78)
at java.nio.channels.Channels.writeFully(Channels.java:101)
at java.nio.channels.Channels.access$000(Channels.java:61)
at java.nio.channels.Channels$1.write(Channels.java:174)
at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
at sun.nio.cs.StreamEncoder.implWrite(StreamEncoder.java:282)
at sun.nio.cs.StreamEncoder.write(StreamEncoder.java:125)
at java.io.OutputStreamWriter.write(OutputStreamWriter.java:207)
at java.io.BufferedWriter.flushBuffer(BufferedWriter.java:129)
at java.io.BufferedWriter.write(BufferedWriter.java:230)
at java.io.Writer.write(Writer.java:157)
[... snip application level info ...]
Suppressed: java.io.IOException: No space left on device
at sun.nio.ch.FileDispatcherImpl.write0(Native Method)
at sun.nio.ch.FileDispatcherImpl.write(FileDispatcherImpl.java:60)
at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:93)
at sun.nio.ch.IOUtil.write(IOUtil.java:65)
at sun.nio.ch.FileChannelImpl.write(FileChannelImpl.java:210)
at java.nio.channels.Channels.writeFullyImpl(Channels.java:78)
at java.nio.channels.Channels.writeFully(Channels.java:101)
at java.nio.channels.Channels.access$000(Channels.java:61)
at java.nio.channels.Channels$1.write(Channels.java:174)
at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
at sun.nio.cs.StreamEncoder.implClose(StreamEncoder.java:316)
at sun.nio.cs.StreamEncoder.close(StreamEncoder.java:149)
at java.io.OutputStreamWriter.close(OutputStreamWriter.java:233)
at java.io.BufferedWriter.close(BufferedWriter.java:266)
[... snip application level info ...]
... 4 more
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
Run this junit test. Set the path to a disk with limited space to save time. When disk is full, the IOException will be printed. Then, while the test continues to sleep, before termination, check for open files.
-----------------------------------
import java.io.BufferedWriter;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.junit.Test;
public class DiskFullTest {
@Test
public void diskFullTest() throws IOException, InterruptedException {
StringBuffer text = new StringBuffer();
for (int i = 0; i < 10000; i++) {
text.append("HelloWorld! ");
}
String bigString = text.toString();
Path tempFile = Files.createTempFile(Paths.get("/tmp"), "diskFullTest", null);
try (BufferedWriter writer = Files.newBufferedWriter(tempFile, StandardCharsets.UTF_8)) {
while (true) {
writer.write(bigString);
writer.newLine();
}
} catch (IOException e) {
System.out.println("Exception: " + e);
}
// Sleep while I check file handles
Thread.sleep(30000);
// Of course file handles are released when the JVM exits
}
}
---------- END SOURCE ----------
CUSTOMER SUBMITTED WORKAROUND :
No workaround known.
java version "1.8.0_45"
Java(TM) SE Runtime Environment (build 1.8.0_45-b14)
Java HotSpot(TM) 64-Bit Server VM (build 25.45-b02, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Linux <host> 3.2.45-0.6.acc.624.45.283.amzn1acc.x86_64 #1 SMP Fri Nov 21 22:39:25 UTC 2014 x86_64 x86_64 x86_64 GNU/Linux
A DESCRIPTION OF THE PROBLEM :
When writing to a file and a disk full condition occurs, the file is not properly closed and the handle is leaked even though a try-with-resources is used.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
use Files.newBufferedWriter() in a try with resources construct. Write until disk full. Check to see if file has been properly closed by checking open files.
You can check open files on Linux like this:
sudo lsof -a +L1 /
(grep for the filename)
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
File should not be open, because the try with resources construct should have closed the file.
ACTUAL -
File remains open as reported by: sudo lsof -a +L1 /
ERROR MESSAGES/STACK TRACES THAT OCCUR :
This exception is generated:
java.io.IOException: No space left on device
at sun.nio.ch.FileDispatcherImpl.write0(Native Method)
at sun.nio.ch.FileDispatcherImpl.write(FileDispatcherImpl.java:60)
at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:93)
at sun.nio.ch.IOUtil.write(IOUtil.java:65)
at sun.nio.ch.FileChannelImpl.write(FileChannelImpl.java:210)
at java.nio.channels.Channels.writeFullyImpl(Channels.java:78)
at java.nio.channels.Channels.writeFully(Channels.java:101)
at java.nio.channels.Channels.access$000(Channels.java:61)
at java.nio.channels.Channels$1.write(Channels.java:174)
at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
at sun.nio.cs.StreamEncoder.implWrite(StreamEncoder.java:282)
at sun.nio.cs.StreamEncoder.write(StreamEncoder.java:125)
at java.io.OutputStreamWriter.write(OutputStreamWriter.java:207)
at java.io.BufferedWriter.flushBuffer(BufferedWriter.java:129)
at java.io.BufferedWriter.write(BufferedWriter.java:230)
at java.io.Writer.write(Writer.java:157)
[... snip application level info ...]
Suppressed: java.io.IOException: No space left on device
at sun.nio.ch.FileDispatcherImpl.write0(Native Method)
at sun.nio.ch.FileDispatcherImpl.write(FileDispatcherImpl.java:60)
at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:93)
at sun.nio.ch.IOUtil.write(IOUtil.java:65)
at sun.nio.ch.FileChannelImpl.write(FileChannelImpl.java:210)
at java.nio.channels.Channels.writeFullyImpl(Channels.java:78)
at java.nio.channels.Channels.writeFully(Channels.java:101)
at java.nio.channels.Channels.access$000(Channels.java:61)
at java.nio.channels.Channels$1.write(Channels.java:174)
at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
at sun.nio.cs.StreamEncoder.implClose(StreamEncoder.java:316)
at sun.nio.cs.StreamEncoder.close(StreamEncoder.java:149)
at java.io.OutputStreamWriter.close(OutputStreamWriter.java:233)
at java.io.BufferedWriter.close(BufferedWriter.java:266)
[... snip application level info ...]
... 4 more
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
Run this junit test. Set the path to a disk with limited space to save time. When disk is full, the IOException will be printed. Then, while the test continues to sleep, before termination, check for open files.
-----------------------------------
import java.io.BufferedWriter;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.junit.Test;
public class DiskFullTest {
@Test
public void diskFullTest() throws IOException, InterruptedException {
StringBuffer text = new StringBuffer();
for (int i = 0; i < 10000; i++) {
text.append("HelloWorld! ");
}
String bigString = text.toString();
Path tempFile = Files.createTempFile(Paths.get("/tmp"), "diskFullTest", null);
try (BufferedWriter writer = Files.newBufferedWriter(tempFile, StandardCharsets.UTF_8)) {
while (true) {
writer.write(bigString);
writer.newLine();
}
} catch (IOException e) {
System.out.println("Exception: " + e);
}
// Sleep while I check file handles
Thread.sleep(30000);
// Of course file handles are released when the JVM exits
}
}
---------- END SOURCE ----------
CUSTOMER SUBMITTED WORKAROUND :
No workaround known.
- relates to
-
JDK-8147534 ObjectInputStream does not reliably close the underlying stream
- Closed