Page 1 of 1

raw temp paging

Posted: Sun Aug 07, 2005 8:14 pm
by GLneo
im going to try to set up paging in my boot sector kinda like i did my gdt, in raw "db 10010010b"'s but is it posible for paging (0x1000 to vurtual 0xC0000000) example might help, thx :)

Re:raw temp paging

Posted: Sun Aug 07, 2005 8:21 pm
by AR
You'd need 0x1000 bytes (4096) per page dir and table (so no), but if you want to generate it then that is more plausible, but not within the 512 byte bootsector, you will need a second stage (or at least a longer first stage) to fit all the required code.

Re:raw temp paging

Posted: Sun Aug 07, 2005 8:26 pm
by Warrior
Is it possible to load your kernel and call "main()" already
then setup the virtual location of the kernel in the address space of every process as opposed to doing it earlier on in assembly?
I mean assuming it's one of the first things you do, I don't see any problem with it.

Re:raw temp paging

Posted: Sun Aug 07, 2005 8:37 pm
by GLneo
if my kernel was at 0x1000 and the durring system calls at 0xC0000000 wont my kernel have to be linked to two places???

Re:raw temp paging

Posted: Sun Aug 07, 2005 9:54 pm
by Brendan
Hi,
GLneo wrote:if my kernel was at 0x1000 and the durring system calls at 0xC0000000 wont my kernel have to be linked to two places???
Yes, but it can be avoided.

If you setup some descriptors in the GDT with limit = 4 GB and base = 0x40001000, then an offset of 0xC0000000 would become a physical address of 0xC0000000 + BASE = 0x0000000100001000, which doesn't fit in 32 bits and is truncated to 0x00001000.

Once you setup paging and map the kernel to 0xC0000000 you'd switch to normal descriptors (with base = 0x00000000). From here on an offset of 0xC0000000 would become 0xC0000000 + BASE = 0xC0000000.

IMHO this is an ugly hack and it's better to setup paging and the GDT before the kernel is used. This would require a seperate piece of code that is disposed of after the kernel is started, but allows for additional features, like having several copies of the kernel (one for each NUMA domain), or using physical pages that are above 16 MB (to conserve memory that can be used for ISA DMA), or selecting which kernel to use based on other factors (for e.g. you might have a multi-CPU kernel and a single-CPU kernel, or a 32 bit kernel and a 64 bit kernel).


Cheers,

Brendan

Re:raw temp paging

Posted: Mon Aug 08, 2005 8:05 am
by GLneo
ok ive tried that but it locks up bochs + qemu my kernel is linked to 0xC0000000 and my boot code is:

Code: Select all

[BITS 16]

  [ORG 0x7C00]

    jmp start

    OSID                db "AndrewOS"
    BytesPerSector      dw 0200h
    SectorsPersector    db 01h
    LeadingSectors      dw 0001h
    NumberOfFATs        db 02h
    RootEntryMax        dw 00E0h
    TotalSectors        dw 0B40h
    MediaType           db 0F0h
    SectorsPerFAT       dw 0009h
    SectorsPerTrack     dw 0012h
    NumberOfHeads       dw 0002h
    HiddenSectors       dd 00000000h
    TotalSectors2       dd 00000000h
    DriveNumber         db 00h
    Reserved            db 00h
    BootSignaure        db 29h
    VolumeID            dd 69696969h
    VolumeLabel         db "AndrewOS   "
    FATID               db "FAT12   "

    LoadSectors:
            push ax
            push bx
            push cx
            mov dl, 12h
            div dl
            inc ah
            mov cl, ah
            mov dh, al
            and dh, 01h
            shr al, 1
            mov ch, al
            mov dl, 00h
            Read:
                mov ah, 02h
                mov al, 01h
                int 13h
                jc Read
            pop cx
            pop bx
            pop ax
            add bx, 0200h
            inc ax
            loop LoadSectors
            ret

    start:
            cli
            mov  ax, 07C0h
            mov  ds, ax
            mov  es, ax
            mov  ax, 9000h
            mov  ss, ax
            mov  sp, 0FFFFh
            sti

    floppy_reset:
            mov ah, 0
            int 13h
            or ah, ah
            jnz floppy_reset

    kernel_load:
            mov ax, 0
            mov es, ax
            mov bx, 0x1000
            mov ax, 1
            mov cx, 50
            call LoadSectors

    gdt:
            cli
            xor ax, ax
            mov ds, ax
            lgdt [toc]
    pmode:
            mov eax, cr0
            or eax, 1
            mov cr0, eax
            jmp 08h:clean_up

