Broken Newlib Program
Posted: Sat Apr 21, 2018 5:59 pm
For the last few months, I've been trying to fix the newlib port for BareMetal OS.
It has been very frustrating.
I was hoping to get some troubleshooting suggestions.
Currently, the newlib test program is loaded into the address 0xffff800000000000.
This may be significant or it may not be. I had to add the option '-mcmodel=large' to GCC for the program sources (including newlib.)
I've tested the same program running at 16 MiB (0x1000000), and the same problem occurs.
When I open up GDB and view the execution steps, I found that the program crashes when the reentrant structure is dereferenced.
The reentrant structure is declared as a static global variable, and has the address 0xffff80000001b340. It is referenced by the
function __getrent(), and by the variable _impure_ptr.
I looked at the disassembly when the structure gets dereferenced, and it appears that the address that is returned is a wild pointer.
I found out that the wild pointer is actually the first eight bytes of the address 0x00, so that tells me there might be a null pointer somewhere.
There are other programs in C and assembly that don't use newlib, and they load and execute just fine.
I noticed that the only difference between the newlib program and the programs that work is that the newlib program has a .got section, and the other ones don't.
But I thought that statically linked executables that are not position independent don't need to be modified before they are loaded (meaning no relocations.)
I verified that there are no relocations with the command.
I wrote a program that writes to and reads from the same point int memory, 0xffff80000001b340, and it works fine.
I did that just in case that the memory was not properly mapped there, but it looks like it is mapped just fine.
I'm really just looking for troubleshooting tips here, I don't want to ask anyone to debug the project.
But in case you want to look at the code, here's the link to the newlib port.
https://github.com/ReturnInfinity/BareM ... e-addr-fix
Note that it's in the large-addr-fix branch (although I no longer think the large address is the problem anymore.)
Thanks in advance for anyone who has read this far!
Edit I forgot to mention, currently programs use the same stack as the one in the kernel.
It has been very frustrating.
I was hoping to get some troubleshooting suggestions.
Currently, the newlib test program is loaded into the address 0xffff800000000000.
This may be significant or it may not be. I had to add the option '-mcmodel=large' to GCC for the program sources (including newlib.)
I've tested the same program running at 16 MiB (0x1000000), and the same problem occurs.
When I open up GDB and view the execution steps, I found that the program crashes when the reentrant structure is dereferenced.
The reentrant structure is declared as a static global variable, and has the address 0xffff80000001b340. It is referenced by the
function __getrent(), and by the variable _impure_ptr.
I looked at the disassembly when the structure gets dereferenced, and it appears that the address that is returned is a wild pointer.
I found out that the wild pointer is actually the first eight bytes of the address 0x00, so that tells me there might be a null pointer somewhere.
There are other programs in C and assembly that don't use newlib, and they load and execute just fine.
I noticed that the only difference between the newlib program and the programs that work is that the newlib program has a .got section, and the other ones don't.
But I thought that statically linked executables that are not position independent don't need to be modified before they are loaded (meaning no relocations.)
I verified that there are no relocations with the command.
Code: Select all
readelf --relocs test.app
I did that just in case that the memory was not properly mapped there, but it looks like it is mapped just fine.
I'm really just looking for troubleshooting tips here, I don't want to ask anyone to debug the project.
But in case you want to look at the code, here's the link to the newlib port.
https://github.com/ReturnInfinity/BareM ... e-addr-fix
Note that it's in the large-addr-fix branch (although I no longer think the large address is the problem anymore.)
Thanks in advance for anyone who has read this far!
Edit I forgot to mention, currently programs use the same stack as the one in the kernel.