Author Topic: need help understanding  (Read 4084 times)

nobody

  • Guest
need help understanding
« on: October 12, 2004, 10:00:32 PM »
i found this code online and was trying it out to try and get a better understanding of programming boostraps and going into protected mode... only problem is the code for going into pmode seems to triple fault the processor and reset it. would anyone know how to fix this?

here is the code:

; Some compiler directives
[ORG 7C00h] ; BIOS puts us here
[BITS 16] ; The instructions below are 16-bit

start:

; -------------------------------------------------------
; Load a binary file off the disk
; -------------------------------------------------------

.reset:
mov ah, 0 ; Reset the floppy
int 13h ;
jc .reset ; Failed -> Try again

.read:
mov ax, 0 ; ES:BX = 0000:8000h
mov es, ax ;
mov bx, 8000h ;
mov ah, 2 ; Load data
mov al, 5 ; Read 5 sectors
mov ch, 0 ; Cylinder = 0
mov cl, 2 ; Sector = 2
mov dh, 0 ; Head = 0
mov dl, 0 ; Drive = A:
int 13h ;
jc .read ; Failed -> Try again



; -------------------------------------------------------
; Goto protected mode
; -------------------------------------------------------
lgdt [gdtr]

mov eax, cr0
or al, 1
mov cr0, eax

jmp SYS_CODE_SEL:do_pm

[BITS 32] ; All code from now on will be 32-bit

do_pm:

mov ax, SYS_DATA_SEL ; Update the segment registers
mov ds, ax ; To complete the transfer to
mov es, ax ; 32-bit mode
mov ss, ax

; Update ESP
mov esp, 9000h

; -------------------------------------------------------
; Execute the binary file that was loaded previously
; -------------------------------------------------------

jmp 08000h


gdtr:
dw gdt_end - gdt - 1 ; GDT limit
dd gdt ; GDT base

; -----------------------------------------------
; GDT
; -----------------------------------------------
gdt:
times 8 db 0 ; NULL Descriptor

SYS_CODE_SEL equ $-gdt
dw 0xFFFF ; limit 15:0
dw 0 ; base 15:0
db 0 ; base 23:16
db 0x9A ; type = present, ring 0, code, non-conforming, readable
db 0xCF ; page granular, 32-bit
db 0 ; base 31:24

SYS_DATA_SEL equ $-gdt
dw 0xFFFF ; limit 15:0
dw 0 ; base 15:0
db 0 ; base 23:16
db 0x92 ; type = present, ring 0, data, expand-up, writable
db 0xCF ; page granular, 32-bit
db 0 ; base 31:24

gdt_end:

thanks

nobody

  • Guest
Re: need help understanding
« Reply #1 on: October 13, 2004, 04:16:03 AM »
actually i found better code... it's just there is one part i do not understand. where did the 08h come from for the code segment in the jump before the 32 bit section? does anyone know?


 [BITS 16]       ; We need 16-bit intructions for Real mode

[ORG 0x7C00]    ; The BIOS loads the boot sector into memory location 0x7C00

cli                     ; Disable interrupts, we want to be alone

xor ax, ax
        mov ds, ax              ; Set DS-register to 0 - used by lgdt

lgdt [gdt_desc]         ; Load the GDT descriptor

mov eax, cr0            ; Copy the contents of CR0 into EAX
        or eax, 1               ; Set bit 0
        mov cr0, eax            ; Copy the contents of EAX into CR0
            **WHERE DOES THAT COME FROM GHAAAAAA**
        jmp 08h:clear_pipe      ; Jump to code segment, offset clear_pipe


[BITS 32]                       ; We now need 32-bit instructions
clear_pipe:
        mov ax, 10h             ; Save data segment identifyer
        mov ds, ax              ; Move a valid data segment into the data segment register
        mov ss, ax              ; Move a valid data segment into the stack segment register
        mov esp, 090000h        ; Move the stack pointer to 090000h

mov byte [ds:0B8000h], 'p'      ; Move the ASCII-code of 'P' into first video memory
        mov byte [ds:0B8001h], 1Bh      ; Assign a color code


hang:
        jmp hang                ; Loop, self-jump


gdt:                    ; Address for the GDT

gdt_null:               ; Null Segment
        dd 0
        dd 0

gdt_code:               ; Code segment, read/execute, nonconforming
        dw 0FFFFh
        dw 0
        db 0
        db 10011010b
        db 11001111b
        db 0

gdt_data:               ; Data segment, read/write, expand down
        dw 0FFFFh
        dw 0
        db 0
        db 10010010b
        db 11001111b
        db 0

gdt_end:                ; Used to calculate the size of the GDT



gdt_desc:                       ; The GDT descriptor
        dw gdt_end - gdt - 1    ; Limit (size)
        dd gdt                  ; Address of the GDT




times 510-($-$$) db 0           ; Fill up the file with zeros

dw 0AA55h                ; Boot sector identifyer

Offline Frank Kotler

  • NASM Developer
  • Hero Member
  • *****
  • Posts: 2358
  • Country: us
Re: need help understanding
« Reply #2 on: October 13, 2004, 05:36:42 AM »
I was going to guess that not setting ds to zero was the problem with the original code...

The "8" that you move into cs (via the far jump) is the index into the gdt of the code descriptor... as "10h" that you move into ds (after the jump to pm) is the index (selector) to the data descriptor.

Best,
Frank

nobody

  • Guest
Re: need help understanding
« Reply #3 on: October 14, 2004, 05:47:31 AM »
i was messing with the code and tried to both load it from a floppy and then go into protected mode as well as loading a program off a floppy going into proteced mode and then jumping to the program... but the code causes the cpu to reset around the time the cr0 register is set... the code works fine if i leave it as is and dont laod anything from the floppy... any idea what's going on?