forked from Tasssadar/kexec-tools
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add documentation/howto for mpc85xx systems
[ [email protected]: removed trailing whitespace ] Signed-off-by: Matthew McClintock <[email protected]> Signed-off-by: Simon Horman <[email protected]>
- Loading branch information
Showing
1 changed file
with
190 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,190 @@ | ||
mpc85xx kexec howto | ||
------------------- | ||
|
||
Matthew McClintock <[email protected]> | ||
Last Updated: 2010-07-20 | ||
|
||
There is some terminology that will be useful which will be described here. | ||
|
||
boot kernel - the first one that you start, from u-boot for instance | ||
kexec kernel - the kernel that you reboot into when running "kexec -e" | ||
kdump kernel - the kernel that you reboot into after the boot kernel crash | ||
relocatable kernel - kernel that can boot from a 256MB alignment of physical | ||
memory (for mpc85xx systems at least) | ||
|
||
Each of the above types of kernels have specific requirements, they can | ||
all be different kernels or all the same kernel depending on your | ||
particular requirements. | ||
|
||
1) Build kernel for kexec (i.e. running kexec -e to reboot) | ||
|
||
This case is the simplest. You need to enable CONFIG_KEXEC for kexec for the | ||
"boot kernel", the kexec kernel can be a any kernel that already boots on your | ||
platform. However, if you want to be able run kexec again after rebooting once | ||
you will need to have CONFIG_KEXEC enabled for the kexec kernel as well. | ||
|
||
2) Build for kdump (i.e. for rebooting when your main kernel crashes) | ||
|
||
In this situation, you need to be aware that the kdump kernel will boot from | ||
a different physical address than your boot kernel (or even the kexec kernel). | ||
There are two approaches to this. First, you can build a relocatable kernel | ||
which will boot from a different physical address with no changes. This method | ||
is ideal as it would even allow your boot kernel and kdump kernel to be the | ||
same one. Optionally, you can build a kernel with custom physical address and | ||
kernel base address according to where you will load the kdump kernel*, but | ||
it's much easier to just use a relocatable kernel and let things work | ||
themselves out at run time. | ||
|
||
You will need to enable CONFIG_CRASH_DUMP on the boot kernel. You can chose to | ||
enable CONFIG_RELOCATABLE for the kdump kernel, and you will still want to | ||
verify that CONFIG_KERNEL_START and CONFIG_PHYSICAL_START have sane defaults. | ||
Most likely, you can leave these as 0xC0000000 and 0x0000000 respectively. | ||
Finally, on the kdump kernel you will want to make sure CONFIG_PROC_VMCORE is | ||
enabled as well so the core dump is exported via /proc/vmcore. You can just | ||
enable all these options on the boot and kdump and use the same kernel for both | ||
which is the simplest option. | ||
|
||
Summary of 1 & 2: | ||
|
||
Just enable kexec, crash support, and relocatable kernel and you should be good | ||
to go for all of the above scenarios using the same kernel. | ||
|
||
3) Obtaining a device tree | ||
|
||
You best bet for getting a working device tree is to pull the one the current | ||
kernel is using. The easiest way to do this is use the device tree compiler | ||
to create one from the proc file system | ||
|
||
$ dtc -I fs -O dtb /proc/device-tree/ > flat-device-tree | ||
|
||
Kexec should be able to take this flat device tree, and modifiy it/update it | ||
as needed for your particular scenario. It will update memreserve regions, add | ||
initrd/ramdisks, fixup the command line, etc. | ||
|
||
NOTE: If no device tree is given, kexec will do the above on it's own to | ||
obtain a useable device tree. You can specify the device tree to use | ||
with the --dtb=<flat_device_tree_blob> kexec argument. | ||
|
||
4) Kexec'ing a new kernel | ||
|
||
If you have followed the procedure above you need to do the following to reboot | ||
into a new kexec kernel. | ||
|
||
$ kexec -l {uImage,vmlinux} | ||
$ kexec -e | ||
|
||
These options will boot the new kernel, you should see some message as shown | ||
below. NOTE: The old command line is used, so if you are booting from an NFS | ||
mount it should work fine, however it you are using an initrd/ramdisk there are | ||
caveats to consider (see #6 below). | ||
|
||
sd 2:0:0:0: [sda] Synchronizing SCSI cache | ||
Starting new kernel | ||
Bye! | ||
Reserving 256MB of memory at 512MB for crashkernel (System RAM: 4096MB) | ||
Using MPC8572 DS machine description | ||
[snip] | ||
|
||
5) Setting for a kdump kernel | ||
|
||
For the boot kernel, you need to reserve a region of memory for the kdump kernel | ||
to use when the system crashes. This region is removed for use from the boot | ||
kernel and when the system crashes the kdump kernel will operate out of this | ||
region exclusively. For mpc85xx, we need to pick a region aligned at 256MB if we | ||
are using a relocatable kernel, other than that the size allocated needs to leave | ||
enough memory for your kdump environment to function properly as well as store | ||
the kdump kernel and any other items added (this would most likely be a ramdisk). | ||
Some valid options are: | ||
|
||
crashkernel={128M,256M,512M}@{256M,512M} and others | ||
|
||
For the example below we choose 256MB (0x10000000) of memory located at offset | ||
512MB (0x20000000). The command line option would look like this. | ||
|
||
crashkernel=256M@512M | ||
|
||
You can see the values the kernel parsed by running looking | ||
at your proc entries. In this case, the physical address is a 64bit value. | ||
|
||
$ hexdump -C /proc/device-tree/chosen/linux,crashkernel-base | ||
00000000 00 00 00 00 20 00 00 00 |.... ...| | ||
00000008 | ||
$ hexdump -C /proc/device-tree/chosen/linux,crashkernel-size | ||
00000000 00 00 00 00 10 00 00 00 |........| | ||
00000008 | ||
|
||
Kdump kernels are only run when the current kernel crashes, there you can not | ||
just restart your system. However, you can still trigger a crash for testing | ||
purposes by enabling CONFIG_MAGIC_SYSRQ and executing the following. | ||
|
||
$ echo c > /proc/sysrq-trigger | ||
|
||
However, before this we need to setup our kdump kernel as shown below. | ||
|
||
$ kexec -p {uImage.reloc, vmlinux} | ||
|
||
The kernel we pass in is a relocatable kernel, in the case of vmlinux no changes | ||
are required since there is no wrapper specifically assigning it to a certain | ||
address. However, kexec will attempt to honor the addresses given to mkimage | ||
when you created your uImage, therefore you need to create a uImage with the | ||
appropriate load and entry address | ||
|
||
$ mkimage -A ppc -O linux -T kernel -C gzip -a 0x20000000 -e 0x20000000 | ||
-n Linux-2.6.35-rc3 | ||
Image Name: Linux-2.6.35-rc3-00246-gd666cd8- | ||
Created: Wed Jul 14 17:34:19 2010 | ||
Image Type: PowerPC Linux Kernel Image (gzip compressed) | ||
Data Size: 3261979 Bytes = 3185.53 kB = 3.11 MB | ||
Load Address: 0x20000000 | ||
Entry Point: 0x20000000 | ||
|
||
You do not sctrictly need to use a RELOCATABLE kernel, you can build a kernel | ||
that can execute from this load address and entry point and it would your | ||
kdump kernel would still function properly. | ||
|
||
The above load address aligns with the crashkernel argument we passed | ||
in via the command line. It is important to make sure these addresses match | ||
each other when using uImage. It's less important for vmlinux since kexec will | ||
attempt to load it at the first available region which should match correctly. | ||
|
||
6) Misc. options to kexec | ||
|
||
There are a few options you can pass into kexec to modify it's behaviour. First, | ||
if you want to reuse your current initrd/ramdisk you can use the following. | ||
You will also need to add "retain_initrd" to the boot kernel command line for | ||
this option to work. So now your command line would look something like this. | ||
|
||
crashkernel=256M@512M retain_initrd | ||
|
||
NOTE: If you are setting up a kdump kernel, you will need to make sure your | ||
original initrd/ramdisk resides in the memory range reserved for the kdump | ||
kernel, otherwise the kdump kernel won't be able to access it. For example | ||
it needs to live within the 512MB-768M range in this case. A warning will | ||
be displayed if this is not the case. | ||
|
||
$ kexec -p uImage.reloc --reuseinitrd | ||
|
||
It's even easier to specify a new ramdisk and you don't need to modify your | ||
boot kernel command line. You also might need to update your command line to | ||
boot with your new ramdisk, you can do it via the --command-line option as well | ||
as add any other changes you want to the command line as well. | ||
|
||
$ kexec -p uImage.reloc --ramdisk=rootfs.ext2.gz | ||
--command-line="root=/dev/ram rw console=ttyS0,115200" | ||
|
||
or the following if you wanted kexec and add "retain_initrd" to the command | ||
line and boot with a ramdisk | ||
|
||
$ kexec -l uImage --ramdisk=rootfs.ext2.gz | ||
--command-line="`cat /proc/cmdline` retain_initrd" | ||
$ kexec -e | ||
|
||
7) After a crash | ||
|
||
If you have a kdump kernel loaded and your system crashes you can now debug | ||
the crash. | ||
|
||
$ gdb vmlinux /proc/vmcore | ||
|
||
You might need to copy these files elsewhere or setup your ramdisk to do these | ||
things automatically. |