JDK-8231451 : ZipFileInputStream.skip does not handle negative values correctly
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.util.jar
  • Affected Version: 11,13,14
  • Priority: P4
  • Status: Resolved
  • Resolution: Fixed
  • OS: windows_10
  • CPU: x86_64
  • Submitted: 2019-09-23
  • Updated: 2019-11-13
  • Resolved: 2019-10-30
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 14
14 b22Fixed
Related Reports
Relates :  
Sub Tasks
JDK-8232384 :  
Description
A DESCRIPTION OF THE PROBLEM :
When ZipFile.getInputStream is called for a STORED entry, a ZipFile$ZipFileInputStream is returned. The method skip(long) of this class is not correctly handling negative values.

All (?) other implementations of InputStream either return 0 when the skip amount is <= 0, or throw an exception. However, ZipFileInputStream simply accepts the negative value, possibly even returning it as number of skipped bytes.

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Run the provided code

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
Either "0" is printed as skipped amount or an exception is thrown
ACTUAL -
"-100" is printed as number of skipped bytes

---------- BEGIN SOURCE ----------
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.UncheckedIOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.zip.CRC32;
import java.util.zip.ZipEntry;
import java.util.zip.ZipFile;
import java.util.zip.ZipOutputStream;

public class ZipFileInputStreamTest {
    public static void main(String[] args) throws IOException {
        Path tempFile = Files.createTempFile("zip-test", ".zip");
        try {
            Files.write(tempFile, createZipFileData());
            
            try (ZipFile zipFile = new ZipFile(tempFile.toFile())) {
                ZipEntry entry = zipFile.entries().nextElement();
                InputStream entryIn = zipFile.getInputStream(entry);
                
                long skipped = entryIn.skip(-100);
                System.out.println("Skipped: " + skipped);
            }
        }
        finally {
            Files.delete(tempFile);
        }
    }
    
    private static byte[] createZipFileData() {
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        ZipOutputStream zipOut = new ZipOutputStream(out);
        
        try {
            // STORED has to be used, DEFLATED would wrap stream inside ZipFileInflaterInputStream 
            // which prevents negative skip amounts
            zipOut.setMethod(ZipEntry.STORED);
            
            ZipEntry zipEntry = new ZipEntry("test");
            
            byte[] data = new byte[] {'t', 'e', 's', 't'};
            zipEntry.setSize(data.length);
            
            CRC32 crc32 = new CRC32();
            crc32.update(data);
            zipEntry.setCrc(crc32.getValue());
            
            zipOut.putNextEntry(zipEntry);
            zipOut.write(data);
            zipOut.finish();
        }
        catch (IOException ioException) {
            throw new UncheckedIOException(ioException);
        }
        
        return out.toByteArray();
    }
}
---------- END SOURCE ----------


Comments
URL: https://hg.openjdk.java.net/jdk/jdk/rev/fba8635290df User: lancea Date: 2019-10-30 19:55:32 +0000
30-10-2019

To reproduce the issue, run the attached test case: JDK 11.0.4 - Fail JDK 13 - Fail JDK 14-ea - Fail Output: Skipped: -100
25-09-2019