Gültiges GDT und LDT
-
ich habe problemen beim aufbauen der GDT und LDT
diesen beiden sind strukturen die der proessor benötig vor der schaltung in Proteced Mode und werden geladen mit
b.s.p.:
lgdt myGDT lldt MyLDTalso kommen wir zurück zu diesen beiden Strukturen
SECTION .text] [BITS 16] [GLOBAL start] start: xor ebx,ebx ;// now in real mode (16-bit) mov bx,cs shl ebx,4 mov eax,ebx ;// EAX=EBX=CS<<4 lea eax,[ebx] mov [gdt2 + 2],ax ;// set descriptor base address=EAX mov [gdt3 + 2],ax shr eax,16 mov [gdt2 + 4],al mov [gdt3 + 4],al mov [gdt2 + 7],ah mov [gdt3 + 7],ah lea eax,[ebx + gdt] ;// point gdt_ptr to the gdt mov [gdt_ptr + 2],eax ;// EAX=linear address of gdt push dword 0 ;// zero EFLAGS (interrupts off, popfd ;// IOPL=0, NT bit=0) lgdt [gdt_ptr] mov eax,cr0 or al,1 mov cr0,eax jmp SYS_CODE_SEL:do_pm [BITS 32] do_pm: mov ax,SYS_DATA_SEL ;// now in 32-bit pmode mov ds,eax ;// EAX works, one byte smaller :) mov ss,eax nop mov es,eax mov fs,eax mov gs,eax xor eax,eax ;// zero top 16 bits of ESP mov ax,sp mov esp,eax [EXTERN _main] call _main ;// call C code jmp $ ;// freeze [SECTION .data] ; null descriptor gdt: dw 0 ;// limit 15:0 dw 0 ;// base 15:0 db 0 ;// base 23:16 db 0 ;// type db 0 ;// limit 19:16, flags db 0 ;// base 31:24 ; linear data segment descriptor LINEAR_SEL equ $-gdt dw 0xFFFF ;// limit 0xFFFFF (1 meg? 4 gig?) dw 0 ;// base for this one is always 0 db 0 db 0x92 ;// present,ring 0,data,expand-up,writable db 0xCF ;// page-granular (4 gig limit), 32-bit db 0 ; code segment descriptor SYS_CODE_SEL equ $-gdt gdt2: dw 0xFFFF dw 0 ;// (base gets set above) db 0 db 0x9A ;// present,ring 0,code,non-conforming,readable db 0xCF db 0 ; data segment descriptor SYS_DATA_SEL equ $-gdt gdt3: dw 0xFFFF dw 0 ;// (base gets set above) db 0 db 0x92 ;// present,ring 0,data,expand-up,writable db 0xCF db 0 gdt_end: gdt_ptr: dw gdt_end - gdt - 1 ;// GDT limit dd gdt ;// linear, physical address of GDT /*Disen Proramm muss mit dem gcc compiliert werden und mit der assembler modul eingebunden werden !*/ #include <string.h> /* movedata() */ #define LINEAR_SEL 0x08 #define SYS_DATA_SEL 0x18 int main(void) { const char Msg[] = "h e l l o "; movedata(SYS_DATA_SEL, (unsigned)Msg, LINEAR_SEL, 0xB8000, sizeof(Msg)); return 0; } /*@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@*/ // Es wird wie folgt Compliert : nasm -f aout -o load.o load.asm gcc -c -O2 -Wall -g -o hello.o hello.c ld -o pm.com -oformat binary -Ttext=0x100 load.o hello.o /djgpp/lib/libc.a /*@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@*/
also das problem liegt beim der assembler modul wenn ich versuche diesen mit mehr als einen c code dann geht nicht !! was könnte der problem sein ?
cu.....
-
/****************************************************************************/
(C)CopyringDiesen source code ist nicht Frei.. wenn sie es für kommerziellen zwecke benuten wollen müssen sie hier posten und mir bescheid sagen......
/****************************************************************************/
Freuntlichen Grüßen
OS-Developer
-
Original erstellt von <OS-Developer>:
**/****************************************************************************/
(C)CopyringDiesen source code ist nicht Frei.. wenn sie es für kommerziellen zwecke benuten wollen müssen sie hier posten und mir bescheid sagen......
/****************************************************************************/
Freuntlichen Grüßen
OS-Developer***loel* Jeder, der deinen code wirklich kommerziell benutzen will, wird sich jetzt sicherlich bei dir melden
Zurueck zum Problem:
Was heisst mit mehr als einem C codeWie linkst Du das dann und was genau laeuft dann falsch?
Ich habe zwar nicht so die Ahnung von gcc, aber vielleicht koennte ich mit ein paar mehr Infos doch einen ungefaehren Ueberblick ueber das Problem bekommen.
-
wo ist das cli???
-
Also wenn das ein bootcode werden soll, müsstest du noch ein paar Sachen vorher machen. z.B. den Stack einrichten (is ein wenig blöd wenn SS:ESP irgendwo hinzeigt, und mensch irgendwo dort (z.B. im eigenen Code) dann Daten hinpushet ).
Hab selber mal ne Routine geschrieben, die nen gültigen GDT erzeugt (is für RM):
;mkGDTE v0.002 ; make Global Descriptor Table Entry ; for RealMode on x86 ; ; by Daniel Otte ; ; ; ; HIGH LOW ; +--------+--------+ ; SP + 21 | AVL | N286C. | SP+ 20 Vaiable & non286compatible ; +--------+--------+ ; SP + 19 | Gran. | SegType| SP+ 18 granularity ; +--------+--------+ ; SP + 17 | Present| DPL | SP+ 16 ; +--------+--------+ ; SP + 15 | SegBaseAddr (h.)| SP+ 14 ; +--------+--------+ ; SP + 13 | SegBaseAddr (l.)| SP+ 12 ; +--------+--------+ ; SP + 11 |00000000| SegSize| SP+ 10 <-- high ; +--------+--------+ ; SP + 09 | SegSize (low) | SP+ 08 ; +--------+--------+ ; SP + 07 | GDT ptr (high) | SP+ 06 ; +--------+--------+ ; SP + 05 | GDT ptr (low) | SP+ 04 ; +--------+--------+ ; SP + 03 | retAddr (Segm.) | SP+ 02 ; +--------+--------+ ; SP + 01 | retAddr (offS.) | SP+ 00 ; +--------+--------+ ; ; %ifndef __mkgdte.asm__ mkGDTE: pop dword [retAddr] ;smc trick to simiulate a ret with a jmp ;now we can pop other values and won't ;need to buffer them in regs ; pop di ;lets make a ptr. to pop es ;our destination ;) pop word [es:di ] ;pop&store SegSize (low) pop word [es:di+6] ;pop&store SegSize (high) pop word [es:di+2] ;pop&store SegBaseAddr (low) pop word ax ;pop SegBaseAddr (high) mov [es:di+7], ah ;store high byte of SegBaseAddr (high) mov [es:di+4], al ;store low byte of SegBaseAddr (high) pop bx ;DPL in bl & Present in bh shl bl, 6 shl bx, 6 pop ax ;SegType in al & Gran. in ah or bh, al ;integrate Segtype in bh shl bh, 1 mov [es:di+5], bh ;store DPL&Co. (one byte) pop bx ;AVL in bh & N286C in bl shl ah, 1 or ah, bl ;integrate N286C in ah shl ah, 2 or ah, bh ;integrate AVL shl ah, 4 ; low Nibble of ah should be 0 or [es:di+6], ah quit: db 0xEA retAddr dd 0x00 ;push dword 0x00000000 ;equ $-4 ;retf %endif %define __mkgdte.asm__
vielleicht hilft dir das ja weiter.
Ach ja, diesen (meinen) Code stelle ich hiermit unter die GPL, also bitte berücksichtigen. (obwohl ich glaube das daran nicht viel schützenswertes ist).mfg
-bg-
-
Das ist kein boot code sonder denn code der das processor in Pmode schaltet..
wenn ich mehr als ein programm linke mit dem gleichen asssembler modul dann leuft er nicht der erste ja und die anderen nicht warum ?
-
#include <string.h> /* movedata() */ #define LINEAR_SEL 0x08 #define SYS_DATA_SEL 0x18 int main(void) { const char Msg[] = "h e l l o "; movedata(SYS_DATA_SEL, (unsigned)Msg, LINEAR_SEL, 0xB8000, sizeof(Msg)); return 0; }
Soweit ich weiß darfst du keine einzige Standardlibrary in deinem Code benutzen...
btw:
wenn ich mehr als ein programm linke mit dem gleichen asssembler modul dann leuft er nicht der erste ja und die anderen nicht warum ?
Ist der . auf deiner Tastatur defekt?
wenn ich mehr als ein programm linke mit dem gleichen asssembler modul dann leuft er nicht. der erste ja. und die anderen nicht. warum?Was benutzt du denn zumn Testen, Bochs?
Wenn ja, das Programm kann man doch im Debugmodus starten (bochsdbg.exe). Dann siehst du genau wo und warum er abstürzt.
-
Das problem ist das ich kein bochs benutze , wenn frage dar wie benuzt man das die einfach das programm mit
Bochs.exe TestProg.exe ; oder so was ?
danke ?..
-
ich weiss nicht aber das tut ist kapput :
Das problem ist das ich kein bochs benutze , wenn frage dar wie benuzt man das die einfach das programm mit
Bochs.exe TestProg.exe ; oder so was ?danke ?..
____________________________________________________________________________
also ich meine wie kann man bochs benutzen ?
-
Na mit .exe ist da nichts, Bochs ist ein x86-Emulator, wie auch VMWare & Co. Wenn du bochs startest kommst du in sowas wie ein Textmenü, dort kannst du einstellen welche Diskimages geladen werden sollen etc. (alternativ über Konfigurationsdatei) und dann starten. Das normale Bochs verhält sich dann wie ein normaler PC, das Debug-Bochs hat einen Breakpoint direkt nachm BIOS-Eintritt, mit der möglichkeit dann Step-by-Step-Debugging zu machen oder halt breakpoints zu setzen (den ersten setzt man meist auf 07c0:0000 weil das bios irgewndwie doch nicht so spannend ist ;))