Virtual function call stuff, again

Christophe de Dinechin ddd at cup.hp.com
Tue Feb 22 22:46:08 UTC 2000


Mark Mitchell wrote:
> 
> >>>>> "Christophe" == Christophe de Dinechin <ddd at cup.hp.com> writes:
> 
> Thanks for helping me with this.
> 
>     Christophe> Mark, I did not find anything containing "Virtual
>     Christophe> Function Calling Convention" in the
>     Christophe> documentation. Could you specify an URL and quote the
>     Christophe> original text, it would help me locating it...
> 
> http://reality.sgi.com/dehnert_engr/cxx/abi-layout.html#vtable
> 
> There doesn't appear to be a tag for the "VFCC" section, but it's down
> just a bit from the URL I gave.

Well, funny I did not find it the first time. A typo in the "find" box, I guess.
Sorry.


> 
> I understand the high-level points of that discussion: what I don't
> understand is exactly what goes where, when.  I'm not really trying to
> reopen any issue -- I'm trying to force the committe to write down
> what it decided.  At this point, the decision is not, quite frankly,
> written in a form that anyone not on the committee is likely to
> decipher.  (Well, at least I've tried hard, I'm not an idiot, I know
> about this application domain, and I still can't figure it out.)

I understand your remarks, and they are perfectly valid. I was trying to clarify
on your example. That's probably the wrong approach, though, since what you want
is a clear enough wording in the writeup. So let me go through the writeup and
see if I can improve things slightly, based on your comments.

Now, Jim, I just realized that for some reason, in the writeup, the vcall
offsets are restricted for "virtual bases" cases. I am unable to implement the
"single adjusting entry point" optimization if this is the case. I fixed it in
the attached writeup, but I may be wrong.

Jason's writeup to B-1 says that you have to implement the vcall offsets even if
you don't use them. I don't think we agreed to get rid of them (or is this
something else important I missed?)


> 
>     >> - If there is a virtual base along this path, let `V' be the
>     >> virtual base nearest to `C' along the path.  (In fact, `V' will
>     >> be `C' itself if `C' is a virtual base.)
> 
>     Christophe> You are considering a path between B and C, so V would
>     Christophe> be the closest between B and C. In which case I do not
>     Christophe> understand the adjustment below ("Adjustment from 'A'
>     Christophe> to 'V'"). Either you are considering that V is between
>     Christophe> A and C, in which case you need to adjust from A to V,
>     Christophe> or you are considering that V is between C and B, in
>     Christophe> which case if you see it at call site, you would have
>     Christophe> to adjust from B to V. Did I misunderstand?
> 
> You won't in general see `V' at the call site, if it's between C and
> B, because you might have `A*' when you're making the call.  (If you
> had a `B*', or a `C*', then `C::f' would be the unique final overrider
> -- by hypothesis -- so you would have converted your pointer to a
> `C*', and you be looking at the C-in-B vtable, rather than the A-in-B
> vtable, which is what my discussion was talking about.)

Violent agreement, apparently. So I must have misunderstood what you wrote. It
was unclear to me that you were discussing only the A-in-B vtable case.


> I'm not sure where you're supposed to adjust `A' to.  That's what I'm
> trying to find out.  It may not be the V that I suggested -- I'm not
> sure.  I'm hoping that my words could serve as the model for whatever
> the right answer is.  They're in the form of an algorithm that
> explains exactly what to put in the vtable, in the general case, and
> that's a good thing, since that's what an implementor needs to know.
> 
>     Christophe> So, starting with your example again. Sorry for the
>     Christophe> verbiage...
> 
>     Christophe> Case 1 is: V is between A and C.
> 
> THere's no discussion of these two different cases in the current
> writeup.  So, I'm already lost.  What you write below seems reasonably
> logical -- but I'm not sure it's the same thing as in the document.

The two cases were because I was trying to reconstruct the possible layouts from
what you said. I saw two cases, there was a third one (your pictogram below)
that I did not even see... These cases are not distinct in the writeup.


> In general, "between A and C" doesn't make sense; they may be
> unrelated. The picture I had in mind was:
> 
>               B
>              / \
>             A   C
> 
> In other words, B is the most derived class, C contains the final
> overrider, we're looking at the vtable for A.  That's the general case
> -- all other cases are special instances of this one.  But, I guess
> for case 1, we're assuming C is derived from A?

I thought this was your intent. Since again I have some trouble reconstructing
what you want (unless there is some additional base common to A and C where f is
first declared???)

The best would be for you to write the code for the case that annoys you.


>     Christophe> - If you call through an A*, you call through the A
>     Christophe> vtable, which points to a virtual-base-adjustment
>     Christophe> thunk. That thunk reads the C-to-A virtual base
>     Christophe> offset, and adds that to get a C*, and then jumps to
> 
> Where is this offset?  There's a vbase offset in C for converting to
> A, if A is a virtual base of C.  But, there's no virtual base offset
> in A, for converting to a C.  Where's V in all this?

I prefer not to add confusion until I see the code you have in mind.



Regards
Christophe




More information about the cxx-abi-dev mailing list