Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit cef48e95 authored by Treehugger Robot's avatar Treehugger Robot Committed by Gerrit Code Review
Browse files

Merge "Support writing a ZIP64 file header"

parents 4eb50485 373147ba
Loading
Loading
Loading
Loading
+66 −0
Original line number Diff line number Diff line
@@ -74,3 +74,69 @@ func TestStripZip64Extras(t *testing.T) {
		}
	}
}

func TestCopyFromZip64(t *testing.T) {
	if testing.Short() {
		t.Skip("slow test; skipping")
	}

	const size = uint32max + 1
	fromZipBytes := &bytes.Buffer{}
	fromZip := NewWriter(fromZipBytes)
	w, err := fromZip.CreateHeaderAndroid(&FileHeader{
		Name:               "large",
		Method:             Store,
		UncompressedSize64: size,
		CompressedSize64:   size,
	})
	if err != nil {
		t.Fatalf("Create: %v", err)
	}
	_, err = w.Write(make([]byte, size))
	if err != nil {
		t.Fatalf("Write: %v", err)
	}
	err = fromZip.Close()
	if err != nil {
		t.Fatalf("Close: %v", err)
	}
	fromZip = nil

	fromZipReader, err := NewReader(bytes.NewReader(fromZipBytes.Bytes()), int64(fromZipBytes.Len()))
	if err != nil {
		t.Fatalf("NewReader: %v", err)
	}

	toZipBytes := &bytes.Buffer{}
	toZip := NewWriter(toZipBytes)
	err = toZip.CopyFrom(fromZipReader.File[0], fromZipReader.File[0].Name)
	if err != nil {
		t.Fatalf("CopyFrom: %v", err)
	}

	err = toZip.Close()
	if err != nil {
		t.Fatalf("Close: %v", err)
	}

	// Save some memory
	fromZipReader = nil
	fromZipBytes.Reset()

	toZipReader, err := NewReader(bytes.NewReader(toZipBytes.Bytes()), int64(toZipBytes.Len()))
	if err != nil {
		t.Fatalf("NewReader: %v", err)
	}

	if len(toZipReader.File) != 1 {
		t.Fatalf("Expected 1 file in toZip, got %d", len(toZipReader.File))
	}

	if g, w := toZipReader.File[0].CompressedSize64, uint64(size); g != w {
		t.Errorf("Expected CompressedSize64 %d, got %d", w, g)
	}

	if g, w := toZipReader.File[0].UncompressedSize64, uint64(size); g != w {
		t.Errorf("Expected UnompressedSize64 %d, got %d", w, g)
	}
}
+15 −3
Original line number Diff line number Diff line
@@ -276,9 +276,6 @@ func writeHeader(w io.Writer, h *FileHeader) error {
	} else {
		b.uint32(h.CRC32)

		if h.CompressedSize64 > uint32max || h.UncompressedSize64 > uint32max {
			panic("skipping writing the data descriptor for a 64-bit value is not yet supported")
		}
		compressedSize := uint32(h.CompressedSize64)
		if compressedSize == 0 {
			compressedSize = h.CompressedSize
@@ -289,6 +286,21 @@ func writeHeader(w io.Writer, h *FileHeader) error {
			uncompressedSize = h.UncompressedSize
		}

		if h.CompressedSize64 > uint32max || h.UncompressedSize64 > uint32max {
			// Sizes don't fit in a 32-bit field, put them in a zip64 extra instead.
			compressedSize = uint32max
			uncompressedSize = uint32max

			// append a zip64 extra block to Extra
			var buf [20]byte // 2x uint16 + 2x uint64
			eb := writeBuf(buf[:])
			eb.uint16(zip64ExtraId)
			eb.uint16(16) // size = 2x uint64
			eb.uint64(h.UncompressedSize64)
			eb.uint64(h.CompressedSize64)
			h.Extra = append(h.Extra, buf[:]...)
		}

		b.uint32(compressedSize)
		b.uint32(uncompressedSize)
	}