Higher half kernels

Discussions on more advanced topics such as monolithic vs micro-kernels, transactional memory models, and paging vs segmentation should go here. Use this forum to expand and improve the wiki!
Post Reply
User avatar
BMW
Member
Member
Posts: 286
Joined: Mon Nov 05, 2012 8:31 pm
Location: New Zealand

Higher half kernels

Post by BMW »

What is the point of a higher half kernel?

Because each process has its own virtual address space, so why not just put the kernel at 0x00 in its own address space????

It shouldn't matter where it is within its VAS, user space programs have their own VAS.
Currently developing Lithium OS (LiOS).

Recursive paging saves lives.
"I want to change the world, but they won't give me the source code."
User avatar
gravaera
Member
Member
Posts: 737
Joined: Tue Jun 02, 2009 4:35 pm
Location: Supporting the cause: Use \tabs to indent code. NOT \x20 spaces.

Re: Higher half kernels

Post by gravaera »

Yo:

The biggest reason is avoiding address space switches, and the TLB cooling that comes with switching address spaces constantly. If you map the kernel into every address space, then a syscall can be theoretically executed entirely within the calling process's address space. When you keep the kernel in its own address space, you every syscall requires you to do two address space switches -- one into the kernel's address space, and one back out into the userspace process' address space.

--Peace out,
gravaera
17:56 < sortie> Paging is called paging because you need to draw it on pages in your notebook to succeed at it.
OSwhatever
Member
Member
Posts: 595
Joined: Mon Jul 05, 2010 4:15 pm

Re: Higher half kernels

Post by OSwhatever »

One benefit of having the kernel at high address is that you have the possibility to move the kernel without affecting the program and that way adjust how much each process has. An example of this is the 3GB switch in Windows that moves the kernel one gigabyte up in order to give the processes more virtual memory.

It's simply easier to move the kernel than the programs. Think about x86-64 where you have a "hole" in the middle of the virtual address space. Let's say they would decide to make this hole smaller one day. Then you don't need to modify your program that starts a 0 but, if the program would be on high address it would require a recompilation in order to take advantage of the larger virtual address space. Possible with relocation though but if you can avoid it......
rdos
Member
Member
Posts: 3276
Joined: Wed Oct 01, 2008 1:55 pm

Re: Higher half kernels

Post by rdos »

Personally, I can't see any valid reason why to place a program at address 0. Executable formats for 32 and 64 bits all have relocation information, and are usually not bound to a specific address, and at least not to 0. The reason why a user program should not execute at address 0 is that this is the address of null-pointers, which should be caught as invalid. The larger invalid space at the beginning, the lower risk of null pointers, or random integers casted to pointers, will be valid.

The same applies to kernels. They should not be a address 0, nor at the top of linear address space (since this allows negative integers to be casted to valid pointers in the kernel).
User avatar
dozniak
Member
Member
Posts: 723
Joined: Thu Jul 12, 2012 7:29 am
Location: Tallinn, Estonia

Re: Higher half kernels

Post by dozniak »

rdos wrote:Executable formats for 32 and 64 bits all have relocation information,
The more relocation information you have to process for a given program, the longer it takes to load and start. Compare:
- load program and jump to it

vs.

- load program
- process relocations for each executable section, process PLT entries
- process relocations for each data section, process GOT relocations
- jump to it

Process of relocation is usually linear with the size of program (has to patch every address) and touches a lot of memory pages (usually the entire executable space of the program), thus trashing the caches and being even less effective (vs. not doing that).
Learn to read.
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: Higher half kernels

Post by bluemoon »

rdos wrote:The reason why a user program should not execute at address 0 is that this is the address of null-pointers, which should be caught as invalid. The larger invalid space at the beginning, the lower risk of null pointers, or random integers casted to pointers, will be valid.
Agree. For this reason I set the first 4KB as absent, and map the first following few MB as kernel-access only (for process specific information block), and the application starts at 16MB.
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: Higher half kernels

Post by bluemoon »

dozniak wrote:The more relocation information you have to process for a given program, the longer it takes to load and start.
However consider a typical scenario that an application consist of a base executable and a dozen of shared libraries.
The added time might not be as worst as you expect since all shared libraries require relocation on both cases.

Furthermore if you are doing address space randomization, you need to do relocations anyway.
egos
Member
Member
Posts: 612
Joined: Fri Nov 16, 2007 1:59 pm

Re: Higher half kernels

Post by egos »

If you use own libraries you can set different predefined base addresses for them to prevent its overlapping. Besides, in many projects the size of base executable module is larger than the size of all used shared libraries.
If you have seen bad English in my words, tell me what's wrong, please.
rdos
Member
Member
Posts: 3276
Joined: Wed Oct 01, 2008 1:55 pm

Re: Higher half kernels

Post by rdos »

dozniak wrote:
rdos wrote:Executable formats for 32 and 64 bits all have relocation information,
The more relocation information you have to process for a given program, the longer it takes to load and start. Compare:
- load program and jump to it

vs.

- load program
- process relocations for each executable section, process PLT entries
- process relocations for each data section, process GOT relocations
- jump to it

Process of relocation is usually linear with the size of program (has to patch every address) and touches a lot of memory pages (usually the entire executable space of the program), thus trashing the caches and being even less effective (vs. not doing that).
First, you can do demand-loading and relocation at the same time. Second, you can bind the executable at a non-zero address, and avoid relocation that way. In x86-64, I let the linker locate the executable far above 4G, and then I mark the entire first 4G as kernel-only.
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: Higher half kernels

Post by bluemoon »

egos wrote:If you use own libraries you can set different predefined base addresses for them to prevent its overlapping. Besides, in many projects the size of base executable module is larger than the size of all used shared libraries.
Let's check a few application on linux:

Code: Select all

$ ldd /bin/ls
	linux-vdso.so.1 =>  (0x00007fff77dff000)
	libselinux.so.1 => /lib/x86_64-linux-gnu/libselinux.so.1 (0x00007f3979a6c000)
	librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007f3979864000)
	libacl.so.1 => /lib/x86_64-linux-gnu/libacl.so.1 (0x00007f397965b000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f397929c000)
	libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007f3979098000)
	/lib64/ld-linux-x86-64.so.2 (0x00007f3979ca2000)
	libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007f3978e7a000)
	libattr.so.1 => /lib/x86_64-linux-gnu/libattr.so.1 (0x00007f3978c75000)
$ ldd /bin/sh
	linux-vdso.so.1 =>  (0x00007fff5bfff000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f633e3ac000)
	/lib64/ld-linux-x86-64.so.2 (0x00007f633e782000)
$ ldd /bin/nano
	linux-vdso.so.1 =>  (0x00007fff62ba2000)
	libncursesw.so.5 => /lib/x86_64-linux-gnu/libncursesw.so.5 (0x00007f34d286f000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f34d24b0000)
	libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007f34d22ab000)
	libtinfo.so.5 => /lib/x86_64-linux-gnu/libtinfo.so.5 (0x00007f34d2084000)
	/lib64/ld-linux-x86-64.so.2 (0x00007f34d2ab3000)
With these sample I assume the number of libraries is significant per normal application.

Now, if you count the relocations entries, you may note that:
1. for normal application, you only need to do relocation for global objects (GOT). The PLT entry only exist if you has exported function on the base executable. The work for relocation is insignificant and however not related to the code size.
2. On the contrast, every shared libraries has tons of relocation.

You got my point.
Post Reply