Page 1 of 1

Makefile in OS Development

Posted: Sun Apr 21, 2013 6:01 pm
by hshihab
I'm currently working on bulding a simple OS from scratch and i'm follwoing a tutorial guide.

as the tutorial advances to the point where you combine the boot_sector code with the kernel code to boot the OS , the amount of terminal commands to compile and execute the OS-image was fairly high.

So the tutorial (fortunately) included a full section about Automating builds with Make

So i decided to break up all of the OS related codes into three directories : boot, drivers, kernel

--Code(here will be the makefile)
--boot:
--some necessary .asm files
--kernel:
--all kernel related files are here (such as kernel.c)
--drivers:
--all driver related files are here

and here is my Makefile so far :

Code: Select all

# Automatically generate lists of sources using wildcards.
VPATH=./boot:./kernel:./drivers
C_SOURCES = $( wildcard kernel/*.c drivers/*.c )
HEADERS = $( wildcard kernel/*.h drivers/*.h )
# TODO : Make sources dep on all header files.


# Convert the *. c filenames to *. o to give a list of object files to build
OBJ = ${C_SOURCES:.c =.o}

# Defaul build target
all: os-image


# Run bochs to simulate booting of our code.
run: all
	bochs

# This is the actual disk image that the computer loads
# which is the combination of our compiled bootsector and kernel
os-image : boot/boot_sect_c.bin kernel.bin
	cat $^ > os-image

# This builds the binary of our kernel from two object files :
# - the kernel_entry , which jumps to main () in our kernel
# - the compiled C kernel
kernel.bin : kernel/kernel_entry.o ${OBJ}
	ld -o $@ -Ttext 0x1000 $^ --oformat binary

# Generic rule for compiling C code to an object file
# For simplicity , we C files depend on all header files .
%.o : %.c ${HEADERS}
	gcc -ffreestanding -c $< -o $@

# Assemble the kernel_entry.
%.o : %.asm
	nasm $< -f elf -o $@
%.bin : %.asm
	nasm $< -f bin -I 'boot/' -o $@
clean:
	rm -fr *.bin *.dis *.o os-image
	rm -fr kernel/*.o boot/*.bin drivers/*.o
now , when i try to make use of the makefile and run :

Code: Select all

make run
this is what i get

Code: Select all

nasm boot/boot_sect_c.asm -f bin -I 'boot/' -o boot/boot_sect_c.bin
nasm kernel/kernel_entry.asm -f elf -o kernel/kernel_entry.o
ld -o kernel.bin -Ttext 0x1000 kernel/kernel_entry.o --oformat binary
ld: warning: cannot find entry symbol _start; defaulting to 0000000000001000
[color=#FF0000]kernel/kernel_entry.o:(.text+0x1): undefined reference to `main'
make: *** [kernel.bin] Error 1[/color]
i tried replacing every source file that could be related to this error into different directories , but i still get the same error



Any help would be greatly appreciated , Thanks

Re: Makefile in OS Development

Posted: Sun Apr 21, 2013 10:22 pm
by xenos
Do you get the same error when you run the commands manually? (I would say: probably yes. So the problem is not related to the makefile.) The most widely accepted solution to this is to use a cross compiler.

Re: Makefile in OS Development

Posted: Sun Apr 21, 2013 11:21 pm
by bluemoon
hshihab wrote:as the tutorial advances to the point where you combine the boot_sector code with the kernel code to boot the OS ,
This is where things getting seriously wrong.
As very simple tutorial it may be useful to combine boot with kernel for illusive purpose, to get you started.
But once you add more stuff on top of it, it will goes nowhere as you waste effort dealing with size limitations, different boot mechanic, etc.

I advice you to isolate boot loader from kernel for cleaner design.

For your question:
ld -o kernel.bin -Ttext 0x1000 kernel/kernel_entry.o --oformat binary
ld: warning: cannot find entry symbol _start; defaulting to 0000000000001000
kernel/kernel_entry.o:(.text+0x1): undefined reference to `main'
You call ld with host's default, which expect main and probably going to build an application.
Add -nostdinc -nostdlib etc, or better, build a cross compiler.

Re: Makefile in OS Development

Posted: Mon Apr 22, 2013 5:19 pm
by sortie
Do not pass -nostdinc. It's a mistake. Use a cross-compiler.. Use the GNU assembler rather than nasm and link with your compiler. Be sure to actually provide a _start entry point. Tell us the commands in future instead of giving us the makefile, it's not relevant unless you want me to criticize it.

[Sorry, in a hurry]

Re: Makefile in OS Development

Posted: Mon Apr 22, 2013 11:44 pm
by Combuster
sortie wrote:Use the GNU assembler rather than nasm
Nonsense.

Re: Makefile in OS Development

Posted: Tue Apr 23, 2013 12:08 am
by sortie
Combuster wrote:
sortie wrote:Use the GNU assembler rather than nasm
Nonsense.
Sorry - I don't intend to derail this discussion. I recommend the GNU assembler over nasm because it integrates much better with the rest of the GNU toolchain (this is my main reason). You get a fully-fledged cross GAS with your cross-binutils, it uses the same syntax as objdump and inline gcc assembly. Your cross GCC uses it as the backend. You don't have to specify options to tell it the target platform, it remembers your --host option and defaults to that. [Which is good, because it makes your build scripts simpler.] When you make an OS-specific toolchain or otherwise adapt binutils, these changes automatically help you port GAS. [And probably a few other reasons I forgot, such as that GAS supports more platforms.] These are the reasons why I recommend newbies GAS over nasm. (And of course, I don't mind experienced users using nasm, I did in the start, but the fact that GAS integrates better should be important to everyone.)

Oh, and if you are just starting out? I recommend you don't do a bootloader and rather use GRUB and multiboot and do a real ELF kernel. It's much nicer and I can assure you there is plenty of interesting "Not-Invented-Here" to enjoy in kernel mode.

Re: Makefile in OS Development

Posted: Tue Apr 23, 2013 12:27 am
by bluemoon
I don't see how nasm, yasm or whateverasm not integrate nicely with gcc, and it its either integrate, or does not integrate, there is nothing in between - so how does one better than other?
And no, no assembler war, please. Use the one you are familiar with, they should all work.
sortie wrote:Do not pass -nostdinc. It's a mistake
Proof wanted.

Re: Makefile in OS Development

Posted: Tue Apr 23, 2013 2:06 am
by sortie
The -nostdinc option surpressed all standard incude directories. You do want these. For instance, you want to use the <stdarg.h> header that comes with your cross-compiler, and all the other nice headers that come with your cross-compiler. People tend to pass -nostdinc when not using a real cross-compiler to surpress these headers, but that is a mistake as well, because you ought use a cross-compiler in the first place.

[Sorry, didn't intend to start a discussion on assemblers. It it merely my opinion that GAS is better for newbies as it comes with binutils and uses the same syntax as the rest of the toolchain. Please carry on. :-)]

Re: Makefile in OS Development

Posted: Tue Apr 23, 2013 3:26 am
by bluemoon
sortie wrote:People tend to pass -nostdinc when not using a real cross-compiler to surpress these headers, but that is a mistake as well,
It is totally work I would not consider it a mistake.
sortie wrote:because you ought use a cross-compiler in the first place.
I totally agree, I also strongly advice to use cross-compiler, but I acknowledge some people like to use host toolchain, and it can be done with special cares.