flat assembler
Message board for the users of flat assembler.
Index
> OS Construction > Another Pmode Problem... Please Help! |
Author |
|
UCM 23 Aug 2005, 18:19
Don't you use cli to stop interrupts?
_________________ This calls for... Ultra CRUNCHY Man! Ta da!! *crunch* |
|||
23 Aug 2005, 18:19 |
|
MialyGK 23 Aug 2005, 18:32
UCM wrote: Don't you use cli to stop interrupts? Wow, too Fast post... I use CLI in boot and the kernel, but the problem still over there... |
|||
23 Aug 2005, 18:32 |
|
smiddy 23 Aug 2005, 19:03
Reposition _protect: under bits 32, not that that is the problem, but that glares at me. The reason is you're jumping to 32-bits and when the label _protect: is in 16-bits it just doesn't seem right.
Your GDTR doesn't look right either: Code: GDTR: dw GDTEnd - GDT - 1 dd GDT In yours it is only 5 bytes, and it should be 6. The first word should be the size in bytes. So you should be able to change it to: Code: set_gdt: ; db 0x20 Commented out this BAD code. dw set_gdt - gdt - 1 dd gdt I hope that gets you squared away! |
|||
23 Aug 2005, 19:03 |
|
Artlav 23 Aug 2005, 19:07
Try removing [org 0x10000] from under the [BITS 16] and putting it under the [BITS 32].
And GDT looks suspicious... |
|||
23 Aug 2005, 19:07 |
|
MialyGK 24 Aug 2005, 05:17
smiddy wrote: Reposition _protect: under bits 32, not that that is the problem, but that glares at me. The reason is you're jumping to 32-bits and when the label _protect: is in 16-bits it just doesn't seem right. Artlav wrote: Try removing [org 0x10000] from under the [BITS 16] and putting it under the [BITS 32]. I try but don't work Help |
|||
24 Aug 2005, 05:17 |
|
Artlav 24 Aug 2005, 06:36
Ok, runned this through a debugger.
1. Right GDT: db 0xFF,0xFF ;# Limit FFFF db 0x00,0x00 ;# Base Low db 0x00,0x9A ;# Base med,Type Code db 0xCF,0x00 ;# Access, base high db 0xFF,0xFF ;# Limit FFFF db 0x00,0x00 ;# Base Low db 0x00,0x92 ;# Base med,Type Data db 0xCF,0x00 ;# Access, base high set_gdt: dw set_gdt-gdt-1 dd gdt The problem here is Base med byte, which was 0x09 instead of 0, which gave 0x00090000 base address insted of 0x00000000. And set_gdt, db 0x20 <-- The size is a word, not byte dd gdt 2. [org 0x10000] Should be under [Bits 32] to link the latter code for flat 0x10000. 3. Typo - line 63: mov ax,10 Selector is 0x10 instead of 10. |
|||
24 Aug 2005, 06:36 |
|
MialyGK 24 Aug 2005, 10:38
Thanks all!
This is my modifications of: boot code (last lines): Code: ORG 0x7c00 BITS 16 CPU 386 jmp _main ;######################### ;# Structure of boot: Signature db 'lofs' Fs_Version db 0,0,0,1 Loading db 'Loading',10,13,0 Need386 db 13,10,'386+ CPU required.',0 ErrorMsg db 13,10,'Error: ',0 HexDig db '0123456789ABCDEF' Drive db 0x00 MaxSectors db 0x00 MaxHeads db 0x00 ;######################### ;# Function: _print ;# In: DS:SI := ASCIIz string ;# Out: <none> ;# Require: push AX,BX _print: lodsb ;# load DS:SI into AL or al,al ;# if (AL==0) ... jz .1 ;# ... goto 1 mov ah,0x0E ;# func. #0E (BIOS) mov bx,0100 ;# text page int 0x10 ;# BIOS interrupt jmp _print ;# Next Letter .1: ret ;# return _end_print: ;######################### ;# Function: _puthex ;# In: CL:=Code ;# Out: <none> ;# Require: BX,AX _puthex: push cx ;# Save original Code (xxxxyyyy) shr cl,4 ;# xxxxyyyy >> 4 = 0000xxxx and cx,0x000F ;# 000000000000xxxx call .1 ;# print hex. number pop cx ;# Load Code and cx,0x000F ;# 000000000000yyyy call .1 ;# print hex. number ret ;# return .1: mov bx,cx ;# bx = cx mov al,[HexDig+bx] ;# bx+HexDig = ASCII Number mov ah,0x0E ;# BIOS 0x0E (print char) xor bx,bx ;# page 0, attribute 0 int 0x10 ;# and print ret ;# return ;######################### ;# Function: _inc_CHS ;# In: cx,dh = CHS ;# Out: cx,dh = CHS _inc_CHS: mov al,cl ;# save sector and high cylinder and cl,0x3F ;# cl = 00ssssss s=sector and al,0xC0 ;# al = cc000000 c=cylinder inc cl ;# cl++; cmp cl,[MaxSectors] ;# if cl<MaxSector jna .1 ;# jump to .1 mov cl,1 ;# else cl = sector 1 inc dh ;# and dh(head)++ cmp dh,[MaxHeads] ;# if dh<MaxHeads jna .1 ;# jump to .1 xor dh,dh ;# else dh=0 inc ch ;# ch(low Cylinder)++ jno .1 ;# jump if no overflow (else ch=0) add al,0x40 ;# else al+= c1000000 c=cylinder .1: or al,cl ;# and 00ssssss | cc000000 = ccssssss (new CHS) ret ;# and return ;######################### ;# Function: _readsector ;# In: si:= number of sectors ;# cx, dh = CHS ;# Out: es:bx:=Load Data from Diskette _readsector: jmp .2 ;# readsector normal .1: xor ax,ax ;# reset drive mov dl,[Drive] ;# dl=drive number (0=A, 1=B) int 0x13 ;# BIOS execute jc .3 ;# if(CF == 1) erorr() .2: mov bx,di ;# ES:BX = Address to write mov ax,0x0201 ;# read one sector int 0x13 ;# BIOS interrupt jc .1 ;# if CF == 1 error() mov ax,0x0E2E ;# print '.' xor bx,bx ;# clear attributes int 0x10 ;# and print call _inc_CHS ;# for next -> CHS++ add di,512 ;# di+=512 next sector dec si ;# number of sectors jnz .2 ;# if sectors != 0 jump .2 ret ;# return .3: jmp _error ;# go to error _end_readsector: ;######################### ;# Function: _error ;# In: ax:=error code ;# Out: <none> ;# Require: 'ErrorMsg' string _error: push ax ;# save ax mov si,ErrorMsg ;# print call _print ;# 'Error' msg pop ax ;# load ax push ax ;# save ax mov cl,ah ;# cl=high byte call _puthex ;# from Code pop ax ;# load ax mov cl,al ;# cl=low byte call _puthex ;# from Code xor ax,ax ;# wait for int 0x16 ;# ... key press jmp 0xFFFF:0x0000 ;# Restart in real mode hlt ;# halt if have error with the restart ;######################### ;# Function: _detectcpu ;# In: <none> ;# Out: <none> ;# Require: Global variable ;# Need386 _detectcpu: ;# detect for 8086/88 (flags 12-15 will be set) pushf ;# Save flags to stack xor ah,ah ;# AH:=0 push ax ;# Save AX to stack popf ;# load word from stack pushf ;# Save flags to stack pop ax ;# and load to AX and ah,0xf0 ;# check if bits 12-15 are set cmp ah,0xf0 ;# if AH = 11110000 je .1 ;# jump if yes (i.e. is 8086/8 ;# detect for 286 (flags 12-15 not will set) mov ah,0xf0 ;# AH:=11110000 push ax ;# save ax into stack popf ;# and load into flags pushf ;# save flags into flags pop ax ;# load word into stack and ah,0xf0 ;# AH & 11110000 = 00000000 jz .1 ;# jump if zero (i.e. is 286) popf ;# load word into flags ret ;# else CPU is 386+ .1: mov si,Need386 ;# Print text for Not Found CPU 80386 call _print ;# jmp _error ;# and jump to _error ;######################### ;# main() function: _main: mov ax,cs ;# AX:=Loading boot mov ds,ax ;# DS:=AX cli ;# clear interrupt flag (protect SS) mov ax,0x8000 ;# AX:=stack mov ss,ax ;# SS:=80000 mov sp,0xFFFF ;# SP:=FFFF => stack:=8FFFF sti ;# set interrupt flag mov es,ax ;# AX:=buffer of kernel sectors mov [Drive],dl ;# Save Currect Drive mov ah,0x08 ;# Get Info int 0x13 ;# From BIOS jc _error ;# if (CF==1) goto error and cl,0x3F ;# Clear high Cylinder mov [MaxSectors],cl ;# and save mov [MaxHeads],dh ;# Heads save mov si,Loading ;# print call _print ;# on screen call _detectcpu ;# Detecting CPU for 386+ _loading: mov cx,0x0002 ;# CHS = 0,0,2 (skip boot sector) xor dh,dh ;# Head = 0 mov dl,[Drive] ;# DL:= Drive Number (0-A, 1-B) mov si,0x40 ;# 40H:=64 mov ax,0x1000 ;# destination mov es,ax ;# segment - es:bx xor bx,bx ;# bx must be 0 xor di,di ;# di->bx call _readsector ;# read! ;# ************************************** ;# Start modifing here.... floppy_off: mov dx, 0x3F2 mov al, 0 out dx, al ;# Enable A20 Gate in al,0x92 or al,2 out 0x92,al _set_pmode: cli lgdt [gdtr] mov eax,cr0 or al,1 mov cr0,eax jmp 0x08:_pmode use32 _pmode: mov ax,0x10 mov ds,ax mov ss,ax mov es,ax mov fs,ax mov gs,ax mov esp,0xFFFC jmp 0x08:0x10000 ;# jump to kernel ;# mov si,ErrorMsg ;;; removing this ;# call _print ;;; and this hlt ;# System halt jmp $ ;# Forever Cycle gdt: dw 0x0000, 0x0000, 0x0000, 0x0000 codesel: dw 0xFFFF, 0x0000, 0x9800, 0x00CF datasel: dw 0xFFFF, 0x0000, 0x9200, 0x00CF gdt_end: gdtr: dw gdt_end - gdt - 1 dd gdt times 0x1fe-($-$$) db 0x90 ;# all "unused" bytes - NOP dw 0xAA55 ;# signature for correct boot and Kernel code: Code: Bits 32 ;# here org 0x10000 jmp _start gdt: db 0,0,0,0,0,0,0,0 db 0xFF,0xFF ;# Limit FFFF db 0x00,0x00 ;# Base Low db 0x00,0x9A ;# Base med,Type Code db 0xCF,0x00 ;# Access, base high ;# modifing ... ^^^^^^^^^^^^^ db 0xFF,0xFF ;# Limit FFFF db 0x00,0x00 ;# Base Low db 0x00,0x92 ;# Base med,Type Data db 0xCF,0x00 ;# Access, base high set_gdt: dw set_gdt - gdt - 1 dd gdt Text db 'Switching to Protect Mode... [ok]',0 ;# Just Work! cursor dd 0 _start: ;# removing the previous code... lgdt [set_gdt] mov ecx,cr0 or cl,1 mov cr0,ecx mov ax,0x10 mov ds,ax mov es,ax mov fs,ax mov ss,ax mov esp,0x90000 jmp 0x08:_protect _protect: mov esi,Text call kputs quit: halt jmp short $ kputs: pusha .loop: lodsb test al, al jz quit mov ecx, [cursor] mov [0xB8000+ecx*2], al inc dword [cursor] jmp short .loop LokiOS (official name ) works!!! I am happy! Thank's all for the help! (and source code of BOS v0.3!) |
|||
24 Aug 2005, 10:38 |
|
hendryten 19 Sep 2005, 11:49
hello all...
I wanna ask about the LIMIT field of the GDT/LDT... say, if I have the LIMIT field set to 0xFFFF (including the Granularity), what would it means?? the limit of the entry is 0xFFFF bytes? or the limit of the entry is below address 0xFFFF ??? thx... _________________ If you want everything, you'll end up with nothing |
|||
19 Sep 2005, 11:49 |
|
bubach 20 Sep 2005, 16:43
One GDT selector doesn't have enougth space to hold the entire limit address, so what the granularity bit does is that it multiplices the specified limit with 4kb if it's on.
See here for more information: http://osdever.net/tutorials/brunmar/tutorial_02.php?the_id=18 |
|||
20 Sep 2005, 16:43 |
|
hendryten 21 Sep 2005, 04:24
bubach wrote: One GDT selector doesn't have enougth space to hold the entire limit address, so what the granularity bit does is that it multiplices the specified limit with 4kb if it's on. that's not excatly what i'm asking...thx anyway.... What I'm asking is what the LIMIT field means....does it represent the highest address possible or number of bytes possible.... sorry...i don't speak english well... _________________ If you want everything, you'll end up with nothing |
|||
21 Sep 2005, 04:24 |
|
Octavio 21 Sep 2005, 09:53
hendryten wrote: What I'm asking is what the LIMIT field means....does it represent the highest address possible or number of bytes possible.... number of bytes+1 or number of 4KB blocks+1 |
|||
21 Sep 2005, 09:53 |
|
hendryten 24 Sep 2005, 11:20
i see....thx thx!!
_________________ If you want everything, you'll end up with nothing |
|||
24 Sep 2005, 11:20 |
|
< Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2024, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.