[BITS 32]
    clean_up:
            mov ax, 10h
            mov ds, ax
            mov ss, ax
            mov esp, 090000h
    stop_floppy:
            mov dx,3F2h
            xor al,al
            out dx,al
    kernel:
            jmp 08h:0xC0000000

    gdt_data:
            dd 0
            dd 0
            dw 0FFFFh
            dw 1000h
            db 0
            db 10011010b
            db 11001111b
            db 40h
            dw 0FFFFh
            dw 1000h
            db 0
            db 10010010b
            db 11001111b
            db 40h
    end_of_gdt:

    toc:
            dw end_of_gdt - gdt_data - 1
            dd gdt_data

    times 510-($-$$) db 0
    dw 0AA55h 
wend i do "[BITS 32]" should i also "[ORG something]" ???

Re:raw temp paging

Posted: Mon Aug 08, 2005 8:51 am
by Brendan
Hi,

I found some problems...

Code: Select all

    start:
            cli
            mov  ax, 07C0h
            mov  ds, ax
            mov  es, ax
            mov  ax, 9000h
            mov  ss, ax
            mov  sp, 0FFFFh
            sti
Don't load SS:SP with 0x9000:0xFFFF - it's 2 problems at the same time. Firstly, SP should be aligned to the nearest word for performance reasons, and secondly this area is used by the EBDA (Extended BIOS Data Area). Try setting SS:SP to 0x8000:0xFFFD instead.

Code: Select all

    pmode:
            mov eax, cr0
            or eax, 1
            mov cr0, eax
            jmp 08h:clean_up

[BITS 32]
    clean_up:
Here's you main problem - the "jmp 08h:clean_up" will jump to CS base + offset, or "0x40001000 + clean_up", which is definately not going to work. Perhaps use something like this instead:

Code: Select all

    stop_floppy:
            mov dx,3F2h
            xor al,al
            out dx,al
    pmode:
            mov eax, cr0
            mov bx, 10h
            mov esp, 090000h
            or eax, 1
            mov cr0, eax
            mov ds, bx
            mov es, bx
            mov ss, bx
    kernel:
            jmp 08h:0xC0000000

Cheers,

Brendan

Re:raw temp paging

Posted: Mon Aug 08, 2005 11:01 am
by GLneo
ok i fixed that and still got errors but the EIP was in my kernel so, i turnd off my kernel GDT setter but still got:

Code: Select all

00004363539i[CPU  ] -----------------------------------
00004363539i[CPU  ] selector->index*8 + 7 = 49159
00004363539i[CPU  ] gdtr.limit = 23
00004363539i[CPU  ] fetch_raw_descriptor: GDT: index > limit
00004363539i[CPU  ] | EAX=60000011  EBX=00000010  ECX=000b0000  EDX=000003f2
00004363539i[CPU  ] | ESP=00090000  EBP=00000000  ESI=00000000  EDI=0000ffe4
00004363539i[CPU  ] | IOPL=0 NV UP DI PL NZ NA PE NC
00004363539i[CPU  ] | SEG selector     base    limit G D
00004363539i[CPU  ] | SEG sltr(index|ti|rpl)     base    limit G D
00004363539i[CPU  ] |  DS:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363539i[CPU  ] |  ES:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363539i[CPU  ] |  FS:0000( 0000| 0|  0) 00000000 0000ffff 0 0
00004363539i[CPU  ] |  GS:0000( 0000| 0|  0) 00000000 0000ffff 0 0
00004363539i[CPU  ] |  SS:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363539i[CPU  ] |  CS:0000( 0000| 0|  0) 00000000 0000ffff 0 0
00004363539i[CPU  ] | EIP=00007cc1 (00007cbc)
00004363539i[CPU  ] | CR0=0x60000011 CR1=0x00000000 CR2=0x00000000
00004363539i[CPU  ] | CR3=0x00000000 CR4=0x00000000
00004363539i[CPU  ] -----------------------------------
it sems CS doesn't have a base of 0x40001000???

