booting a simple kernel with grub

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
anon19287473
Member
Member
Posts: 97
Joined: Thu Mar 15, 2007 2:27 pm

booting a simple kernel with grub

Post by anon19287473 »

I pulled together a small kernel, which sets up a gdt and prints some stuff on the screen, and it is a valid multboot elf file, which grub recognizes, however, when I boot it, I don't see the character being printed, I've attached the code. I've tried everything I can think of, I just can't figure out the problem. (Note, this is my first attempt at a protected mode OS, cut me some slack if its a stupid mistake).

EDIT: I've also attached the ld script I used.

I compiled it with the following commands:

Code: Select all

nasm -f elf -o kernel.o kernel.asm
ld -T kernel.ld kernel.o
Thanks in advance.
Attachments
kernel.ld
The ld script I used
(332 Bytes) Downloaded 54 times
kernel.asm
The tiny "kernel"
(915 Bytes) Downloaded 22 times
User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Post by Combuster »

The problem is probably here:

Code: Select all

mov word [gs:0xb800], 0x641
I think you confused realmode segments with linear offsets. The correct address is

Code: Select all

mov word [gs:0xb8000], 0x641
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
anon19287473
Member
Member
Posts: 97
Joined: Thu Mar 15, 2007 2:27 pm

Post by anon19287473 »

Thanks, I'll try that. Still getting used to the whole protected mode thing :)
anon19287473
Member
Member
Posts: 97
Joined: Thu Mar 15, 2007 2:27 pm

Post by anon19287473 »

Nope :( , it still does't work. Any other ideas?
jnc100
Member
Member
Posts: 775
Joined: Mon Apr 09, 2007 12:10 pm
Location: London, UK
Contact:

Post by jnc100 »

Your gdt is wrong:

Code: Select all

gdt:
	;; NULL descriptor
	TIMES 8 db 0

	;; Unused descriptor
	TIMES 9 db 0
the second one I guess is a typo, try TIMES 8 db 0 like previously.

Also,

Code: Select all

DATA_SEL equ $-gdt
	dw 0xffff
	dw 0
	db 0
	db 0x92
	db 0xcf
	db 0
DATA_SEL isn't the correct selector for that descriptor - you need to use, as its the third entry (entry number 2 in a zero-based list):

2 << 3 + RPL, where I assume RPL for you is 0
= 0x10

Plus keep the fix Combuster posted.

Regards,
John.
anon19287473
Member
Member
Posts: 97
Joined: Thu Mar 15, 2007 2:27 pm

Post by anon19287473 »

I made those changes and it still won't work :(

Code: Select all

[BITS 32]
section .text
global start
start:
	; mov esp, sys_stack
	
	lgdt [gdtr]
	mov ax, DATA_SEL
	mov ds, ax
	mov es, ax
	mov ss, ax
	mov fs, ax
	mov gs, ax

	mov word [gs:0xb8000], 0x641
	
	jmp $
	
	MULTIBOOT_PAGE_ALIGN	equ 1<<0
	MULTIBOOT_MEMORY_INFO	equ 1<<1

	MULTIBOOT_HEADER_MAGIC equ 0x1BADB002
	MULTIBOOT_HEADER_FLAGS equ MULTIBOOT_PAGE_ALIGN | MULTIBOOT_MEMORY_INFO
	CHECKSUM equ -(MULTIBOOT_HEADER_MAGIC + MULTIBOOT_HEADER_FLAGS)

	;; The Multiboot header
	align 4 
	dd MULTIBOOT_HEADER_MAGIC
	dd MULTIBOOT_HEADER_FLAGS
	dd CHECKSUM

section .data

[BITS 16]
	
gdtr:
	dw gdt_end - gdt - 1
	dd gdt

gdt:
;; NULL descriptor
	dw 0
	dw 0
	db 0
	db 0
	db 0
	db 0	

;; Unused descriptor
	dw 0
	dw 0
	db 0
	db 0
	db 0
	db 0

CODE_SEL equ $-gdt
	dw 0xFFFF
	dw 0
	db 0
	db 0x9A
	db 0xCF
	db 0

DATA_SEL equ $-gdt
	dw 0xFFFF
	dw 0
	db 0
	db 0x92
	db 0xCF
	db 0
gdt_end:

[BITS 32]
		
SECTION .bss
	resb 8192		; Reserve 8KBytes of memory for the stack
sys_stack:
With the same linker script. Note: I wrote out the empty GDT sels, to avoid similar problems :)
jnc100
Member
Member
Posts: 775
Joined: Mon Apr 09, 2007 12:10 pm
Location: London, UK
Contact:

Post by jnc100 »

Just noted in your linker script you're relocating to 0xc0000000. This means that the executable you're creating is expecting to be run at address 0xC0000000, whereas by the AT directive you're informing grub to actually load the sections at 0x100000. This means the memory access to load your gdt is wrong.

If you really want a higher half kernel, I suggest you follow the instructions in Higher Half With GDT. You'll note that it defines a special section in the output, called .setup, which contains the gdt to be loaded, and specifies both the virtual and physical addresses to be at 1MB, whereas the rest of the sections (.text, .data and .bss) are loaded above 1MB but relocated to above 0xc0000000.

Regards,
John.
Post Reply