Verständnisproblem mit dynamischem Speicher



  • @Nobuo<whitespace>T :p
    Ok, das habe ich glaube ich kapiert! Nun nur noch 2 Dinge: Mir ist noch überhaupt nicht klar, wie ich in den anderen Code springen kann.
    Ich habe 2 Dateien: boot.bin sowie pong.bin. Diese habe ich mit MagicIso in ein Image gepackt und auf eine Diskette geschrieben.
    Nun weiss ich ja, dass das BIOS den Code aus boot.bin in die Adresse 07c00h kopiert ok! Aber doch bloss die 512 Bytes des ersten Sektors. Die restlichen Daten befinden sich doch noch auf der Diskette und nicht im Arbeitsspeicher?! Wie kann ich dann einfach in dahin springen?

    2. Ich habe da noch ein Problem: Es ladet nicht einmal dieser verflixte Bootloader! Dies ist mein code:

    ORG 7C00h
    
    start: mov ax,03h
           int 10h
    	   mov ah,0eh
    	   mov al,'S'
    	   int 10h 
           jmp $
    TIMES 510-($-$$) DB 0
    DW 0AA55h
    

    Aber es kommt immer folgender Fehler:

    Disk formatted with MagicISO 4.70 (c) 2001-04 MagicISO, Inc.
    Bootsector form C.H. Hochstätter

    No Systemdisk. Booting from harddisk

    Also ich bin schon sehr überrascht, wie es möglich ist, dass an dieser Stelle Text von MagicIso steht?! Das kann doch eigentlich nur bedeuten, dass MagicSchrott da seinen eigenen Bootloader reingehackt hat?! Ein sehr ähnliches Problem hatte ich min WinImage! Gibt es irgendeine Software, die einfach mal das tut, was sie soll?



  • Ich habe das fertige Image mit einem Hex-Editor analysiert! Dieses Scheiss MagicIso überschreib meinen Programmcode komplett! :p



  • Ishildur schrieb:

    Nun weiss ich ja, dass das BIOS den Code aus boot.bin in die Adresse 07c00h kopiert ok! Aber doch bloss die 512 Bytes des ersten Sektors. Die restlichen Daten befinden sich doch noch auf der Diskette und nicht im Arbeitsspeicher?! Wie kann ich dann einfach in dahin springen?

    Wie ich bereits schrieb, musst du den restlichen Code natuerlich zuerst von der Diskette laden, bevor du reinspringen kannst.
    Dazu bietet es sich an, die BIOS Funktionen des int 13h zu benutzen - weitere Infos in FAQ, Forensuche, Internetsuche ... gibt wirklich genug zu dem Thema - auch Beispielcodes.

    Ishildur schrieb:

    2. Ich habe da noch ein Problem: Es ladet nicht einmal dieser verflixte Bootloader! Dies ist mein code:[...]

    Dazu sei noch angemerkt, dass auch Interrupt-Aufrufe den Stack verwenden. Wenn du keinen eingerichtet hast, kann das uU. zum Crash fuehren. Daher sollte wirklich das Erste, was du in deinem Bootloader machst, das Einrichten des Stacks und der Segmentregister sein.

    Ishildur schrieb:

    Dieses Scheiss MagicIso überschreib meinen Programmcode komplett!

    Versuch's mal mit RawRite o.Ae.? Das sieht ueberhaupt so aus, als wuerdest du versuchen, ein von CD bootbares Diskettenimage zu fabrizieren.
    Dabei sollte dir schon klar sein, dass ein CD-ROM keine Diskette ist und entsprechend auch komplett anders funktioniert. Mit einschlaegigen ISO-/Brennprogrammen fabrizierte Images verwenden daher einen speziellen Bootloader, der ein Diskettenlaufwerk simuliert und dann deinen Code spaeter nachlaedt.



  • RawWrite kann AFAIK eben nur fertige Images auf Disketten schreiben oder ein Image aus einer bestehenden Diskette erzeugen! Was ich aber doch brauche ist ein Programm, welches ein neues Image erstellen kann?! Mehrere Dateien als Input, ein Imagefile als Output?! Ich bin nun seit Stunden nach so einem Programm am suchen, aber ohne Erfolg! 😞



  • Ehrlich gesagt verstehe ich nicht ganz, was du vor hast, wozu du ein tolles Programm zum Image-Erstellen brauchst?
    Entweder linkst du deine Dateien geschickt zusammen, oder du haengst sie einfach per HexEditor (oder wenn gewusst wie mit dem copy-Befehl) hintereinander. Die so erzeugte Datei kopierst du mittels Rawrite auf Diskette - fertig.
    Selbst deinen 512Byte grossen Bootloader kannst du wie er ist mittels Rawrite in den Sektor 0 einer Diskette schreiben, um ihn auszuprobieren. Dabei rate ich allerdings zur Vorsicht, da du dir so deine wertvollen Disketten zerstoeren kannst.
    Zum ersten Rumspielen empfehle ich daher sowas wie bochs. Dem kannst du AFAIR auch deinen 512Byte Bootloader als Disketten-Image verfruehstuecken.



  • Hmmm... Wieso können denn dabei die Disketten kaputtgehen? 😮



  • AFAIK: Weil der Bootsektor normalerweise in den ersten Bytes auch Informationen ueber die Diskettengeometrie enthaelt (leider gerade wieder kein Beispiel zur Hand). Meiner Erfahrung nach reagieren viele Systeme nicht gut darauf, wenn diese zB. mit deinem Code ueberschrieben werden.



  • Und wie kann ich denn das verhindern?

    2. Ich habe mir inzwischen mal die Speicheraufteilung angesehen:http://www.in4mation.de/services/memory.html#konventionellerspeicher

    Da ist nichts davon zu erkennen, dass sich im Speicher unterhalb von 07c00h irgendetwas vom BIOS befinden würde. Ausserdem ist daraus ersichtlich, dass der Bildschirmspeicher bei a0000h anfängt, wieso also kann ich den Speicher nur bis zur Adresse 98000h benutzen?

    Ach ja noch was, wieso kann das Programm überhaupt funktionieren, ich habe doch gar kein Codesegment definiert, aber aus irgendeinem Grund funktionierts trotzdem!

    Ich verwirrt! 🙂



  • Ishildur schrieb:

    Und wie kann ich denn das verhindern?

    Indem du diese Daten in deinen Bootsektor einbaust. Schau dir mal hier den Teil zum BPB an (und den Rest vielleicht auch noch 😉 ).

    Ishildur schrieb:

    2. Ich habe mir inzwischen mal die Speicheraufteilung angesehen:http://www.in4mation.de/services/memory.html#konventionellerspeicher

    Da ist nichts davon zu erkennen, dass sich im Speicher unterhalb von 07c00h irgendetwas vom BIOS befinden würde.

    KA, warum das da nicht drin steht, aber es ist so.
    Die BDA geht auch nicht unbedingt genau bis 7C00h - wenn du darunter aber einfach nichts rumschreibst, ohne genau zu wissen was du tust, bist du auf der sicheren Seite. 🙂

    Ishildur schrieb:

    Ausserdem ist daraus ersichtlich, dass der Bildschirmspeicher bei a0000h anfängt, wieso also kann ich den Speicher nur bis zur Adresse 98000h benutzen?

    Wieder gilt: Vorsicht ist die Mutter der Porzellankiste. 😃
    Duerfte aber eigentlich auch bis A0000 problemlos klappen. Musst da oben nur mit der Segmentierung aufpassen, damit du nicht aus versehen in den Grafikspeicher kommst.



  • Hmmmm. Irgendetwas klappte mit meinem Stack nicht! Wie muss ich den Stackpointer initialisieren?

    Im Internet habe ich folgendes gefunden:

    Danach startet der eigentliche Bootloader. Zuerst basteln wir uns einen Stack, dessen Adresse wir auf 0x9000 legen. Den Stackpointer setzen wir dabei auf 0. Während wir unseren Stack zusammenbauen, dürfen wir KEINE Interrupts verwenden!

    Code:
    start:
    cli ; Keine Interrupts verwenden!
    mov ax, 0x9000 ; Adresse des Stack speichern
    mov ss, ax ; Stackadresse festlegen
    mov sp, 0 ; Stackpointer auf 0 setzen
    sti ; Jetzt lassen wir wieder Interrupts zu

    [/quote]

    Ich habe das ein wenig abgeändert:

    cli             ; disable all interrupts as there is still no stack available
    mov ax,MEM_STK  ; copy the address of the stack into ax
    mov ss,ax       ; copy ax into the stacksegment
    xor sp,sp       ; init the stack pointer by zero
    sti             ; enable all interupts
    

    Also, leider funktioniert dass nicht, sobald ich xor sp,sp oder mov sp,00h mache, startet das Programm anschliessend nicht mehr! Was ich sowieso nicht so richtig verstehen kann: Ist es nicht so, dass der Stackpointer dekrementiv ist, müsste man diesen dann nicht wennschon mit bspw. 512 initialisieren?

    Lg Ishildur



  • Ishildur schrieb:

    Hmmmm. Irgendetwas klappte mit meinem Stack nicht! Wie muss ich den Stackpointer initialisieren?[...]
    Was ich sowieso nicht so richtig verstehen kann: Ist es nicht so, dass der Stackpointer dekrementiv ist, müsste man diesen dann nicht wennschon mit bspw. 512 initialisieren?

    Habe ich eigentlich auch schon geschrieben: Stimmt, aber 0 - 2 ist im 16Bit-Register FFFE. Dahin wird auch der erste Wert dann gespeichert.
    Warum dein Code nicht startet, kannst du dir zB. im Bochs debugger anzeigen lassen. Ansonsten kann ich auch nur raten - welchen Wert hat denn zB. MEM_STK?

    Noch eine Anmerkung: AFAIK wird beim Setzen von SS automatisch das Interrupt-Flag bis zur Ausfuehrung des uebernaechsten Befehls geloescht. Ein cli/sti um die 2 Befehle zur Stack-Einrichtung ist also unnoetig.



  • Hmmm, OK, das Problem mit dem Stack konnte ich lösen, ich dachte eben, dass die CPU den Stackpointer vom definierten Stackpointer herunterzählt...

    Irgendwie kriege ich das mit der Diskette lesen nicht gebacken! Woher weiss ich denn, von welchem Track und aus welchem Sektor ich lesen muss? Ist die Sektorgrösse nicht von der Formatierung abhängig?
    Ausserdem, wenn ich nun 15 KBytes auslesen, will, woher weiss ich dann wieviele Tracks und Sektoren dass sind?

    Gibts vielleicht irgendwo ein gutes Tutorial in Bezug auf das lesen von Diskette ohne Dateisystem?

    Lg Ishildur



  • Ishildur schrieb:

    Irgendwie kriege ich das mit der Diskette lesen nicht gebacken! Woher weiss ich denn, von welchem Track und aus welchem Sektor ich lesen muss?

    Du weisst, in welcher Reihenfolge die Daten/Programmteile in deinem Image liegen. Weisst du das nicht, solltest du dir darueber erstmal klar werden.
    Fuer Disketten wird dann AFAIK immer die chs-Adressierung verwendet...
    Wenn du dir dazu noch den Artikel ueber LBA durchliest, wird die Sache hoffentlich klarer... Die Werte fuer die Diskettengeometrie stehen im BPB.

    Ishildur schrieb:

    Ist die Sektorgrösse nicht von der Formatierung abhängig?

    Nein. Von der Laufwerksgeometrie. AFAIK ist das aber eigentlich immer mit der Blockgroesse gleichzusetzen, welche eigentlich auch immer 512 Byte betraegt (mir ist zumindest keine Ausnahme bekannt).

    Ishildur schrieb:

    Ausserdem, wenn ich nun 15 KBytes auslesen, will, woher weiss ich dann wieviele Tracks und Sektoren dass sind?

    Teile die 15kiloByte durch die Blockgroesse. Die so gewonnene Anzahl von Bloecken kannst du mit Hilfe der Laufwerksgeometrie-Daten und der Umrechnungsformel LBA/chs von Wikipedia weiter umrechnen.

    Ishildur schrieb:

    Gibts vielleicht irgendwo ein gutes Tutorial in Bezug auf das lesen von Diskette ohne Dateisystem?

    Kenne keines. Vielleicht bei den OS-Dev-Links.


Anmelden zum Antworten