[PATCH v9 16/19] gnu directives: add support for gnu_attribute and gnu_subsection in OAv2 context
Jan Beulich
jbeulich@suse.com
Fri Nov 7 09:00:12 GMT 2025
On 06.11.2025 17:39, Matthieu Longo wrote:
> On 31/10/2025 12:48, Jan Beulich wrote:
>> On 01.09.2025 18:56, Matthieu Longo wrote:
>>> --- a/bfd/elf-attrs.c
>>> +++ b/bfd/elf-attrs.c
>>> @@ -2667,10 +2667,11 @@ oav2_parse_subsection (bfd *abfd,
>>> }
>>>
>>> const char *vendor_name = get_elf_backend_data (abfd)->obj_attrs_vendor;
>>> - obj_attr_subsection_scope_v2 scope
>>> - = (strncmp (subsection_name, vendor_name, strlen (vendor_name)) == 0
>>> - ? OA_SUBSEC_PUBLIC
>>> - : OA_SUBSEC_PRIVATE);
>>> + obj_attr_subsection_scope_v2 scope = OA_SUBSEC_PRIVATE;
>>> + if (strncmp (subsection_name, vendor_name, strlen (vendor_name)) == 0
>>> + || (strncmp (subsection_name, "gnu", 3) == 0
>>> + && !gnu_testing_namespace (subsection_name)))
>>> + scope = OA_SUBSEC_PUBLIC;
>>>
>>> *subsec = _bfd_elf_obj_attr_subsection_v2_init
>>> (subsection_name, scope, comprehension_raw, value_encoding);
>>> --- a/binutils/readelf.c
>>> +++ b/binutils/readelf.c
>>> @@ -20014,7 +20014,9 @@ elf_parse_attrs_subsection_v2 (unsigned char *cursor,
>>> const char *subsec_name = (const char *) cursor;
>>> printf (_(" - Name: %s\n"), subsec_name);
>>> bool public_subsection
>>> - = strncmp (subsec_name, public_name, strlen (public_name)) == 0;
>>> + = (strncmp (subsec_name, public_name, strlen (public_name)) == 0
>>> + || (strncmp (subsec_name, "gnu", 3) == 0
>>> + && strncmp (subsec_name + 3, "-testing", 8) != 0));
>>> cursor += subsection_name_len;
>>> op.read += subsection_name_len;
>>>
>>> --- a/gas/config/obj-elf-attr.c
>>> +++ b/gas/config/obj-elf-attr.c
>>> @@ -1078,10 +1078,11 @@ obj_attr_v2_subsection_record (const char *name,
>>>
>>> const char *vendor_name
>>> = get_elf_backend_data (stdoutput)->obj_attrs_vendor;
>>> - obj_attr_subsection_scope_v2 scope
>>> - = (strncmp (name, vendor_name, strlen (vendor_name)) == 0
>>> - ? OA_SUBSEC_PUBLIC
>>> - : OA_SUBSEC_PRIVATE);
>>> + obj_attr_subsection_scope_v2 scope = OA_SUBSEC_PRIVATE;
>>> + if (strncmp (name, vendor_name, strlen (vendor_name)) == 0
>>> + || (strncmp (name, "gnu", 3) == 0
>>> + && strncmp (name + 3, "-testing", 8) != 0))
>>> + scope = OA_SUBSEC_PUBLIC;
>>
>> Three times the effectively same check - shouldn't there be a helper centralizing
>> this?
>>
>
> See my reply in patch 9/19.
>
> I moved the code to this helper:
>
> /* Identify the scope of a subsection from its name. */
> obj_attr_subsection_scope_v2
> bfd_elf_obj_attr_subsection_v2_scope (bfd *abfd, const char *subsec_name)
> {
> const char *vendor_name = get_elf_backend_data (abfd)->obj_attrs_vendor;
> obj_attr_subsection_scope_v2 scope = OA_SUBSEC_PRIVATE;
> size_t vendor_name_len = strlen (vendor_name);
> if ((strncmp (subsec_name, vendor_name, vendor_name_len) == 0
> && subsec_name[vendor_name_len] == '_')
> || (strncmp (subsec_name, "gnu_", 4) == 0
> && !gnu_testing_namespace (subsec_name)))
> scope = OA_SUBSEC_PUBLIC;
> return scope;
> }
Yet that still doesn't cover readelf, aiui. Please have cross-ref comments
at both sites then, to make clear that both need keeping in sync.
>>> +/* Parse a .gnu_subsection directive. */
>>> +
>>> +static void
>>> +obj_elf_gnu_subsection (int ignored ATTRIBUTE_UNUSED)
>>> +{
>>> + obj_attr_version_t version = elf_obj_attr_version (stdoutput);
>>> + if (! attr_fmt_has_subsections (version))
>>> + {
>>> + as_bad (_(".gnu_subsection is only available with object attributes v2,"
>>> + " and the current target only supports object attributes v1"));
>>
>> This message, first of all, is liable to go stale the moment some target supports
>> both v1 and v2.
>
> The version specified in the backend corresponds to the only-supported
> output format for a given backend. If a backend wants to migrate, and
> sets this to OAv2, it means that no object with OAv1 can be generated
> with this version of binutils. However, OAv1 objects would be accepted
> at link time, but the resulting build artifact will only contain OAv2. I
> said "would" because this requires a translation layer implemented by
> the backend, and there is no such example today.
>
> How is this relevant to parsing ?
> For parsing, nowhere the spec mentioned a way to indicate what version
> of OAv1 or OAv2 is used in an assembly file. If you look at the cover
> letter, I proposed a flag --obj-attr=[OAv1|OAv2] for such a use case,
> but I would say that adding such an option is out of scope for this
> patch series. This option would allow a period where files can be
> migrated one by one, instead of migrating everything at the same time.
> If the approach of a command line option were adopted, the check should
> use a value other than elf_obj_attr_version (stdoutput) (i.e. the
> preferred output format), which would store the command line option value.
>
> Given that this option is hypothetical until someone decides to go
> through a migration, I would recommend not to pay too much attention to
> this check. What is you opinion about this given the previous explanation ?
>
> > I also think (see other respective remarks elsewhere) that the>
> diagnostic is too long. AT the very least the second "object attributes"
> looks
>> redundant, for example.
>>
>
> Yes, I agree. What about this simpler sentence, but a bit vague in my
> opinion.
>
> ".gnu_subsection is only available with object attributes v2"
I'd be fine with this, as it also addresses my other comment above.
>>> @@ -5745,6 +5746,10 @@ partial programs. You may need the HPPA-only @code{.EXPORT} directive as well.
>>> @end ifset
>>>
>>> @ifset ELF
>>> +@node Gnu_subsection
>>> +@section @code{.gnu_subsection @var{name}, @var{comprehension}, @var{encoding}}
>>> +Record a @sc{gnu} object attribute subsection for this file. @xref{Object Attributes}
>>
>> Here you document the new directive, whereas ...
>>
>>> @@ -7954,32 +7959,62 @@ Many architectures support incompatible variations. For instance, floating
>>> point arguments might be passed in floating point registers if the object file
>>> requires hardware floating point support---or floating point arguments might be
>>> passed in integer registers if the object file supports processors with no
>>> -hardware floating point unit. Or, if two objects are built for different
>>> -generations of the same architecture, the combination may require the
>>> -newer generation at run-time.
>>> -
>>> -This information is useful during and after linking. At link time,
>>> -@command{@value{LD}} can warn about incompatible object files. After link
>>> -time, tools like @command{gdb} can use it to process the linked file
>>> -correctly.
>>> +hardware floating point unit. Another example might be when two object files
>>> +make use of different architectural extensions: the final image will require
>>> +both features to be supported at runtime; or if the features are mutually
>>> +exclusive, the linker can issue a diagnostic.
>>>
>>> -Compatibility information is recorded as a series of object attributes. Each
>>> -attribute has a @dfn{vendor}, @dfn{tag}, and @dfn{value}. The vendor is a
>>> -string, and indicates who sets the meaning of the tag. The tag is an integer,
>>> -and indicates what property the attribute describes. The value may be a string
>>> -or an integer, and indicates how the property affects this object. Missing
>>> -attributes are the same as attributes with a zero value or empty string value.
>>> +@command{@value{AS}} currently supports two versions of object attributes:
>>> +@itemize @bullet{}
>>> +@item
>>> +Object Attributes version 1 (OAv1) used by: ARC, ARM, C-SKY, MIPS, MSP430, M68K,
>>> +PowerPC, RISC-V, SPARC, s390, and TIC6X.
>>> +@item
>>> +Object Attributes version 2 (OAv2) used by: AArch64.
>>> +@end itemize
>>>
>>> -Object attributes were developed as part of the ABI for the ARM Architecture.
>>> -The file format is documented in @cite{ELF for the ARM Architecture}.
>>> +Object attributes are only supported when generating ELF format.
>>>
>>> @menu
>>> +* Object Attributes v1:: Object Attributes v1
>>> +* Object Attributes v2:: Object Attributes v2
>>> * GNU Object Attributes:: @sc{gnu} Object Attributes
>>> * Defining New Object Attributes:: Defining New Object Attributes
>>> @end menu
>>>
>>> +@node Object Attributes v1
>>> +@section Object Attributes v1
>>> +
>>> +In Object Attributes v1 (OAv1) Compatibility information is recorded as a series
>>> +of object attributes. Each attribute has a @dfn{vendor}, @dfn{tag}, and
>>> +@dfn{value}. The @dfn{vendor} is a string, and indicates who sets the meaning
>>> +of the tag. The @dfn{tag} is an integer, and indicates what property the
>>> +attribute describes. The @dfn{value} may be a string or an integer, and
>>> +indicates how the property affects this object. Integer tags generally default
>>> +to 0, while string tags default to the empty string. Tags are only recorded in
>>> +the file if they have a non-default value.
>>> +
>>> +OAv1 were developed as part of the ABI for the ARM Architecture. The file
>>> +format is documented in @cite{Addenda to, and Errata in, the ABI for the Arm
>>> +Architecture}.
>>> +
>>> +@node Object Attributes v2
>>> +@section Object Attributes v2
>>> +
>>> +Object Attributes v2 (OAv2) share common concepts of @dfn{vendor}, @dfn{tag}
>>> +and @dfn{value} with OAv1, but also introduce the new ones like @dfn{subsection}
>>> +and @dfn{scope}. Attributes with common properties are grouped into subsections.
>>> +All the attributes in a subsection share the same encoding, comprehension, and
>>> +scope. A subsection starting with the vendor name is considered public. The
>>> +value of an attribute may be a string or an integer depending on the encoding
>>> +set on its subsection.
>>> +
>>> +OAv2 is only used by AArch64. Directives are documented in @ref{AArch64
>>> +Directives}. The file format is documented in @cite{Build Attributes for the
>>> +Arm 64-bit Architecture (AArch64)}.
>>
>> ... here you refer to something living elsewhere.
>
> I am not sure that I understand what your concern is with the current
> documentation.
> Do you mean that I should remove the reference "@xref{Object
> Attributes}" because the link between this directive, and the
> explanation of what OAv2 are is not clear, or at least not directly
> related ?
> Please could you elaborate ?
"AArch64 Directives" lives in c-aarch64.texi. The patch doesn't alter that file
at all, hence why I can't help the impression that the @ref here points to the
wrong place. That said, I may be irritated by it being .gnu_subsection that you
document here, while at the same time inserting a reference to where
.aeabi_subsection and .aeabi_attribute are documented. Perhaps this reference
wants adding there already in patch 04?
It's further unclear to me where exactly the @cite points. Looking back through
the series, a similar @cite is added in patch 04. There it's also unclear what
it references. You don't expect people to search the internet for something by
that title, with unpredictable quality of results, do you? Surely there is a
stable URL you could supply?
Jan
More information about the Binutils
mailing list