I have the exact same source code/make file compiled natively on two machines: Linux Fedora 16 32 bit and Linux Fedora 17 64 bit.
On the 32 bit machine:
(gdb) break FRS::FRS
Breakpoint 4 at 0x804ea29: file ntfs.cpp, line 751.
Breakpoint 5 at 0x804e18f: file ntfs.cpp, line 505.
warning: Multiple breakpoints were set.
Use the "delete" command to delete unwanted breakpoints.
GNU gdb (GDB) Fedora (7.3.50.20110722-16.fc16)
On the 64 bit machine:
(gdb) break FRS::FRS
Breakpoint 1 at 0x407daf: file ntfs.cpp, line 751.
GNU gdb (GDB) Fedora (7.4.50.20120120-54.fc17)
Using the knowledge from the 32 bit debugging session, I set the other breakpoint (and deleted the first one) to debug the proper function. However, it executes differently and only hits that constructor twice for the same test case. On the 32 bit environment it hits the breakpoint a dozen or so times.
FRS::FRS (MFT *Mft, uint32 MFTRef, bool shallow) // this is line 505
{
memset (this, 0, sizeof *this);
ParentMFT = Mft;
MFTReference = MFTRef;
Volume *vol = GetParentVolume ();
frs_bytes = ParentMFT -> GetFRSSizeInBytes();
frs_buf = new uint8 [frs_bytes];
if (!frs_buf)
{
fprintf (stderr, "FRS: alloc(%u) err\n", frs_bytes);
exit (1);
}
int sects = ParentMFT->GetFRSSizeInSectors(); // sectors per FRS
bool rc;
if (!MFTRef)
rc = vol -> RelativeRead (frs_buf, ParentMFT->GetMFTStart(), sects);
else
{
uint32 FirstLsn = Mft -> LogicalFromVirtual(MFTReference * sects);
uint32 LastLsn = Mft -> LogicalFromVirtual(MFTReference * sects + sects - 1);
if (FirstLsn + sects - 1 == LastLsn) // is contiguous?
rc = vol -> RelativeRead (frs_buf, FirstLsn, sects); // optimize read
else
{ // not contiguous: read sectors one at a time
for (int j = 0; j < sects; ++j)
{
... (170 more lines)
// copy constructor
FRS::FRS(FRS *frs) // this is line 751
{
int j;
*this = *frs;
if (frs_buf)
{
frs_buf = new uint8 [frs_bytes];
memcpy (frs_buf, frs -> frs_buf, frs_bytes);
}
DAttr = NULL;
StreamList = NULL;
... // 50 more lines
Is there something intrinsically different about 64 bit code that this function would be compiled away? (It is a 204 line function, so I have truncated it after demonstrating it is non-trivial.)
What would explain why gdb doesn't "see" the same set of constructors, and why the code doesn't seem to get called as much—though why it would be different from "everything or nothing" is a mystery.
You're comparing different versions of gdb as well as different versions of gcc. That is just too many variables.
Most likely it is debuginfo differences. But it isn't really possible to say with just this information.
One thing to know is that the C++ ABI specifies multiple copies of constructors to be emitted. There are "in-charge" and not-in-charge variants. gdb will put breakpoints on all the ones it finds.
However, I think this can be affected by the debuginfo and other factors. It is not always obvious what happens from source to executable... You can use tools like "nm" and "readelf -wi" to dig through the symbols and debuginfo if you really want to find exactly why this happens.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With