This is the mail archive of the
binutils@sources.redhat.com
mailing list for the binutils project.
[wip:binutils] Large corefile support
- From: Andrew Cagney <ac131313 at redhat dot com>
- To: binutils at sources dot redhat dot com
- Date: Fri, 16 Jan 2004 18:46:36 -0500
- Subject: [wip:binutils] Large corefile support
Hello,
On the i386, GDB has problems when a corefile is >2gb. The problems are
directly attributable to BFD's use of:
typedef long file_ptr;
and
fseek (FILE *stream, long int offset, int whence)
The attached, when combined with a BFD/GDB configured / built with
--enable-64-bit-bfd, lets GDB handle corefiles >2gb, per this test:
http://sources.redhat.com/ml/gdb-patches/2004-01/msg00358.html
Of note in the patch are:
- it scatters #ifdef's to handle fseek et.al. variants
Is there a better way of doing this?
- is requires --enable-64-bit-bfd
A 32-bit BFD has a 32-bit signed file_ptr (limiting SEEK_SET to files up
to 2gb). I think the only robust way of handling files larger than that
2gb is to require a 64-bit file_ptr (and hence --enable-64-bit-bfd).
- it turns out that --enable-64-bit-bfd tickles some bugs in GDB's
thread code :-/
- given a 3gb core file, 32-bit objdump isn't very helpful
objdump prints zero's instead of error for the sections contents :-(
Someone might want to look at this.
Anyway, is this "in principal" ok for BFD (assuming I can track down the
regressions :-)?
Andrew
2004-01-16 Andrew Cagney <cagney@redhat.com>
* configure.in (bfd_cv_has_long_long): Check for fseeko, ftello,
fseeko64, and ftello64.
* configure, config.in: Re-generate.
* cache.c (close_one): Use ftello or ftello64 when applicable.
* bfdio.c (bfd_tell): Ditto.
(bfd_seek) [0]: Ditto.
* cache.c (bfd_cache_lookup_worker): Use fseeko or fseeko64 when
applicable.
* bfdio.c (bfd_seek): Change type of "file_position" to
"file_ptr". Use fseeko or fseeko64 when applicable.
Index: bfdio.c
===================================================================
RCS file: /cvs/src/src/bfd/bfdio.c,v
retrieving revision 1.4
diff -u -r1.4 bfdio.c
--- bfdio.c 24 Nov 2003 18:06:39 -0000 1.4
+++ bfdio.c 16 Jan 2004 23:18:12 -0000
@@ -170,7 +170,13 @@
if ((abfd->flags & BFD_IN_MEMORY) != 0)
return abfd->where;
+#if defined HAVE_FTELLO64 && defined BFD64
+ ptr = ftello64 (bfd_cache_lookup (abfd));
+#elif defined HAVE_FTELLO && defined BFD64
+ ptr = ftello (bfd_cache_lookup (abfd));
+#else
ptr = ftell (bfd_cache_lookup (abfd));
+#endif
if (abfd->my_archive)
ptr -= abfd->origin;
@@ -217,7 +223,7 @@
{
int result;
FILE *f;
- long file_position;
+ file_ptr file_position;
/* For the time being, a BFD may not seek to it's end. The problem
is that we don't easily have a way to recognize the end of an
element in an archive. */
@@ -278,7 +284,13 @@
tripping the abort, we can probably safely disable this code,
so that the real optimizations happen. */
file_ptr where_am_i_now;
+#if defined HAVE_FTELLO64 && defined BFD64
+ where_am_i_now = ftello64 (bfd_cache_lookup (abfd));
+#elif defined HAVE_FTELLO && defined BFD64
+ where_am_i_now = ftello (bfd_cache_lookup (abfd));
+#else
where_am_i_now = ftell (bfd_cache_lookup (abfd));
+#endif
if (abfd->my_archive)
where_am_i_now -= abfd->origin;
if (where_am_i_now != abfd->where)
@@ -307,7 +319,17 @@
if (direction == SEEK_SET && abfd->my_archive != NULL)
file_position += abfd->origin;
+#if defined HAVE_FSEEKO64 && defined BFD64
+ /* NOTE: 64-bit seek is really only useful when BFD has been built
+ 64-bit. A 32-bit BFD build will have a 32-bit file_ptr which
+ limits the SEEK_SET range to 0..2^31. */
+ result = fseeko64 (f, file_position, direction);
+#elif defined HAVE_FSEEKO && defined BFD64
+ /* For a BFD built 64-bit, hopefully off_t is 64-bit. */
+ result = fseeko (f, file_position, direction);
+#else
result = fseek (f, file_position, direction);
+#endif
if (result != 0)
{
int hold_errno = errno;
Index: cache.c
===================================================================
RCS file: /cvs/src/src/bfd/cache.c,v
retrieving revision 1.10
diff -u -r1.10 cache.c
--- cache.c 29 Jun 2003 10:06:39 -0000 1.10
+++ cache.c 16 Jan 2004 23:18:12 -0000
@@ -155,7 +155,13 @@
return TRUE;
}
+#if defined HAVE_FTELLO64 && defined BFD64
+ kill->where = ftello64 ((FILE *) kill->iostream);
+#elif defined HAVE_FTELLO && defined BFD64
+ kill->where = ftello ((FILE *) kill->iostream);
+#else
kill->where = ftell ((FILE *) kill->iostream);
+#endif
return bfd_cache_delete (kill);
}
@@ -356,8 +362,20 @@
return NULL;
if (abfd->where != (unsigned long) abfd->where)
return NULL;
+#if defined HAVE_FSEEKO64 && defined BFD64
+ /* NOTE: 64-bit seek is really only useful when BFD has been
+ built 64-bit. A 32-bit BFD build will have a 32-bit file_ptr
+ which limits the SEEK_SET range to 0..2^31. */
+ if (fseeko64 ((FILE *) abfd->iostream, abfd->where, SEEK_SET) != 0)
+ return NULL;
+#elif defined HAVE_FSEEKO && defined BFD64
+ /* For a BFD built 64-bit, hopefully off_t is 64-bit. */
+ if (fseeko ((FILE *) abfd->iostream, abfd->where, SEEK_SET) != 0)
+ return NULL;
+#else
if (fseek ((FILE *) abfd->iostream, (long) abfd->where, SEEK_SET) != 0)
return NULL;
+#endif
}
return (FILE *) abfd->iostream;
Index: configure.in
===================================================================
RCS file: /cvs/src/src/bfd/configure.in,v
retrieving revision 1.142
diff -u -r1.142 configure.in
--- configure.in 19 Dec 2003 11:43:53 -0000 1.142
+++ configure.in 16 Jan 2004 23:18:12 -0000
@@ -159,7 +159,7 @@
AC_HEADER_TIME
AC_HEADER_DIRENT
AC_CHECK_FUNCS(fcntl getpagesize setitimer sysconf fdopen getuid getgid)
-AC_CHECK_FUNCS(strtoull)
+AC_CHECK_FUNCS(strtoull fseeko fseeko64)
BFD_BINARY_FOPEN