Wednesday, September 21, 2011

Understanding the kernel code, and CR3 register

Recently, I was working on the kernel code and CR3 register. This article is going to record what I have learn.
First Question: How can we get the kernel code of Operating System?
Get Virtual Address of kernel code:
$ cat /boot/System.map-2.6.32-33-generic | grep text
c0100000 T_text
The first one is start virtual address of kernel code

Get Physical Address of kernel code:
$ cat /proc/iomem
00100000-00590de6 : Kernel Code

More info: please see
http://fengweizhang.blogspot.com/2010/12/boot-cat-system.html
http://jianggmulab.blogspot.com/2009/09/blog-post.html

Second Question: How to translate virtual address to physical address? 
Control Register 3 (CR3) stores the base address of Page Directory Table. More info please see page 47 in ULK book. 

Third Question: Which CR3 I should use to translate VA to PA of kernel code?
Any CR3. For each process, it has its own address spaces and CR3. No matter which processes the operating system is running, the virtual address and physical address of kernel code will never change. Although the CR3 is different depends on the running process, same VA will map to same PA by CR3.

Each process has its own address space. From the virtual address point of view, it has some address space at 0-3G region, and it also has some address space at 3-4G region (this is for kernel mode). All Processes get same mappings for the kernel address space (3-4G). Each process also has its own page directory table and page tables. CR3 is the base address of page directory table. The address space at 3-4G region must have its own translation entries in page directory table and page tables. These entries are always same in different page directory table and page tables. 

Process 1 has virtual address space from 0xc0100000-0xc0590de6 (kernel code), translate to physical address is 0x00100000-0x00590de6
Process 2 has virtual address space from 0xc0100000-0xc0590de6 (kernel code), translate to physical address is 0x00100000-0x00590de6

Thus, process 1 and process 2 has same kernel memory mappings. (CR3 is different)


Monday, September 19, 2011

cat /proc/iomem

This is command shows the io memory map
This is the virtual address (linear address in Linux).
For example, it tells you the virtual address of kernel code.
If you want to get the kernel code, you could write a kenel module, and read the code out.


[root@localhost fengweiWorkSpace]# cat /proc/iomem
00010000-0009e3ff : System RAM
000a0000-000bffff : Video RAM area
000c0000-000cefff : Video ROM
000d3800-000d3fff : Adapter ROM
000f0000-000fffff : System ROM
00100000-7ddff7ff : System RAM
  00400000-00620dc5 : Kernel code
  00620dc6-007039fb : Kernel data
7ddff800-7de53bff : ACPI Non-volatile Storage
7de53c00-7de55bff : ACPI Tables
7de55c00-7dffffff : reserved
80000000-800fffff : PCI Bus #01
  80000000-8001ffff : 0000:01:00.0
  80020000-8002ffff : 0000:01:00.0
80100000-801fffff : PCI Bus #03
  80100000-8010ffff : 0000:03:00.0
  80110000-80110fff : 0000:03:02.0
80200000-8021ffff : 0000:00:19.0
  80200000-8021ffff : e1000e
80220000-80223fff : 0000:00:1b.0
  80220000-80223fff : ICH HD audio
80224000-80224fff : 0000:00:03.3
80225000-80225fff : 0000:00:19.0
  80225000-80225fff : e1000e
80226000-802263ff : 0000:00:1a.7
  80226000-802263ff : ehci_hcd
80226400-802264ff : 0000:00:1f.3
d0000000-dfffffff : PCI Bus #01
  d0000000-dfffffff : 0000:01:00.0
e0000000-fed003ff : reserved
fed20000-fed9ffff : reserved
fedad000-fedad00f : 0000:00:03.0
fee00000-feefffff : reserved
ff970000-ff9707ff : 0000:00:1f.2
  ff970000-ff9707ff : ahci
ff980800-ff980bff : 0000:00:1d.7
  ff980800-ff980bff : ehci_hcd
ffb00000-ffffffff : reserved