2011-12-21 45 views
8

Tôi đang cố tìm vị trí của tiêu đề tệp Thư mục Trung tâm đầu tiên trong tệp Zip.Cách tìm vị trí của Thư mục Trung tâm trong một tệp Zip?

tôi đang đọc những: http://en.wikipedia.org/wiki/Zip_(file_format) http://www.pkware.com/documents/casestudies/APPNOTE.TXT

Như tôi đã nhìn thấy nó, tôi chỉ có thể quét qua các dữ liệu Zip, xác định bởi các tiêu đề những loại phần tôi đang ở, và sau đó làm điều đó cho đến khi Tôi nhấn tiêu đề Thư mục Trung tâm. Tôi rõ ràng sẽ đọc các Header tập tin trước đó và sử dụng "kích thước nén" để bỏ qua các dữ liệu thực tế, và không cho vòng lặp ... Read More đã biết tất cả các tập tin và thư mục bên trong tệp Zip trong trường hợp này tôi không thấy sử dụng nhiều cho Thư mục Trung tâm nữa.

Để hiểu biết của tôi, mục đích của Thư mục trung tâm là liệt kê siêu dữ liệu tệp và vị trí của dữ liệu thực trong tệp Zip để bạn không cần phải quét toàn bộ tệp?

Sau khi đọc về End Of kỷ lục Trung Directory, Wikipedia nói:

đặt hàng này cho phép một tập tin zip được tạo ra trong một vượt qua, nhưng nó là thường giải nén bằng cách đầu tiên đọc thư Trung ương tại kết thúc.

Tôi làm cách nào để tìm bản ghi Kết thúc thư mục trung tâm một cách dễ dàng? Chúng ta cần phải nhớ rằng nó có thể có một bình luận có kích thước tùy ý ở đó, vì vậy tôi có thể không biết có bao nhiêu byte từ cuối luồng dữ liệu mà nó nằm ở đó. Tôi chỉ quét nó?

P.S. Tôi đang viết một trình đọc tệp Zip.

+0

Bạn không thể bắt đầu quét ngược từ đầu (thư mục ZIP nằm ở cuối tệp)? –

+1

Vâng tôi có thể, nhưng đây thực sự là cách bạn phải làm điều này?Quét ngược lại để tìm End of Central Directory là một khả năng, nhưng xem xét thực tế là nó có một trường nhận xét có kích thước biến có kích thước 16 bit, bạn có thể có khoảng 65k nhận xét mà bạn cần đọc/quét, và nếu nhận xét chứa số ma thuật mà quá trình quét của bạn sẽ thất bại. – Tower

+0

nhận xét luôn trống rỗng nhất và 64K là gì? –

Trả lời

1

Tôi đã kết thúc lặp qua các byte bắt đầu từ cuối. Vòng lặp dừng lại nếu nó tìm thấy một chuỗi byte phù hợp, chỉ mục dưới 0 hoặc nếu nó đã đi qua 64k byte.

+0

Bạn đã tìm thấy giải pháp? Thư mục Trung ương trông như thế nào? Tôi có một tệp được mã hóa base64. –

8

Bắt đầu từ đầu và quét về phía đầu, tìm phần cuối của chữ ký thư mục và đếm số byte bạn đã quét. Khi bạn tìm thấy một ứng cử viên, hãy lấy độ lệch byte 20 cho chiều dài chú thích (L). Kiểm tra xem L + 20 có khớp với số lượng hiện tại của bạn hay không. Sau đó kiểm tra xem sự khởi đầu của thư mục trung tâm (được chỉ ra bởi bù đắp byte 12) có chữ ký thích hợp hay không.

Nếu bạn giả định các bit khá ngẫu nhiên khi kiểm tra chữ ký xảy ra là phỏng đoán hoang dã (ví dụ: đoán đích vào phân đoạn dữ liệu), xác suất nhận được tất cả các bit chữ ký chính xác là khá thấp. Bạn có thể tinh chỉnh điều này và tìm ra cơ hội hạ cánh trong một phân đoạn dữ liệu và cơ hội đánh một tiêu đề hợp pháp (như một hàm số của các tiêu đề như vậy), nhưng điều này nghe có vẻ giống như một khả năng thấp với tôi. Bạn có thể tăng mức độ tin cậy của bạn bằng cách kiểm tra chữ ký của hồ sơ tệp đầu tiên được liệt kê, nhưng hãy đảm bảo xử lý trường hợp biên của một tệp zip trống.

+1

Cảm ơn câu trả lời này Derek, thực sự đánh giá cao nó –

+0

Nó cũng nên được đề cập là tốt nhất để bắt đầu tại vị trí 'endOfFile - 22', vì kết thúc thực sự của signatue thư mục trung tâm không thể xảy ra sau vị trí này. Đối với các bản lưu trữ có nhận xét trống, điều này sẽ tìm chữ ký trên lần lặp đầu tiên. – Mark

+0

Tôi đã kiểm tra tại endOfFile -22, nếu thất bại thì hãy thử endOfFile - 64k - 22 và lặp lại cho đến khi endOfFile -22 áp dụng kiểm tra heuristical này bất cứ lúc nào tôi thấy chữ ký. Mã ở đây cho những người tò mò: https://github.com/paulsapps/msgi/blob/840857346a84efc0b29ae00edb0b693b805ae4f1/Source/MgsLib/Fs.cpp#L323 – paulm

1

Chỉ cần vượt qua các ngón tay của bạn và hy vọng rằng không có mục nhập với CRC, dấu thời gian hoặc dấu thời gian là 06054B50 hoặc bất kỳ chuỗi bốn byte nào khác xảy ra là 06054B50.

+3

Tôi thực sự không nghĩ rằng điều này thêm bất cứ điều gì khủng khiếp xây dựng cho câu hỏi này. Có thể đã được thêm tốt hơn chỉ là một bình luận. –

Các vấn đề liên quan