Page 1 of 1

Bare minimal x64 kernel trouble under qemu under x64 linux

Posted: Tue Feb 12, 2013 8:03 am
by unomadh
Hello,

I'm just falling in the kernel writing ocean now; i'm currently trying to write a bare minimal x64 kernel under qemu. It does not work.
I'm coding on Ubuntu x64.
Here are my files:

kernel.c (comes from the tuto)

Code: Select all

#include <stdint.h>
 
void kmain(void)
{
   extern uint32_t magic;
 
   if ( magic != 0x2BADB002 )
   {
      /* Something went not according to specs. Print an error */
      /* message and halt, but do *not* rely on the multiboot */
      /* data structure. */
   }

   volatile unsigned char *videoram = (unsigned char *)0xB8000;
   videoram[0] = 65; /* character 'A' */
   videoram[1] = 0x07; /* light grey (7) on black (0). */

   while (1);
}
loader.s (the unmodified loader from the tuto)

Code: Select all

.global loader                          # making entry point visible to linker

# setting up the Multiboot header - see GRUB docs for details
.set ALIGN,    1<<0                     # align loaded modules on page boundaries
.set MEMINFO,  1<<1                     # provide memory map
.set FLAGS,    ALIGN | MEMINFO          # this is the Multiboot 'flag' field
.set MAGIC,    0x1BADB002               # 'magic number' lets bootloader find the header
.set CHECKSUM, -(MAGIC + FLAGS)         # checksum required

.align 4
.long MAGIC
.long FLAGS
.long CHECKSUM

# reserve initial kernel stack space
stack_bottom:
.skip 16384                             # reserve 16 KiB stack
stack_top:
.comm  mbd, 4                           # we will use this in kmain
.comm  magic, 4                         # we will use this in kmain

loader:
    movl  $stack_top, %esp               # set up the stack, stacks grow downwards
    movl  %eax, magic                   # Multiboot magic number
    movl  %ebx, mbd                     # Multiboot data structure

    call  kmain                         # call kernel proper

    cli
hang:
    hlt                                 # halt machine should kernel return
    jmp   hang
link.ld

Code: Select all

OUTPUT_FORMAT(elf64-x86-64)
ENTRY(kmain)
SECTIONS
{
    . = 10000;

    .text : AT(ADDR(.text) - 10000)
    {
        _code = .;
        *(.text)
        *(.rodata*)
        . = ALIGN(4096);
    }

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

   .eh_frame : AT(ADDR(.eh_frame) - 10000)
   {
       _ehframe = .;
       *(.eh_frame)
        . = ALIGN(4096);
   }

   .bss : AT(ADDR(.bss) - 10000)
   {
       _bss = .;
       *(.bss)

       /*
        * You usually need to include generated COMMON symbols
        * under kernel BSS section or use gcc's -fno-common
        */

        *(COMMON)
       . = ALIGN(4096);
   }

   _end = .;

   /DISCARD/ :
   {
        *(.comment)
   }
}
Here i don't know what KERNEL_VMA was about, so i replaced it by 10000 without really knowing why


The commands a used:

Code: Select all

$ as -o loader.o loader.s
$ gcc  -m64  -ffreestanding  -nostdlib  -mcmodel=large  -mno-red-zone  -mno-mmx  -mno-sse  -mno-sse2  -mno-sse3  -mno-3dnow -nostartfiles -nodefaultlibs -c kernel.c
$ ld -nostdlib -nodefaultlibs -T link.ld -o kernel kernel.o loader.o

The result:

Code: Select all

$ file kernel
kernel: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), statically linked, not stripped
$ qemu-system-x86_64 -kernel kernel
Cannot load x86-64 image, give a 32bit one.
which i don't understand since the same command on my local copy of my /vmlinuz works like a charm under qemu-system-x86_64, while not under qemu-system-i386, as expected. When checking vmlinuz, i just found this:

Code: Select all

$ file vmlinuz
vmlinuz: Linux kernel x86 boot executable bzImage, version 3.5.0-23-generic (buildd@komainu) #35-Ubuntu SMP Thu Jan 24 13:, RO-rootFS, swap_dev 0x4, Normal VGA
x86 ?? My system is amd64...


What does that mean ?

I'm aware i miss a lot of understanding (the reason why i'm here), that i should start learning ld scripting also, which i'm likely to do, but my really first goal is to have a bare minimum stuff that works.

