Page 1 of 1
Check if cross compiler broken? 40kb .img file
Posted: Wed Feb 09, 2022 10:58 am
by Paletech35
I ve been trying to write an OS for raspberry pi, and I made a cross compiler exactly as described on the wiki with arm-none-eabi as the target. Everything has been working until now, when I am trying to implement interrupts. I noticed when I first compiled the rPi bare bones example it had a size of 40kb, which I though was too large, but It seemed to work. Now when I am trying to implement interrupts, I was not getting the expected result and have determined that my interrupts handler function in irq_handler.c is not running. Is it possible that I messed up my cross compiler, or are there any other issues that could cause this? I think possibly the exception vector table isnt truly being moved to the beginning of memory. Code is at
github in case that helps, I am running it on a raspberry pi model 1. Thanks!
Re: Check if cross compiler broken? 40kb .img file
Posted: Wed Feb 09, 2022 11:33 am
by Octocontrabass
You're right, it's too large. There's a huge block of extra padding that causes your kernel to be loaded at the wrong address, so your exception vectors don't point to your kernel.
I notice the wiki uses "-fpic", but this should be completely unnecessary as long as the kernel is loaded at the correct address. Did the author of that article have the same issue and simply not notice?
Remove "-fpic" from all commands in your makefile. Add "-Wl,-z,max-page-size=0x1000" to your link command.
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 10:50 am
by Paletech35
Thanks, I have removed all -fpic options and added the -Wl options, but the .img file is only a couple hundred bytes smaller now, and interrupts still aren't working. Is there anything else that could be causing this? Having looked at the sizes of all the files, I noticed that boot.S compiled into 33696 bytes as boot.o, and all other files are a reasonable size. I imagine this is what's causing the issues. The contents of boot.S are exactly as on the wiki.
EDIT: I noticed that the linker was putting boot.o at 0x8000 which then contained 0x8000 of padding. I removed the padding, and boot.o is still almost 1kb, bigger than boot.S, which still seems off to me, and interrupts still dont work
. The .img file is only 14kb now tho
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 1:16 pm
by Paletech35
Would it be possible to create a new section in the linker, and make my exception vector table in a .S file that gets put in the new section? Then I just place the new section at 0x0000 before the rest of the kernel is loaded at 0x8000? Something like:
linker.ld:
Code: Select all
ENTRY(_start)
SECTIONS
{
.vectable:
{
*(.vectable)
}
. = 0x8000;
__start = .;
__text_start = .;
.text :
{
KEEP(*(.text.boot))
*(.text)
}
. = ALIGN(4096); /* align to page size */
__text_end = .;
...
__end = .;
}
exception_vector.S:
Code: Select all
.section "vectable"
ldr pc, res_abs_addr
ldr pc, undef_abs_addr
ldr pc, swi_abs_addr
ldr pc, prefetch_abort_abs_addr
ldr pc, data_abort_abs_addr
nop
ldr pc, irq_abs_addr
ldr pc, fiq_abs_addr
res_abs_addr: .word reset_handler
undef_abs_addr: .word undefined_instruction_handler
swi_abs_addr: .word swi_handler
prefetch_abort_abs_addr: .word prefetch_abort_handler
data_abort_abs_addr: .word data_abort_handler
irq_abs_addr: .word irq_handler_wrapper
fiq_abs_addr: .word fiq_handler
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 1:27 pm
by Octocontrabass
Paletech35 wrote:I removed the padding, and boot.o is still almost 1kb, bigger than boot.S, which still seems off to me, and interrupts still dont work
. The .img file is only 14kb now tho
Hmm, that should fix the problem. I'll have to take another look.
Paletech35 wrote:Would it be possible to create a new section in the linker, and make my exception vector table in a .S file that gets put in the new section? Then I just place the new section at 0x0000 before the rest of the kernel is loaded at 0x8000?
No. If you do that, the new section will be loaded at 0x8000, and your kernel won't work.
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 1:48 pm
by Paletech35
Octocontrabass wrote:
Paletech35 wrote:Would it be possible to create a new section in the linker, and make my exception vector table in a .S file that gets put in the new section? Then I just place the new section at 0x0000 before the rest of the kernel is loaded at 0x8000?
No. If you do that, the new section will be loaded at 0x8000, and your kernel won't work.
Isnt that what the linker is for? I would just add the new section BEFORE using . = 0x8000; in the linker, so the new section is loaded at 0x0000 then .text.data is loaded at 0x8000 as per usual since it is after the . = 0x8000; command in linker.ld. Something like:
Code: Select all
. = 0x0000;
//add .vectable section
. = 0x8000;
//add the rest of the sections
I tried it and the kernel still boots up, although interrupts still dont work
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 2:27 pm
by Paletech35
Out of curiosity, I compiled an empty .S file with my cross compiler and the .o file came to 548 bytes. I assume this is because its including references to libraries or something. Either way, it seems too big to me, and I think it could be because my I compiled my cross compiler incorrectly, as it shouldnt contain any references to any libraries since it is a cross compiler and I havent linked to any of my own code. Is there anyway to test if it is broken/ compiling for userspace code? The only other error I can currently see is if my exception vector table isnt really being moved to the beginning of memory. Are there any easy ways I can check this? Thanks
Re: Check if cross compiler broken? 40kb .img file
Posted: Fri Feb 11, 2022 2:59 pm
by Octocontrabass
Paletech35 wrote:Isnt that what the linker is for? I would just add the new section BEFORE using . = 0x8000; in the linker, so the new section is loaded at 0x0000 then .text.data is loaded at 0x8000 as per usual since it is after the . = 0x8000; command in linker.ld.
No. The linker does not control where the kernel binary will be loaded. The kernel binary will always be loaded at 0x8000.
Paletech35 wrote:Out of curiosity, I compiled an empty .S file with my cross compiler and the .o file came to 548 bytes.
That sounds normal to me.
Paletech35 wrote:The only other error I can currently see is if my exception vector table isnt really being moved to the beginning of memory. Are there any easy ways I can check this?
Run it in QEMU and use a debugger. Although, you haven't actually described what's not working - are you sure interrupts are happening at all? Maybe see if SWI calls the handler before trying hardware interrupts.