Page 1 of 1

Linking 64-Bit Kernel code

Posted: Tue Jan 20, 2009 5:24 am
by thepowersgang
I've finally managed to make binutils build gas so I can use gcc to code my kernel instead of pure assembler.
I thought that code produced by GCC/GAS should be easily linked into an elf64 binary by GNU LD but it seems that I'm wrong. Does anyone know why this happens?

I'm using x86_64-pc-elf-gcc and x86_64-pc-elf-ld as my build tools, built from version gcc-core-3.4.6 and binutils-2.19.

Output of `make all` (actually mingw32-make.exe all)

Code: Select all

x86_64-pc-elf-gcc.exe -Wall -O -fno-exceptions -fstrength-reduce -fleading-underscore -nostdinc -fno-builtin -I./include -o main.o -c main.c
x86_64-pc-elf-ld.exe -T link.ld -nostdlib -nodefaultlibs -o "../Acess64.bin" start32.ao start64.ao main.o -M > acess64.map.txt
main.o: In function `_kmain':
main.c:(.text+0xa): undefined reference to `_Screen_Clear'
main.c:(.text+0xa): relocation truncated to fit: R_X86_64_PC32 against undefined symbol `_Screen_Clear'
main.c:(.text+0x11): undefined reference to `__giMultibootMagic'
main.c:(.text+0x11): relocation truncated to fit: R_X86_64_PC32 against undefined symbol `__giMultibootMagic'
main.c:(.text+0x1c): relocation truncated to fit: R_X86_64_32 against `.rodata'
main.c:(.text+0x21): undefined reference to `_Screen_Puts'
main.c:(.text+0x21): relocation truncated to fit: R_X86_64_PC32 against undefined symbol `_Screen_Puts'
main.c:(.text+0x2a): relocation truncated to fit: R_X86_64_32 against `.rodata'
main.c:(.text+0x2f): undefined reference to `_Screen_Puts'
main.c:(.text+0x2f): relocation truncated to fit: R_X86_64_PC32 against undefined symbol `_Screen_Puts'
main.o:(.eh_frame+0x20): relocation truncated to fit: R_X86_64_32 against `.text'
mingw32-make: *** [../Acess64.bin] Error 1
Linker script `link.ld`

Code: Select all

/*
AcessOS 64
Linker Script
LINK.LD
*/

KERNEL_LOW = 0x200000;
KERNEL_BASE = 0xFFFF800000000000;

OUTPUT_FORMAT(elf64-x86-64)
ENTRY(_start32)

SECTIONS
{
	. = KERNEL_LOW;	/* Low Memory Address = 2Mb */
	
	.bootstrap : AT(ADDR(.bootstrap)) {
		start32.ao (.text)
		. = ALIGN(0x1000);
		start32.ao (.data)
	}
	
	. += KERNEL_BASE;
	. = ALIGN(0x1000);
	
	.text : AT(ADDR(.text) - KERNEL_BASE) {
		_code = .;
		*(.text)
		*(.rodata*)
		. = ALIGN(4096);
	}

	.data : AT(ADDR(.data) - KERNEL_BASE) {
		_data = .;
		*(.data)	
		. = ALIGN(4096);
	}

	.ehframe : AT(ADDR(.ehframe) - KERNEL_BASE)	{
		_ehframe = .;
		*(.ehframe)
		. = ALIGN(4096);
	}

	.bss : AT(ADDR(.bss) - KERNEL_BASE)	{
		_bss = .;
		*(.bss)
		. = ALIGN(4096);
	}

	_end = .;
	_end_pa = . - KERNEL_BASE;

	/DISCARD/ :
	{
		*(.comment)
	}
}

Re: Linking 64-Bit Kernel code

Posted: Tue Jan 20, 2009 5:53 am
by Ross
try passing -mcmodel=large to gcc

Ross

Re: Linking 64-Bit Kernel code

Posted: Tue Jan 20, 2009 8:43 am
by thepowersgang
Thanks a LOT, I think I could remember reading that somewhere but I forgot it when I wrote my makefile. #-o