Thank you in advance !...

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:12 am
by Combuster
The multiboot 1 standard doesn't do 64-bit kernels. (Nor is stealing code and compiling 32-bit assembly with a 64-bit assembler ever a good idea)

If you want a 64-bit kernel in this way, you have to do your own CPU initialisation.

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:16 am
by unomadh
Hi,
The multiboot ? 1 ? Standard ?

You mean, in the loader ? Is it the peace of code that checks for the cpu in vmlinuz and is able to claim you are trying to boot 64 on 32 bits hardware ?

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:18 am
by Combuster

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:22 am
by unomadh
Sorry to be a beginner, i just don't understand why speak about multiboot here. I know, you time is precious and you probably can't spend 2 seconds answering yes or no to my last question, and understand that i may not fully appreciate the common sense of the terms "multiboot 1 standard", that looks just as a kind of weird sentence to me, but defenly not a group of words i may keep together and search about.
Does that kind of speaking usually serves to make you feel a great person over the "common" people ?

I actually tried compiling in 32 bits, but if there is such an option for the last step, ld, i didn't find about, even using google.
As x86_64 appears to me as a x86 extension, i thought the assembly code would just compile right as is.
If i'm obliged to code on a 32 bits distrib in order to produce 32 bits kernel, i would prefer to know right now about how to make a x64 kernel :p

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:45 am
by Combuster
I actually tried compiling in 32 bits, but if there is such an option for the last step, ld, i didn't find about, even using google.
The top of this page wrote:The OSDev.org Wiki - Got a question? Search this first!
unomadh wrote:Does that kind of speaking usually serves to make you feel a great person over the "common" people?
Not sure if trolling, or just plain stupid. Either way, read the forum rules.

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 8:54 am
by unomadh
It's noticed in the quote you made that i did search. So, could we just have a nice exchange of useful information ?

The information i find by searching ... is full of probably useful theory, but i'm not at a level where i understand where it goes in real binary blobs. Even the tutorials on the net are assuming this and this as obvious all the time ... how i am supposed to learn this way ? If i have the same kind of answer in the forum ?

Could you please explain me a little about this boot ?
Thanks

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 9:02 am
by Combuster
Whatever searching you did beforehand, you could not have possibly have read the pointers for documentation (two of them) I gave you, and I'm certainly not going to spend any more than a fraction of the time you take to do your homework to write a post in reply. In fact, you violated a specific forum rule in assuming this behaviour (implicit in the second post, and now twice explicitly) and made it obvious you haven't understood them.

Your first post was a perfect start, the rest pretty much wasted all of that effort. Now get to work and show me you can do better than this.

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 9:06 am
by unomadh
It is not a homework at all :shock:
And what did you give me ? I seriously don't know what you find so explicit. I think you have a problem, keep easy, a leave me please.

Well, is anyone else who could help me ?

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 12:58 pm
by AndrewBuckley
calling -kernel from qemu is using the multiboot 1 standard, and as combuster said multiboot 1 does not support 64 bit kernels. this hobby requires a lot of personal effort and we will not spoon feed you. Combuster told you what was wrong and how to fix it. you didn't bother to read what he said or search the standard yourself. as for the issue of "common people", this is not a forum for them. We have rules to keep this forum useful, and they are very important.

please read them again.
http://forum.osdev.org/viewtopic.php?f=1&t=16944

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 1:09 pm
by unomadh
Thanks for your answer, this is clear (about multiboot), i appreciate and that was a useful answer.

I just asked for that, not a lot more. I didn't expect a so brutal answer, the above mention person could have answer the same way as yours and saved a lot of effort trying to keep his/her self-estime.
I don't ask for spoon-feed at all, defenely not, i just expected to find some pertinent indications in order to understand the stuff a little better.
If you claim this forum is useful, it should be accessible for people wanting to learn from it, instead of staying closed to people who already knows. This is my point of view.
[EDIT] Well, the clause 8 is not in his/her favour here...


So, about the subject of this topic, could i ask you what does the file start64.c handle here X86-64 ? since the script assumes the kernel64 is already build, i assume it's not part of it, and i assume also that loader32 had to handle the job to launch the kernel64 (that is detecting cpu nature and switching to long mode)

Thank you

Re: Bare minimal x64 kernel trouble under qemu under x64 lin

Posted: Tue Feb 12, 2013 5:13 pm
by beyondsociety
If you had done your homework and read the other articles under "see also" at the bottom of that very page, you would of solved your problem by now as all the info you need is in those other links. Hint: read http://wiki.osdev.org/Creating_a_64-bit_kernel