[C++ RFC] Fix up attribute handling in templates (PR c++/79502)

Martin Sebor msebor@gmail.com
Sun Feb 19 21:56:00 GMT 2017


On 02/17/2017 09:53 PM, Jason Merrill wrote:
> On Thu, Feb 16, 2017 at 6:13 PM, Martin Sebor <msebor@gmail.com> wrote:
>> On 02/16/2017 12:49 PM, Jason Merrill wrote:
>>>
>>> On Thu, Feb 16, 2017 at 11:33 AM, Jakub Jelinek <jakub@redhat.com> wrote:
>>>>
>>>>         PR c++/79502
>>>>         * pt.c (apply_late_template_attributes): If there are
>>>>         no dependent attributes, set *p to attributes.  If there were
>>>>         some attributes in *p previously with or without dependent
>>>>         attributes, chain them after the new attributes.
>>>
>>>
>>> Here's the variant of your patch that I'm applying.
>>
>>
>> Sorry to butt in but I feel like I'm missing something basic.  Are
>> these attributes (nodiscard, noreturn, maybe_unused, and deprecated)
>> meant to apply to templates?  The text in for nodiscard suggests
>> they're not:
>>
>>   The attribute-token nodiscard may be applied to the declarator-id
>>   in a function declaration or to the declaration of a class or
>>   enumeration.
>>
>> Noreturn also doesn't mention templates:
>>
>>   The attribute may be applied to the declarator-id in a function
>>   declaration.
>>
>> Deprecated explicitly mentions template specializations but not
>> primary templates:
>>
>>   The attribute may be applied to the declaration of a class,
>>    a typedef-name, a variable, a non-static data member, a function,
>>    a namespace, an enumeration, an enumerator, or a template
>>    specialization.
>>
>> I can certainly see how applying attributes to the primary template
>> would be useful so it's puzzling to me that the standard seems to
>> preclude it.
>
> I don't think it's precluded; a /template-declaration/ syntactically
> includes a /declaration/, so in general any statement about e.g. a
> function declaration also applies to a function template declaration.

I'm sure you're right that it's not meant to be precluded, otherwise
the standard library couldn't declare noreturn the throw_with_nested
function template (the only template declared noreturn in the library
I could find).

FWIW, a context where noreturn clearly is not applicable is function
pointers.  G++ accepts it there but then ignores it.  Clang rejects
it.  I would think accepting it on function pointers would be useful
as well.  GCC (in C mode) accepts __attribute__ noreturn on function
pointers and treats them as such (G++ does not).

Another interesting context is the explicit instantiation directive.
Again, the standard seems clear that noreturn isn't allowed but GCC
and Microsoft Visual C++ both accept it. Clang and EDG reject it.
I think rejecting it here makes sense and accepting is a bug.

>> I ask also because I was just looking at bug 79021 and scratching
>> my head about what to thing about it.   While trying to understand
>> how GCC handles attributes for the primary template I came across
>> what doesn't make sense to me.   Why would it apply the attribute
>> from the primary to the explicit specialization when the two are
>> distinct entities?  Is that a bug?
>
> This seems like a Core issue; the standard says nothing about how
> attributes on a template affect specializations.

Yes, I thought so as well.  Thanks for confirming that.  Unless
you would prefer to bring it up yourself let me post it to the
core reflector and suggest to open a new issue for it.

> I think that as a general rule, not applying attributes from the
> template to specializations makes sense.  There will be some
> exceptions, such as the abi_tag attribute which is a property of the
> name rather than a particular declaration.

That makes sense to me.

Thanks
Martin



More information about the Gcc-patches mailing list