tags:

views:

532

answers:

5

I have the following C code:

struct myStruct_t
{
    const char     m_name[60];
    const uint32_t m_data;
};

const struct myStruct_t myStruct
    __attribute__(( __aligned__( 64 ), section(".init") )) =
    {
        "myName",
        (uint32_t)&someOtherStruct
    };

When I compile in gcc 4.1.1 (for PS3), I get the warning:

1>c:/t/ccy6.s: Assembler messages:
1>c:/t/ccy6.s(106): Warning: setting incorrect section attributes for .init

The assembly code the warning points to is the ".section" clause below:

            .section              .init,"aw",@progbits
            .align 6
            .type                 myStruct , @object
            .size                 myStruct , 64
myStruct :
            .ascii                "myName"
            .long                 someOtherStruct

It doesn't like the "w" (writable) part of the flags since stuff in .init is read-only, and "const" in all the possible places doesn't compel the compiler not to spit out the "w". How can I tell the compiler "no, really, it is const, I'm not kidding"?

A: 

Wild guess, but perhaps the attribute it's setting that's wrong is the "aw", which suggests "writable" to me. Does it still do this if everything in your struct is const?

Edit: Random googling seems to suggest that "w" could also stand for "weak"?

Dan Olson
I changed OP to put const everywhere, and I get the same result. Yeah, it doesn't like the "w"ritable flag due to .init being read-only. Why is gcc spitting out "w" in the first place, and how can I prevent it? ("a" means allocatable, which is fine here)
Jim Buck
Hmm, I hadn't seen "weak", but here is "writable" (under the ELF section): http://sourceware.org/binutils/docs/as/Section.html
Jim Buck
A: 

On a GNU/Linux PC with GCC 4.3.3, .init isn't made writable. I didn't find in the documentation how to set the section attributes manually.

Maybe it won't help much, but here are a few suggestions:

  • If what you want is to execute some code before main(), you can use a C++ object. Its constructor will be called before main(), and its destructor after.
  • You could write a small tool that will patch the object file manually. I'm pretty sure this already exists. Maybe here: http://www.eresi-project.org/.
  • You could contact the GCC developers. Maybe it's a bug.
Bastien Léonard
Thanks for the response. C++ is unfortunately not an option, and I don't actually want .init to be writable. I'm just trying to remove all warnings from the code. This struct is fine if it's read-only, but yeah, it looks like a gcc bug that it spits out a "w" for data with const everywhere.
Jim Buck
+1  A: 

For God's sake, man, don't try to use gcc as an assembler! I don't see any reason why this thing should be in the .init section (it isn't code), but if you must have it there, write the assembly code you want (you have a good start there; just edit), put it under source control in the appropriate place for each platform, and be done with it!

Norman Ramsey
A: 

If you want to place myStruct somewhere special, use a linker file.

http://sourceware.org/binutils/docs-2.19/ld/Scripts.html#Scripts

Markus Schnell
A: 

This is a problem with GCC auto-specifying the parameters for the .section directive. Luckily, the section name parameter is copied directly into the assembly output, permitting you to work around this issue.

This directive:

__attribute__ ((section(".init")))

Generates this assembly:

.section .init,"aw",@progbits

To remove the warning, you can specify the attribute like this:

__attribute__ ((section(".init,\"ar\",@progbits ;")))

Which will generate:

.section .init,"ar",@progbits ;"aw",@progbits

The semicolon marks the rest of the line as a comment, so the assembler ignores it.

Luke Gumbley