Problem mit Kompiler für OS


  • Mod

    Nothing to be done for 'makefile'.

    makefile ist im Gegensatz zu Batch-Dateien aufgabenorientiert. Bei Fehlern bricht es ab, und wenn alles schon besteht, macht es nichts und meldet dies.

    Zieldateien löschen, und schauen, ob diese erstellt werden.

    Übrigens sollte man - zumindest ab und zu - auch -Wall bei CCFLAGS einbauen, um zu sehen, was noch so an Ungereimtheiten existiert (manchmal z.B. UCHAR/CHAR).



  • Ich habe jetzt alle Sachen gelöscht, die er erstellen soll. Aber es kommt immer noch die selbe Meldung. Man muss doch aber die .c Dateien nicht selber kompilieren, oder?



  • Also so wie ich das gerade sehe, liegt es am "mingw32-make makefile".

    Versuch es mal so:

    SET PATH=C:\MinGW\bin;C:\msys\1.0\bin;C:\crosstools-complete\crosstools-complete\i586-elf\bin;C:\Programme\NASM;%PATH%
    mingw32-make
    pause
    

    Denn make öffnet das makefile im aktuellen Ordner ja eigentlich schon standardmäßig.


  • Mod

    Klappt's?



  • So, ich habe das von Deli1 mal ausprobiert. Scheint zu gehen, jetzt gibt es da nur noch irgendwelche Fehler, was das kompilieren mit nasm angeht, werde mich gleich mal darum kümmern, sobald ich etaws mehr weis, oder auch nicht, melde ich micht wieder.



  • So, das mit dem Assembler habe ich gelöst, war ein falscher Name schuld. Bei mir heißt er nämlich nasm und nicht nasmw. Jetzt häge ich gerade beim Kompilerproblem fest. Er meldet folgendes:

    process _begin: CreateProcess(NULL, i586-elf-gcc  -O -ffreestanding -fleading-unde
    rscore -c -o ckernel.o ckernel.c, ...) failed
    


  • So, irgendwie geht das jetzt, aber das makefile und die .bat verhalten sich noch etwas eigenartig. Da werde ich wohl noch mal dran arbeiten müssen. Aber immerhin bekomme ich jetzt mein HobbyOS.bin.

    EDIT: Seltsame Verahlten habe ih ihm gerade abgewöhnt. Als letztes will ich jetzt noch von C zu C++ umsteigen. Wenn das geht, poste ich hier mal das abgeänderte makefile


  • Mod

    Aber immerhin bekomme ich jetzt mein HobbyOS.bin.

    Gut!

    das makefile und die .bat verhalten sich noch etwas eigenartig.

    make/makefile ist ein mächtiges Gespann, aber es macht auf Dauer Spaß damit zu fahren. Dran bleiben. 👍
    Kaum hat man beim OSDEV eine Sache gelöst, steht die nächste Herausforderung ins Haus. Lieber erst mal einfach anfangen und kleine Ziele setzen.



  • a) Warum benutzt ihr Makefiles in einem neuen Projekt und nicht eine der moderneren Alternativen

    b) Wieso nicht die Autotools?



  • Das mit C++ habe ich verworfen, ist mir zu kompliziert. Ich benutzte jetzt nur C, ist ja sowie so die Standartsprache für OSDev.
    Hier nun meine .bat Datei und das komplette makefile. Ich hoffe, es wird irgendwem Helfen, der vielleicht das selbe Problem hat wie ich.
    Bat:

    SET PATH=C:\MinGW\bin;C:\crosstools-complete\crosstools-complete\bin;C:\Programme\NASM;%PATH%
    mingw32-make
    pause
    

    Makefile:

    SOURCES = kernel.asm $(filter-out boot.asm kernel.asm ,$(wildcard *.asm *.c))
    OBJECTS = $(addsuffix .o,$(basename $(SOURCES)))
    
    ASFLAGSBIN= -O32 -f bin
    ASFLAGSOBJ= -O32 -f elf
    NASM = nasm
    
    CFLAGS=	   -O -ffreestanding -fleading-underscore    
    CC= i586-elf-gcc
    
    LDFLAGS= -T kernel.ld -Map kernel.map -nostdinc
    LD= i586-elf-ld
    
    all: boot.bin ckernel.bin image     
    
    boot.bin: boot.asm
    	$(NASM) $(ASFLAGSBIN) $< -o $@
    
    %.o: %.asm
    	$(NASM) $(ASFLAGSOBJ) $< -o $@
    
    ckernel.bin: $(OBJECTS)
    	$(LD) $(LDFLAGS) $+ -o $@
    
    image:
    	cmd /c copy /b boot.bin + ckernel.bin HobbyOS.bin    
    
    #    $<        Erste Abhängigkeit
    #    $+        Liste aller Abhängigkeiten   
    #    $@        Name des Targets
    


  • Jetzt kommt der nicht in den CKernel. Auf dem Bildschirm steht immer nur diese bootloadermesage. Der CKernel:

    void k_clear_screen()
    {
    	char* vidmem = (char*) 0xb8000;
    	unsigned int i=0;
    	while(i<(80*2*25))
    	{
    		vidmem[i] = ' ';
    		i++;
    		vidmem[i] = 0x07;
    		i++;
    	};
    };
    
    unsigned int k_printf(char* message, unsigned int line)
    {
    	char* vidmem = (char*) 0xb8000;
    	unsigned int i = line*80*2;
    
    	while(*message!=0)
    	{
    		if(*message==0x2F)
    		{
    			*message++;
    			if(*message==0x6e)
    			{
    				line++;
    				i=(line*80*2);
    				*message++;
    				if(*message==0){return(1);};
    			};
    		};
    		vidmem[i]=*message;
    		*message++;
    		++i;
    		vidmem[i]=0x7;
    		++i;
    	};
    	return 1;
    };
    
    inline void outportb(unsigned int port,unsigned char value)
    {
        asm volatile ("outb %%al,%%dx"::"d" (port), "a" (value));
    };
    
    void update_cursor(int row, int col)
    {
    	unsigned short	position=(row*80) + col;
    	// cursor LOW port to vga INDEX register
    	outportb(0x3D4, 0x0F);
    	outportb(0x3D5, (unsigned char)(position&0xFF));
    	// cursor HIGH port to vga INDEX register
    	outportb(0x3D4, 0x0E);
    	outportb(0x3D5, (unsigned char)((position>>8)&0xFF));
    };
    
    // Hauptprogramm
    int main()
    {
    	k_clear_screen();
    	k_printf("Welcome to HenkesSoft OS.", 0);
    	k_printf("The C kernel has been loaded.", 2);
    	update_cursor(3, 0);
    
    	// Endlosschleife des OS
    	/*while(0)
    	{
    
    	};*/
    
    	return 0;
    };
    

    Was habe ich da wieder falsch gemacht?


  • Mod

    Zeige mal das Linkerskript und den Sprung nach _main in Assembler.


  • Mod

    a) Warum benutzt ihr Makefiles in einem neuen Projekt und nicht eine der moderneren Alternativen
    b) Wieso nicht die Autotools?

    http://de.wikipedia.org/wiki/GNU_Build_System

    Hat jemand Erfahrungen damit?



  • Linkskript:

    OUTPUT_FORMAT("binary")
    ENTRY(KernelStart)
    SECTIONS
    {
      . = 0x00008000;
      .text   : { *(.text)   }
      .data   : { *(.data)   }    
      .rodata : { *(.rodata) }
      .bss    : { *(.bss)    }  
    }
    

    Kernel.asm:

    [Bits 32]
    section .text          ; ld needs that for coff format
    
    [global KernelStart]
    KernelStart:
        mov    ax, 0x10
        mov    ds, ax      ; data descriptor --> data, stack and extra segment
        mov    ss, ax          
        mov    es, ax
        xor    eax, eax    ; null desriptor --> FS and GS
        mov    fs, ax
        mov    gs, ax
        mov    esp, 0x200000 ; set stack below 2 MB limit
    
    [extern _main]         ; entry point in ckernel.c
        call _main ; ->-> C-Kernel
        jmp $
    

  • Mod

    ... sieht unverdächtig aus. Schau mal nach kernel.map, ob da alles am rechten Platz gelandet ist, vor allem am Anfang bei 0x8000.



  • Memory Configuration
    
    Name             Origin             Length             Attributes
    *default*        0x00000000         0xffffffff
    
    Linker script and memory map
    
                    0x00008000                phys = 0x8000
    
    .text           0x00008000       0xfb
     *(.text)
     .text          0x00008000       0x1c kernel.o
                    0x00008000                KernelStart
     .text          0x0000801c       0xdf ckernel.o
                    0x00008041                _k_printf
                    0x0000801c                _k_clear_screen
                    0x00008091                _outportb
                    0x0000809d                _update_cursor
                    0x000080cb                _main
    
    .data           0x000080fc        0x0 load address 0x000080fb
     *(.data)
     .data          0x000080fc        0x0 ckernel.o
    
    .rodata
     *(.rodata)
    
    .rodata.str1.1  0x000080fb       0x38
     .rodata.str1.1
                    0x000080fb       0x38 ckernel.o
    
    .bss            0x00008134        0x0 load address 0x00008133
     *(.bss)
     .bss           0x00008134        0x0 ckernel.o
    LOAD kernel.o
    LOAD ckernel.o
    OUTPUT(ckernel.bin binary)
    
    .comment        0x00000000       0x31
     .comment       0x00000000       0x1f kernel.o
     .comment       0x0000001f       0x12 ckernel.o
    

    Ich kann dort nichts finden!


  • Mod

    ja, sieht gut aus. Wo kommt denn das phys = 0x8000 her? Da passt etwas nicht zusammen.



  • Keine Anhnung, aber vielleicht hat es etwas damit zu tuen:

    jmp 0x8:0x8000    ; this is a 16-bit-FAR-Jmp, but CS is loaded with "index" 8 in GDT
                          ; hence, the code will be interpreted as 32 bit from here on
                          ; the address can be found in the linker script (phys)
    

  • Mod

    Das ist der far jump zum Protected mode. Der ist o.k. Ich habe nur darauf hin weisen wollen, dass das Linkerskript und kernel.map nicht zusammen passen, weil in einem phys (Variable) steht und im anderen nicht.



  • Jetzt weis ich nicht was ich machen soll.


Anmelden zum Antworten