Very strange GCC/Linker problem!

All off topic discussions go here. Everything from the funny thing your cat did to your favorite tv shows. Non-programming computer questions are ok too.
Post Reply
chorakm
Posts: 14
Joined: Fri Dec 08, 2006 12:07 am

Very strange GCC/Linker problem!

Post by chorakm »

Hi! I got really interested in OS development and wanted to make a simple kernel. I noticed a very strange and annoying case with gcc and ld. Say I create a function called strlen() to calculate the length of a string that is passed to it. If I create the string using a literal string like...

char string[] = "Hello World!";
strlen(string);

and then I pass it to the function, the program goes from normally compiling to about 8kb to about 1.0mb!!! And then when I try to load the kernel with GRUB, it says that it's an invalid kernel. Here is an interesting case however, If I initialize the string like this

char string[16];

string[0] = 'H';
string[1] = 'e';
and so on

and then I append it with
string[x] = 0 (Null terminator)
strlen(string);

And compile, the code compiles back down to 8kb and is successfully loaded by GRUB. The interesting thing is that the program will not increase in size and become corrupt if I merely declare the variable:

char string[16] = "Hello World!";

But it happens when I pass the variable to a function, i.e. strlen (that I have created). I believe it has something to do with the stack but I don't have enough knowledge in this area and I was wondering if someone could give me some insight! I am using a linker script.

http://www.osdever.net/bkerndev/Docs/intro.htm

This is the site that I'm following, so the source code I'm using is basically exactly what he has, except edited a bit because he sucks at proof reading :-P. Thanks for the help!
User avatar
Solar
Member
Member
Posts: 7615
Joined: Thu Nov 16, 2006 12:01 pm
Location: Germany
Contact:

Post by Solar »

Rule 0, the chance of you finding a bug in the compiler or linker is next to non-existent. Look for an error of your own.

The usual suspects:
  • Strings usually end up in a different section of the binary (.rodata).
  • Sections are usually page-aligned. Adding a section to the binary significantly increases its size, at least when the binary is very small still.
  • Learn to use objdump, it is a great help with many debugging problems.
You may also have mis-edited some code. Never say "it's like that, just different"...
Last edited by Solar on Fri Dec 08, 2006 5:19 am, edited 1 time in total.
Every good solution is obvious once you've found it.
urxae
Member
Member
Posts: 149
Joined: Sun Jul 30, 2006 8:16 am
Location: The Netherlands

Post by urxae »

My educated guess: You forgot to add .rodata to your linker script (you are using a linker script, aren't you?)

That would be the first option Solar mentioned, by the way.
And I second his suggestion to learn to use objdump, it's a very useful tool.
chorakm
Posts: 14
Joined: Fri Dec 08, 2006 12:07 am

Great!

Post by chorakm »

That is getting me on the right track! I searched google high and low for documentation on ld scripts and the different sections. I'm assuming rodata is read only data but I'm having trouble finding any documentation on explanations of the different sections, and generally how to create linker scripts in general. If anyone could point me to some resources that would be great. I.e. How did you come across the knowledge of the different sections?
chorakm
Posts: 14
Joined: Fri Dec 08, 2006 12:07 am

Woooh!

Post by chorakm »

Guys I have to thank you. You steered me in the right direction about the rodata section. I added that, my kernel compiles correctly, and can display text onto the string! Woooh exciting! Hahah, thanks a lot guys!
Post Reply