[cxx-abi-dev] Passing an empty class by value

Gabriel Dos Reis gdr at integrable-solutions.net
Sat Feb 27 07:57:01 UTC 2016


On Fri, Feb 26, 2016 at 8:01 PM, Jason Merrill <jason at redhat.com> wrote:

> On 12/11/2015 01:37 PM, Jason Merrill wrote:
>
>> On 12/10/2015 07:32 PM, Richard Smith wrote:
>>
>>> On 10 December 2015 at 16:15, John McCall <rjmccall at apple.com> wrote:
>>>
>>> On Dec 10, 2015, at 4:11 PM, Nelson, Clark <clark.nelson at intel.com>
>>>>>
>>>> wrote:
>>>>
>>>>>
>>>>> It has come to my attention that GCC and clang generate incompatible
>>>>> code
>>>>> for passing an argument of an empty class type.
>>>>>
>>>>> clang seems to completely ignore arguments and parameters of empty
>>>>> class
>>>>> type -- which seems to make a certain amount of sense.
>>>>>
>>>>> OTOH, as far as I understand it, GCC effectively treats an empty class
>>>>> equivalently to a class containing a single member with some character
>>>>> type -- which also seems pretty reasonable.
>>>>>
>>>>> Should the C++ ABI come down on one side or the other of this question?
>>>>>
>>>>> This is really the sort of question a psABI should settle. But of
>>>>> course
>>>>> the C language doesn't actually support a structure with no members, so
>>>>> it's not too surprising if a psABI doesn't nail down what should happen
>>>>> for this.
>>>>>
>>>>
>>>> It’s valid as a C extension in GCC.  If there are platforms where we
>>>> use a
>>>> different rule from GCC, we should come to some understanding with them.
>>>>
>>>> Because of the GCC extension, C++ can’t really use different rules
>>>> from C.
>>>>
>>>
>>>
>>> (For x86_64:) GCC uses different rules for C and C++. In C, they do not
>>> pass anything. In C++, they pass a 1-byte object on the stack. Clang uses
>>> the same rules for C and C++, passing nothing in both cases.
>>>
>>> A careful reading of the x86_64 psABI suggests that clang is right in
>>> both
>>> cases; the eightbyte corresponding to the 1-byte empty struct
>>> parameter is
>>> never classified (at all), so should occupy neither a register nor
>>> memory,
>>> but it's not really especially clear.
>>>
>>> In any case, I think GCC should be the one to change here, because its C
>>> and C++ ABIs don't match.
>>>
>>
>> Agreed.
>>
>
> On further discussion, it came up that the C and C++ ABIs really can't
> match.  In GNU C, an empty struct has size 0; in C++ it has size 1.  We
> could finesse this difference for argument passing, as suggested here, but
> we really can't paper over the difference in general.  What if you have a
> class containing an empty class?  GNU C still says that has size 0, but
> it's less clear that this makes sense for C++.  Significantly, this does
> not fit the ABI definition of an empty class.
>

Five years ago, we determined that it would make sense (read: provably
safe) to optimize that case too -- even for arrays.  See section 6.2 of
      http://www.axiomatics.org/~gdr/formal-cxx/layout-popl11.pdf
for the "layman" summary.


>
> I also notice that the ABI says "If the base ABI does not specify rules
> for empty classes, then an empty class has size and alignment 1."


-- Gaby
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://sourcerytools.com/pipermail/cxx-abi-dev/attachments/20160226/e23fec69/attachment.html>


More information about the cxx-abi-dev mailing list