Re: [RFA/c++] Fix printing classes with virtual base classes

Daniel Jacobowitz
2001-11-26T21:36:00Z

On Mon, Nov 26, 2001 at 11:39:34PM -0500, Jim Blandy wrote:
>
> I'm with you on VALUE_OFFSET and VALUE_EMBEDDED_OFFSET. I'm pretty
> sure VALUE_OFFSET can be eliminated from GDB entirely, with some minor
> changes to the representation of subvalues of registers and
> convenience variables.

I am exceedingly tempted to do this.

> Can you explain exactly what TYPE_VPTR_FIELDNO means, and how it works
> in heavily derived classes? What I think you're basically doing there
> is taking the address of the field indicated by TYPE_VPTR_FIELDNO,
> casting that to a void *, and then casting that to the `struct
> gdb_gnu_v3_abi_vtable' type. I have this vague memory that maybe
> using TYPE_VPTR_FIELDNO correctly would fix that.

I certainly can't explain it :) This code mostly mystifies me. It
seems that the vptr for a given class is always a field of the class,
and may actually overlap where the vptr for its first virtual base
class. TYPE_VPTR_FIELDNO tells us where it is. For example, in GCC
2.x, this code:

class Foo
{
int bar;
public:
virtual int thug() { return 1; }
};

class Foo2
{
int bar2;
};

class Baz : public Foo2, public Foo {
int baz;
public:
virtual int thugs() { return 1; }
};

will cause vptr_fieldno for Baz to be 1, indicating its vptr is stored
in memory at the beginning of field 1.

Gnu v2 code handles this by casting the Baz to a Foo, at which point
magic happens, and somehow the vptr is visible. This suggests that my
fix is not the best way of doing it, and I should be using
TYPE_VPTR_BASETYPE somehow instead. I may need to think some more.

Upon further reflection, TYPE_VPTR_FIELDNO is supposed to be a field
index in TYPE_VPTR_BASETYPE. Interesting. I think there's something
wrong here; more comments tomorrow.

> I wonder if that dereferencing code could be simplified with a
> judicious use of `lookup_pointer_type (vtable_type)' and
> `value_deref'...

I suppose it would read simpler if I took a value_addr () and cast a
bit. But magic happens in value casting that I don't want to happen.

--
Daniel Jacobowitz Carnegie Mellon University
MontaVista Software Debian GNU/Linux Developer