From 1c57e8763bb9fea0aea2bbe98883b56c3248c9c5 Mon Sep 17 00:00:00 2001 From: Wil Mahan Date: Tue, 8 Nov 2005 19:10:39 +0000 Subject: [PATCH] re PR java/23617 (Out of memory when classpath contains jar file with zip-style comment) 2005-11-08 Wil Mahan PR java/23617 * zextract.c (read_zip_archive): Fix out of memory error when reading jar files with zip-style comments. From-SVN: r106648 --- gcc/java/ChangeLog | 6 ++++++ gcc/java/zextract.c | 21 ++++++++++++++++++++- 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/gcc/java/ChangeLog b/gcc/java/ChangeLog index bb614b5f8721..093fc8fb089f 100644 --- a/gcc/java/ChangeLog +++ b/gcc/java/ChangeLog @@ -1,3 +1,9 @@ +2005-11-08 Wil Mahan + + PR java/23617 + * zextract.c (read_zip_archive): Fix out of memory error when + reading jar files with zip-style comments. + 2005-11-07 Terry Laurenzo * gjavah.c (HANDLE_CODE_ATTRIBUTE): Only define for ELF Object diff --git a/gcc/java/zextract.c b/gcc/java/zextract.c index c10b952dcec8..461cfbd493c3 100644 --- a/gcc/java/zextract.c +++ b/gcc/java/zextract.c @@ -1,7 +1,7 @@ /* Handle a .class file embedded in a .zip archive. This extracts a member from a .zip file, but does not handle uncompression (since that is not needed for classes.zip). - Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004 + Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005 Free Software Foundation, Inc. This file is part of GCC. @@ -287,6 +287,25 @@ read_zip_archive (ZipFile *zipf) return -1; if (read (zipf->fd, buffer, ECREC_SIZE+4) != ECREC_SIZE+4) return -2; + if (buffer[0] != 'P' + || strncmp ((const char *) &buffer[1], END_CENTRAL_SIG, 3)) + { + /* We could not find the end-central-header signature, probably + because a zipfile comment is present. Scan backwards until we + find the signature. */ + if (lseek (zipf->fd, (long)(-ECREC_SIZE), SEEK_END) <= 0) + return -2; + while (buffer[0] != 'P' + || strncmp ((const char *) &buffer[1], END_CENTRAL_SIG, 3)) + { + if (lseek (zipf->fd, -5, SEEK_CUR) < 0) + return -2; + if (read (zipf->fd, buffer, 4) != 4) + return -2; + } + if (read (zipf->fd, buffer + 4, ECREC_SIZE) != ECREC_SIZE) + return -2; + } zipf->count = makeword((const uch *) &buffer[TOTAL_ENTRIES_CENTRAL_DIR]); zipf->dir_size = makelong((const uch *) &buffer[SIZE_CENTRAL_DIRECTORY]); #define ALLOC xmalloc