[lkml]   [1996]   [Jul]   [2]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
Messages in this thread
SubjectRe: Driver optimization.
| Implementation:
| Ideally gcc should grok an #pragma similar to the MSC compiler above.
| Otherwise an "asm" statement could be inserted before and after
| init routines to switch to a different segement. The problem with
| this approach is that a string in the routine causes an
| .section .rodata
| .LC0:
| .string "this is the string
| .text
| to be emitted just before the function, undoing the simple
| asm (".section .init");
| A way around this needs to be found.

Umm, providing you use an ELF gcc compiler, GCC already supports this:

extern void foo() __attribute__((section(".foo")));
void foo(){}

generates the following code:

.file "foo.c"
.version "01.01"
.section .foo,"ax",@progbits
.align 16
.globl foo
.type foo,@function
pushl %ebp
movl %esp,%ebp
movl %ebp,%esp
popl %ebp
.size foo,.Lfe1-foo
.ident "GCC: (GNU) 2.7.2"

There is no way at all an a.out compiler can support section
attributes, due to the limited nature of the object format. Also
note, that as currently configured, the Alpha and 32-bit mips do not
support putting text in any section other than .text (ie, if you use
it, you will need to wrap it in macros so that it can be turned off).

Note, that the __attribute__ must appear on the function declaration,
not the definition.

| In ELF lots of segments get mapped the same as .text, ".init" is
| indeed one of them, so if you don't want to go and edit binutils, you
| could just use one of those (I don't know if ".init" is already used).

In some ELF systems, .init contains all of the constructors (actually,
the crti.o module contains the function prologue, and each module
deposits a call foo into the .init section to call the appropriate
construction, and the crtn.o module contains the function epilogue).
The crt[01].o then calls the .init section. Static constructors are
handled similarly with a section known as .fini.

This of course also assumes that the linker will link the other other
sections close enough to the normal callers, since on RISC platforms
in general, the call instruction is limited in the range it can call
to without loading the address into a pointer and calling indirect
through it. If that happens, you either get an abort, or the linker
creates a PLT-type call, which uses up a few cycles.

By the way, the technique of putting init code into memory that will
be freed up is quite old. I first ran across it in 1976 on CDC Cybers
running Kronos. I'm sure it was old even then.

Michael Meissner, Cygnus Support (East Coast)
Suite 105, 48 Grove Street, Somerville, MA 02144, USA, 617-629-3016 (office), 617-629-3010 (fax)

 \ /
  Last update: 2005-03-22 13:37    [W:0.088 / U:0.416 seconds]
©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site