Hi all,

With gas, does anyone know of a way to create a section whose name is
based on that of the current section?

The specific requirement is to be able to define a generic macro like
the example "fixup" below, whose purpose is to record ancilliary data
related to some other section.  To illustrate:

.macro fixup
100\@ :
    .pushsection fixup<current section name>, "a"
        .long 100\@b
    .popsection
.endm

.text
...
    fixup
    .long sym1
...

.section .other, "ax"
...
    fixup
    .long sym2


The linux kernel uses a technique just like this for patching SMP
kernels at bootup to work on uniprocessor platforms (when
CONFIG_SMP_ON_UP is enabled), resulting in code looking something like
this:

void exit __attribute__ (( __section__ (".text.exit") ))
{
    ...
    asm(
        ...
        FIXUP("something")
        ...
    );
}

Note that the inline asm may actually come out of a generic header
file rather than being explitly written for this invocation.  So it
may have to be truly generic.


Is far as I have been able to determine, it's not possible to generate
sections named based on the current section.  In practice, the kernel
puts all the fixups into a single section.

The downside of this is that when sections are selectively discarded
at link time (which in general may happen -- for example, Linux
discards the "module exit" code for drivers which are built into the
kernel and therefore never exit) there is no way to selectively
discard the related fixup entries.  Currently the only solution is to
include all the module exit code in the image and discard it at
run-time when the kernel boots.  This is obviously wasteful.
Attempting to discard that code at like time results in a link error,
since fixups refer to the removed sections.

Of course, the "fixup" macro could be given an extra parameter to name
the containing section, but the macro can then no longer be called in
a generic way: all the calls to that macro must be manually (and
buggily) maintained to ensure that the referenced section name is
correct, some object post-processing must be done before linking,
and/or a tool must be created to implement the missing assembler
functionality.  Unfortunately, such solutions are likely to be too
fragile or complex to make it upstream.


It's interesting to note that the same problem will apply for any
section containing ancilliary data for another section.  In
particular, it looks like either the ABI or the assembler has had to
grow a special-case workaround for this in order to support exception
unwind information sections generated by .fnstart ... .fnend in a sane
way: the unwind information sections get called .ARM.ex{idx,tab} for
.text, and .ARM.ex{idx,tab}<section> for any other section.  As a
consequence, link-time discarding can handle this information
properly, but IMHO this is a bit of a cheat and admits the general
need to create sections with names based transparently on those of
other sections, without satisfying that need.  .popsection is also an
example of such a cheat: most other aspects of assmbler state still
cannot be saved and restored.


In general, it would be useful if gas supported some general
reflective abilities: i.e., the ability to query the current assembler
state (section, subsection, active instruction set, active macro mode,
etc.) and/or the ability to wrap or hook existing pseudo-ops.  For
example, the above problem would almost certainly solvable using
assembler macros (albeit painfully) if wrapper macros could be defined
for the section manipulation directives (section, .text, .data, .bss,
.pushsection, .popsection, .previous).  However, supporting some magic
macro parameters reflecting the assembler state would be a lot
simpler.

As an example of the kind of behaviour I think would be useful, the
macro argument qualifier could be extended to allow macros to query
the assembler state in a backwards-compatible way; something like:

.macro fixup base_section:gas_current_section_name,
old_altmacro:gas_macro_mode
    .altmacro
    LOCAL fixup_location

fixup_location:
    .pushsection \base_section\().fixup
        .long 100\@b
    .popsection

    \old_altmacro
.endm

Existing assembler code will continue to work just fine with this approach.

Note how this also enables a local label to be generated hygenically,
by making it possible to save and restore the macro mode.  Otherwise,
.altmacro (and hence LOCAL) is hard to use safely, since the initial
macro mode is unknown and can't be restored.

Any thoughts / comments?

Cheers.
---Dave

_______________________________________________
linaro-toolchain mailing list
linaro-toolchain@lists.linaro.org
http://lists.linaro.org/mailman/listinfo/linaro-toolchain

Reply via email to