Re:raw temp paging

Posted: Mon Aug 08, 2005 6:20 pm
by Brendan
Hi,
GLneo wrote:ok i fixed that and still got errors but the EIP was in my kernel so, i turnd off my kernel GDT setter but still got:

Code: Select all

00004363539i[CPU  ] -----------------------------------
00004363539i[CPU  ] selector->index*8 + 7 = 49159
It's like you tried doing "jmp far 0xC000:0x????????", while CS:IP = 0x0000:0x07CC1 in real mode. I think it's an assembler quirk - try "jmp dword 08h:0xC0000000" or "a32 jmp 08h:0xC0000000" (can't remember which works for NASM, and I'm not at home to check)...


Cheers,

Brendan

Re:raw temp paging

Posted: Tue Aug 09, 2005 7:44 am
by GLneo
well that helped(my CS is corect) but my EIP is out of here, i think the GDT trick didnt rap around???:

Code: Select all

00004363620p[CPU  ] >>PANIC<< prefetch: running in bogus memory
00004363620i[SYS  ] Last time is 1123594955
00004363620i[CPU  ] protected mode
00004363620i[CPU  ] CS.d_b = 32 bit
00004363620i[CPU  ] SS.d_b = 32 bit
00004363620i[CPU  ] | EAX=00000000  EBX=ffffffff  ECX=ffffffff  EDX=ffffffff
00004363620i[CPU  ] | ESP=0008ffd0  EBP=ffffffff  ESI=00000000  EDI=c0005fec
00004363620i[CPU  ] | IOPL=0 NV UP DI PL NZ AC PO CY
00004363620i[CPU  ] | SEG selector     base    limit G D
00004363620i[CPU  ] | SEG sltr(index|ti|rpl)     base    limit G D
00004363620i[CPU  ] |  DS:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363620i[CPU  ] |  ES:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363620i[CPU  ] |  FS:0000( 0000| 0|  0) 00000000 0000ffff 0 0
00004363620i[CPU  ] |  GS:0000( 0000| 0|  0) 00000000 0000ffff 0 0
00004363620i[CPU  ] |  SS:0010( 0002| 0|  0) 40001000 000fffff 1 1
00004363620i[CPU  ] |  CS:0008( 0001| 0|  0) 40001000 000fffff 1 1
00004363620i[CPU  ] | EIP=ffffffff (ffffffff)
00004363620i[CPU  ] | CR0=0x60000011 CR1=0x00000000 CR2=0x00000000
00004363620i[CPU  ] | CR3=0x00000000 CR4=0x00000000
00004363620i[     ] restoring default signal behavior
00004363620i[CTRL ] quit_sim called with exit code 1

Re:raw temp paging

Posted: Tue Aug 09, 2005 8:22 am
by Brendan
Hi,

For some reason, ESP was decreased from 0x00090000 to 0x0008FFD0, EAX was cleared, EBX was changed to 0xFFFFFFFF, EDI got changed to 0xC0005FEC. Now I wonder what code did all of these things? These aren't values that would have been left over from the real mode code I saw....

I'm only guessing, but it looks to me like it worked perfectly! :)

The question could be "What's wrong with your kernel's code?"....


Cheers,

Brendan

Re:raw temp paging

Posted: Tue Aug 09, 2005 2:10 pm
by GLneo
your right (good eye) it is a problem writing to video memory, so i think i should enable paging so 0xB8000 will be liner, thx for help with trick ;)