private void readCentralDirectoryEntry()

in src/main/java/org/apache/commons/compress/archivers/zip/ZipFile.java [1475:1587]


    private void readCentralDirectoryEntry(final Map<ZipArchiveEntry, NameAndComment> noUTF8Flag) throws IOException {
        cfhBbuf.rewind();
        IOUtils.readFully(archive, cfhBbuf);
        int off = 0;
        final Entry ze = new Entry();

        final int versionMadeBy = ZipShort.getValue(cfhBuf, off);
        off += ZipConstants.SHORT;
        ze.setVersionMadeBy(versionMadeBy);
        ze.setPlatform(toPlatform(versionMadeBy));

        ze.setVersionRequired(ZipShort.getValue(cfhBuf, off));
        off += ZipConstants.SHORT; // version required

        final GeneralPurposeBit gpFlag = GeneralPurposeBit.parse(cfhBuf, off);
        final boolean hasUTF8Flag = gpFlag.usesUTF8ForNames();
        final ZipEncoding entryEncoding = hasUTF8Flag ? ZipEncodingHelper.ZIP_ENCODING_UTF_8 : zipEncoding;
        if (hasUTF8Flag) {
            ze.setNameSource(ZipArchiveEntry.NameSource.NAME_WITH_EFS_FLAG);
        }
        ze.setGeneralPurposeBit(gpFlag);
        ze.setRawFlag(ZipShort.getValue(cfhBuf, off));

        off += ZipConstants.SHORT;

        // noinspection MagicConstant
        ze.setMethod(ZipShort.getValue(cfhBuf, off));
        off += ZipConstants.SHORT;

        final long time = ZipUtil.dosToJavaTime(ZipLong.getValue(cfhBuf, off));
        ze.setTime(time);
        off += ZipConstants.WORD;

        ze.setCrc(ZipLong.getValue(cfhBuf, off));
        off += ZipConstants.WORD;

        long size = ZipLong.getValue(cfhBuf, off);
        if (size < 0) {
            throw new IOException("broken archive, entry with negative compressed size");
        }
        ze.setCompressedSize(size);
        off += ZipConstants.WORD;

        size = ZipLong.getValue(cfhBuf, off);
        if (size < 0) {
            throw new IOException("broken archive, entry with negative size");
        }
        ze.setSize(size);
        off += ZipConstants.WORD;

        final int fileNameLen = ZipShort.getValue(cfhBuf, off);
        off += ZipConstants.SHORT;
        if (fileNameLen < 0) {
            throw new IOException("broken archive, entry with negative fileNameLen");
        }

        final int extraLen = ZipShort.getValue(cfhBuf, off);
        off += ZipConstants.SHORT;
        if (extraLen < 0) {
            throw new IOException("broken archive, entry with negative extraLen");
        }

        final int commentLen = ZipShort.getValue(cfhBuf, off);
        off += ZipConstants.SHORT;
        if (commentLen < 0) {
            throw new IOException("broken archive, entry with negative commentLen");
        }

        ze.setDiskNumberStart(ZipShort.getValue(cfhBuf, off));
        off += ZipConstants.SHORT;

        ze.setInternalAttributes(ZipShort.getValue(cfhBuf, off));
        off += ZipConstants.SHORT;

        ze.setExternalAttributes(ZipLong.getValue(cfhBuf, off));
        off += ZipConstants.WORD;

        final byte[] fileName = IOUtils.readRange(archive, fileNameLen);
        if (fileName.length < fileNameLen) {
            throw new EOFException();
        }
        ze.setName(entryEncoding.decode(fileName), fileName);

        // LFH offset,
        ze.setLocalHeaderOffset(ZipLong.getValue(cfhBuf, off) + firstLocalFileHeaderOffset);
        // data offset will be filled later
        entries.add(ze);

        final byte[] cdExtraData = IOUtils.readRange(archive, extraLen);
        if (cdExtraData.length < extraLen) {
            throw new EOFException();
        }
        try {
            ze.setCentralDirectoryExtra(cdExtraData);
        } catch (final RuntimeException e) {
            throw ZipUtil.newZipException("Invalid extra data in entry " + ze.getName(), e);
        }

        setSizesAndOffsetFromZip64Extra(ze);
        sanityCheckLFHOffset(ze);

        final byte[] comment = IOUtils.readRange(archive, commentLen);
        if (comment.length < commentLen) {
            throw new EOFException();
        }
        ze.setComment(entryEncoding.decode(comment));

        if (!hasUTF8Flag && useUnicodeExtraFields) {
            noUTF8Flag.put(ze, new NameAndComment(fileName, comment));
        }

        ze.setStreamContiguous(true);
    }