Reputation: 16724
I am writing a simple kernel in C and ASM(to call assembly instructions generated by C compile). I am following this excellent articles from osdev.org. After read an kernel written in assembly and compiled and executed, it was worked fine, I see the kernel.bin running on qemu, fantastic. But I want really to write it in C. I found an example in same web page.
I compiled it and tried run the kernel.bin on qemu but I get "boot failed" from all devices: hard disk, floopd and CD-rom. then I disassembled the kernel.bin generated by ks.o (kernel.asm assembled using nasm) and kernel.o (kernel.c assembled using gcc) assembled to bin file using the ld. The kernel.bin:
http://pastebin.com/Y0pLFvij I can't see my string or any instruction to assembly write my string on video.
The C code that generate it:
#define WHITE_TXT 0x07 // white on black text
unsigned int k_printf(char *message, unsigned int line);
void k_clear_screen();
k_main()
{
k_clear_screen();
k_printf("Hi!\nHow's this for a starter OS?", 0);
};
unsigned int k_printf(char *message, unsigned int line) // the message and then the line #
{
char *vidmem = (char *) 0xb8000;
unsigned int i=0;
i=(line*80*2);
while(*message!=0)
{
if(*message=='\n') // check for a new line
{
line++;
i=(line*80*2);
*message++;
} else {
vidmem[i]=*message;
*message++;
i++;
vidmem[i]=WHITE_TXT;
i++;
};
};
return(1);
};
void k_clear_screen() // clear the entire text screen
{
char *vidmem = (char *) 0xb8000;
unsigned int i=0;
while(i < (80*25*2))
{
vidmem[i]=' ';
i++;
vidmem[i]=WHITE_TXT;
i++;
};
and the assembly
that call it:
[bits 32]
[global start]
[extern k_main] ; this is in the c file
start:
call k_main
cli ; stop interrupts
hlt ; halt the CPU
the link.ld
OUTPUT_FORMAT("binary")
ENTRY(start)
SECTIONS
{
.text 0x100000 : {
code = .; _code = .; __code = .;
*(.text)
. = ALIGN(4096);
}
.data : {
data = .; _data = .; __data = .;
*(.data)
. = ALIGN(4096);
}
.bss :
{
bss = .; _bss = .; __bss = .;
*(.bss)
. = ALIGN(4096);
}
end = .; _end = .; __end = .;
}
and the makefile:
bin:
nasm -f aout -o ks.o kernelbase.asm
gcc -Wall -c -o kernel.o kernel.c
ld -T link.ld -o kernel.bin ks.o kernel.o
run1:
qemu kernel.bin
clear:
rm -f *.o
cbin:
rm -f *.bin
and the kernel in pure assembly, disassembled: http://pastebin.com/Bkvkq3YQ that worked fine for me, and I can see the instrutions to write on video.
My OS: Ubuntu 10.4
Compiler: gcc
Assembler : NASM
Where am I wrong?
Upvotes: 1
Views: 655
Reputation: 14792
I tried to do that tutorial and the code failed too. Finally I did this:
Compile both files for 32 bit:
nasm -f elf32 ks.asm -o kernelbase.o
gcc -m32 -c kernel.c -o kernel.o
And link:
gcc -m32 kernelbase.o kernel.o -o Kernel.bin
After a while I found out that I don't get any errors by using gcc for linking.
Hope I helped :-)
Upvotes: 1