Skip to contentSkip to conversation

V2 Implement crashkernel=auto

PATCH In review Amerigo Wang 3 participants 12 messages Aug 6, 2009 – Aug 10, 2009

lore
Share & tools
lore
#0 lore raw

cover V2 Implement crashkernel=auto

V1 -> V2:
- Use include/asm-generic/kexec.h, suggested by Neil.
- Rename a local variable, suggested by Fenghua.
- Fix some style problems found by checkpatch.pl.
- Unify the Kconfig docs.

This series of patch implements automatically reserved memory for crashkernel, by introducing a new boot option "crashkernel=auto". This idea is from Neil.

In case of breaking user-space applications, it modifies this boot option after it decides how much memory should be reserved.

On different arch, the threshold and reserved memory size is different. Please refer patch 7/7 which contains an update for the documentation.

Note: This patchset was only tested on x86_64 with differernt memory sizes.

Cc Neil Horman <[email protected]>
Cc Eric W. Biederman <[email protected]>
Cc Ingo Molnar <[email protected]>
Cc Tony Luck <[email protected]>
Cc Anton Vorontsov <[email protected]>
Cc Andi Kleen <[email protected]>
Cc Fenghua Yu <[email protected]>
---
 Documentation/kdump/kdump.txt    |   16 ++++++++++++++++
 arch/ia64/Kconfig                |   10 ++++++++++
 arch/ia64/include/asm/kexec.h    |    8 ++++++++
 arch/powerpc/Kconfig             |   10 ++++++++++
 arch/powerpc/include/asm/kexec.h |    8 ++++++++
 arch/x86/Kconfig                 |   10 ++++++++++
 arch/x86/include/asm/kexec.h     |    1 +
 kernel/kexec.c                   |   34 ++++++++++++++++++++++++++++++++++
 8 files changed, 97 insertions(+)
#1 lore raw

PATCH 1/7 x86: add CONFIG_KEXEC_AUTO_RESERVE

Introduce a new config option KEXEC_AUTO_RESERVE for x86.

---
Index: linux-2.6/arch/x86/Kconfig =================================--- linux-2.6.orig/arch/x86/Kconfig +++ linux-2.6/arch/x86/Kconfig
@@ -1482,6 +1482,16 @@ config KEXEC
support. As of this writing the exact hardware interface is strongly in flux, so no good recommendation can be made.

+config KEXEC_AUTO_RESERVE
+ bool "automatically reserve memory for kexec kernel"
+ depends on KEXEC
+ default y
+ ---help---

+	  Automatically reserve memory for a kexec kernel, so that you don't
+	  need to specify numbers for the "crashkernel=X@Y" boot option,
+	  instead you can use "crashkernel=auto".
+	  On x86, 128M is reserved and only when you have memory > 4G.

+
config CRASH_DUMP
bool "kernel crash dumps"
depends on X86_64 || (X86_32 && HIGHMEM)

#2 lore raw

PATCH 2/7 x86: implement crashkernel=auto

In reply to Amerigo Wang

Implement "crashkernel=auto" for x86 first, other arch will be added in the following patches.

(Is 128M too big to be reserved on x86?)

---
Index: linux-2.6/kernel/kexec.c =================================--- linux-2.6.orig/kernel/kexec.c +++ linux-2.6/kernel/kexec.c
@@ -37,6 +37,7 @@
#include <asm/io.h>
#include <asm/system.h>
#include <asm/sections.h>
+#include <asm/setup.h>

/* Per cpu memory for storing cpu states in case of system crash. */ note_buf_t* crash_notes;
@@ -1297,6 +1298,39 @@ int __init parse_crashkernel(char *cm

ck_cmdline += 12; /* strlen("crashkernel=") */

+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+ if (strncmp(ck_cmdline, "auto", 4) = 0) {
+ unsigned long long size;
+ int len;
+ char tmp[32];
+
+ size = arch_default_crash_size(system_ram);
+ if (size != 0) {
+ *crash_size = size;
+ *crash_base = arch_default_crash_base();
+ len = scnprintf(tmp, sizeof(tmp), "%luM@%luM",
+ (unsigned long)(*crash_size)>>20,
+ (unsigned long)(*crash_base)>>20);
+ /* 'len' can't be <= 4. */
+ if (likely((len - 4 + strlen(cmdline))
+ < COMMAND_LINE_SIZE - 1)) {
+ memmove(ck_cmdline + len, ck_cmdline + 4,
+ strlen(cmdline) - (ck_cmdline + 4 - cmdline) + 1);
+ memcpy(ck_cmdline, tmp, len);
+ }
+ return 0;
+ } else {
+ /*
+ * We can't reserve memory auotmatcally,
+ * remove "crashkernel=auto" from cmdline.
+ */
+ ck_cmdline += 4; /* strlen("auto") */
+ memmove(ck_cmdline - 16, ck_cmdline,
+ strlen(cmdline) - (ck_cmdline - cmdline) + 1);
+ return -ENOMEM;
+ }
+ }
+#endif
/*
* if the commandline contains a ':', then that's the extended
* syntax -- if not, it must be the classic syntax
Index: linux-2.6/arch/x86/include/asm/kexec.h =================================--- linux-2.6.orig/arch/x86/include/asm/kexec.h +++ linux-2.6/arch/x86/include/asm/kexec.h
@@ -23,6 +23,7 @@

#include <asm/page.h>
#include <asm/ptrace.h>
+#include <asm-generic/kexec.h>

/*
* KEXEC_SOURCE_MEMORY_LIMIT maximum page get_free_page can return.
Index: linux-2.6/include/asm-generic/kexec.h =================================--- /dev/null
+++ linux-2.6/include/asm-generic/kexec.h
@@ -0,0 +1,27 @@
+#ifndef _ASM_GENERIC_KEXEC_H
+#define _ASM_GENERIC_KEXEC_H
+
+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifndef KEXEC_AUTO_RESERVED_SIZE
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<27) /* 128M */ +#endif
+#ifndef KEXEC_AUTO_THRESHOLD
+#define KEXEC_AUTO_THRESHOLD (1ULL<<32) /* 4G */
+#endif
+static inline
+unsigned long long arch_default_crash_size(unsigned long long total_size) +{
+ if (total_size < KEXEC_AUTO_THRESHOLD)
+ return 0;
+ else
+ return KEXEC_AUTO_RESERVED_SIZE;
+}
+static inline
+unsigned long long arch_default_crash_base(void)
+{
+ /* 0 means find the base address automatically. */
+ return 0;
+}
+#endif /* CONFIG_KEXEC_AUTO_RESERVE */
+
+#endif

#3 lore raw

PATCH 3/7 ia64: add CONFIG_KEXEC_AUTO_RESERVE

In reply to Amerigo Wang

Introduce a new config option KEXEC_AUTO_RESERVE for ia64.

---

Index: linux-2.6/arch/ia64/Kconfig =================================--- linux-2.6.orig/arch/ia64/Kconfig +++ linux-2.6/arch/ia64/Kconfig
@@ -582,6 +582,16 @@ config KEXEC
support. As of this writing the exact hardware interface is strongly in flux, so no good recommendation can be made.

+config KEXEC_AUTO_RESERVE
+ bool "automatically reserve memory for kexec kernel"
+ depends on KEXEC
+ default y
+ ---help---

+	  Automatically reserve memory for a kexec kernel, so that you don't
+	  need to specify numbers for the "crashkernel=X@Y" boot option,
+	  instead you can use "crashkernel=auto".
+	  On IA64, 256M is reserved and only when you have memory > 4G.

+
config CRASH_DUMP
bool "kernel crash dumps"
depends on IA64_MCA_RECOVERY && !IA64_HP_SIM && (!SMP || HOTPLUG_CPU)

#4 lore raw

PATCH 4/7 ia64: implement crashkernel=auto

In reply to Amerigo Wang

Since in patch 2/7 we already implement the generic part, this will add the rest part for ia64.

---

Index: linux-2.6/arch/ia64/include/asm/kexec.h =================================--- linux-2.6.orig/arch/ia64/include/asm/kexec.h +++ linux-2.6/arch/ia64/include/asm/kexec.h
@@ -19,6 +19,14 @@

                 flush_icache_range(page_addr, page_addr + PAGE_SIZE); \
         } while(0)

+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */ +#include <asm-generic/kexec.h>
+#endif
+
extern struct kimage *ia64_kimage;
extern const unsigned int relocate_new_kernel_size; extern void relocate_new_kernel(unsigned long, unsigned long,

#5 lore raw

Re: [Patch 4/7] ia64: implement crashkernel=auto

Review

Quoted 10 lines · Amerigo Wang
(quoted diff) +8 -0
+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */
+#include <asm-generic/kexec.h>
+#endif
+
 extern struct kimage *ia64_kimage;

IMO that's way too small for practial use on IA64 systems.

For SLES11, which is based on Linux 2.6.28 IIRC, we use following memory size values in the YaST2 kdump module which configures the crashkernel parameter (this is YCP syntax, but I think everybody understands it):

Quoted 11 lines

// bnc #446480 - Fine-tune kdump memory proposal
if ((Arch::ia64()) && (total_memory >= 1024))

{
    integer total_memory_gigabyte = total_memory/1024;
    if ((total_memory_gigabyte >= 1) && (total_memory_gigabyte <12))
        alocated_memory = "256";
    else if ((total_memory_gigabyte >= 12) && (total_memory_gigabyte <128))
        alocated_memory = "512";
    else if ((total_memory_gigabyte >= 128) && (total_memory_gigabyte <256))
        alocated_memory = "768";
    else if ((total_memory_gigabyte >= 256) && (total_memory_gigabyte <378))
Quoted 8 lines
        alocated_memory = "1024";
    else if ((total_memory_gigabyte >= 378) && (total_memory_gigabyte <512))
        alocated_memory = "1536";
    else if ((total_memory_gigabyte >= 512) && (total_memory_gigabyte <768))
        alocated_memory = "2048";
    else if (total_memory_gigabyte >= 768)
        alocated_memory = "3072";
}

I got that assumtions from SGI (and they are known to have large IA64 systems) and I think the values were tested.

But IMO it doesn't make sense to put such policy decisions in the kernel. I see no advantage for that. The average user doesn't have to write crashkernel parameters, they use the values that the distribution ships. Or do you think that an average user knows what a UUID of a file system is just to specify the correct root partition?

Regards,
Bernhard

#6 lore raw

Re: [Patch 4/7] ia64: implement crashkernel=auto

Quoted 42 lines · Bernhard Walle

Review

Quoted 11 lines · Amerigo Wang
(quoted diff) +8 -0
+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */
+#include <asm-generic/kexec.h>
+#endif
+
 extern struct kimage *ia64_kimage;

IMO that's way too small for practial use on IA64 systems.

For SLES11, which is based on Linux 2.6.28 IIRC, we use following memory size values in the YaST2 kdump module which configures the crashkernel parameter (this is YCP syntax, but I think everybody understands it):

Quoted 11 lines

// bnc #446480 - Fine-tune kdump memory proposal
if ((Arch::ia64()) && (total_memory >= 1024))

{
    integer total_memory_gigabyte = total_memory/1024;
    if ((total_memory_gigabyte >= 1) && (total_memory_gigabyte <12))
        alocated_memory = "256";
    else if ((total_memory_gigabyte >= 12) && (total_memory_gigabyte <128))
        alocated_memory = "512";
    else if ((total_memory_gigabyte >= 128) && (total_memory_gigabyte <256))
        alocated_memory = "768";
    else if ((total_memory_gigabyte >= 256) && (total_memory_gigabyte <378))
Quoted 9 lines
        alocated_memory = "1024";
    else if ((total_memory_gigabyte >= 378) && (total_memory_gigabyte <512))
        alocated_memory = "1536";
    else if ((total_memory_gigabyte >= 512) && (total_memory_gigabyte <768))
        alocated_memory = "2048";
    else if (total_memory_gigabyte >= 768)
        alocated_memory = "3072";
}
Quoted 3 lines

I got that assumtions from SGI (and they are known to have large IA64 systems) and I think the values were tested.

Hmm, thanks for this.

Quoted 6 lines

But IMO it doesn't make sense to put such policy decisions in the kernel. I see no advantage for that. The average user doesn't have to write crashkernel parameters, they use the values that the distribution ships. Or do you think that an average user knows what a UUID of a file system is just to specify the correct root partition?

The advantage is that we can provide a clever policy which can't be implemented with current mechanism, e.g. 32nd of phy mem, as proposed by Eric.

#7 lore raw

Re: [Patch 4/7] ia64: implement crashkernel=auto

In reply to Amerigo Wang

Review

Quoted 10 lines · Amerigo Wang
(quoted diff) +8 -0
+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */
+#include <asm-generic/kexec.h>
+#endif
+
 extern struct kimage *ia64_kimage;

IMO that's way too small for practial use on IA64 systems.

For SLES11, which is based on Linux 2.6.28 IIRC, we use following memory size values in the YaST2 kdump module which configures the crashkernel parameter (this is YCP syntax, but I think everybody understands it):

Quoted 11 lines

// bnc #446480 - Fine-tune kdump memory proposal
if ((Arch::ia64()) && (total_memory >= 1024))

{
    integer total_memory_gigabyte = total_memory/1024;
    if ((total_memory_gigabyte >= 1) && (total_memory_gigabyte <12))
        alocated_memory = "256";
    else if ((total_memory_gigabyte >= 12) && (total_memory_gigabyte <128))
        alocated_memory = "512";
    else if ((total_memory_gigabyte >= 128) && (total_memory_gigabyte <256))
        alocated_memory = "768";
    else if ((total_memory_gigabyte >= 256) && (total_memory_gigabyte <378))
Quoted 8 lines
        alocated_memory = "1024";
    else if ((total_memory_gigabyte >= 378) && (total_memory_gigabyte <512))
        alocated_memory = "1536";
    else if ((total_memory_gigabyte >= 512) && (total_memory_gigabyte <768))
        alocated_memory = "2048";
    else if (total_memory_gigabyte >= 768)
        alocated_memory = "3072";
}

I got that assumtions from SGI (and they are known to have large IA64 systems) and I think the values were tested.

But IMO it doesn't make sense to put such policy decisions in the kernel. I see no advantage for that. The average user doesn't have to write crashkernel parameters, they use the values that the distribution ships. Or do you think that an average user knows what a UUID of a file system is just to specify the correct root partition?

Regards,
Bernhard

#8 lore raw

Re: [Patch 4/7] ia64: implement crashkernel=auto

In reply to Amerigo Wang

Review

Quoted 10 lines · Amerigo Wang
(quoted diff) +8 -0
+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */
+#include <asm-generic/kexec.h>
+#endif
+
 extern struct kimage *ia64_kimage;

IMO that's way too small for practial use on IA64 systems.

For SLES11, which is based on Linux 2.6.28 IIRC, we use following memory size values in the YaST2 kdump module which configures the crashkernel parameter (this is YCP syntax, but I think everybody understands it):

Quoted 11 lines

// bnc #446480 - Fine-tune kdump memory proposal
if ((Arch::ia64()) && (total_memory >= 1024))

{
    integer total_memory_gigabyte = total_memory/1024;
    if ((total_memory_gigabyte >= 1) && (total_memory_gigabyte <12))
        alocated_memory = "256";
    else if ((total_memory_gigabyte >= 12) && (total_memory_gigabyte <128))
        alocated_memory = "512";
    else if ((total_memory_gigabyte >= 128) && (total_memory_gigabyte <256))
        alocated_memory = "768";
    else if ((total_memory_gigabyte >= 256) && (total_memory_gigabyte <378))
Quoted 8 lines
        alocated_memory = "1024";
    else if ((total_memory_gigabyte >= 378) && (total_memory_gigabyte <512))
        alocated_memory = "1536";
    else if ((total_memory_gigabyte >= 512) && (total_memory_gigabyte <768))
        alocated_memory = "2048";
    else if (total_memory_gigabyte >= 768)
        alocated_memory = "3072";
}

I got that assumtions from SGI (and they are known to have large IA64 systems) and I think the values were tested.

But IMO it doesn't make sense to put such policy decisions in the kernel. I see no advantage for that. The average user doesn't have to write crashkernel parameters, they use the values that the distribution ships. Or do you think that an average user knows what a UUID of a file system is just to specify the correct root partition?

Regards,
Bernhard

#9 lore raw

PATCH 5/7 powerpc: add CONFIG_KEXEC_AUTO_RESERVE

In reply to Amerigo Wang

Introduce a new config option KEXEC_AUTO_RESERVE for powerpc.

---

Index: linux-2.6/arch/powerpc/Kconfig =================================--- linux-2.6.orig/arch/powerpc/Kconfig +++ linux-2.6/arch/powerpc/Kconfig
@@ -346,6 +346,16 @@ config KEXEC
support. As of this writing the exact hardware interface is strongly in flux, so no good recommendation can be made.

+config KEXEC_AUTO_RESERVE
+ bool "automatically reserve memory for kexec kernel"
+ depends on KEXEC
+ default y
+ ---help---

+	  Automatically reserve memory for a kexec kernel, so that you don't
+	  need to specify numbers for the "crashkernel=X@Y" boot option,
+	  instead you can use "crashkernel=auto".
+	  On PPC, 256M is reserved and only when you have memory > 4G.

+
config CRASH_DUMP
bool "Build a kdump crash kernel"
depends on PPC64 || 6xx

#10 lore raw

PATCH 6/7 powerpc: implement crashkernel=auto

In reply to Amerigo Wang

Since in patch 2/7 we already implement the generic part, this will add the rest part for powerpc.

---

Index: linux-2.6/arch/powerpc/include/asm/kexec.h =================================--- linux-2.6.orig/arch/powerpc/include/asm/kexec.h +++ linux-2.6/arch/powerpc/include/asm/kexec.h
@@ -39,6 +39,14 @@ typedef void (*crash_shutdown_t)(void);

#ifdef CONFIG_KEXEC

+#ifdef CONFIG_KEXEC_AUTO_RESERVE
+#ifdef KEXEC_AUTO_RESERVED_SIZE
+#undef KEXEC_AUTO_RESERVED_SIZE
+#endif
+#define KEXEC_AUTO_RESERVED_SIZE (1ULL<<28) /* 256M */ +#include <asm-generic/kexec.h>
+#endif
+
/*
* This function is responsible for capturing register states if coming
* via panic or invoking dump using sysrq-trigger.

#11 lore raw

PATCH 7/7 doc: update the kdump document

In reply to Amerigo Wang

Update the document for kdump.

---

Index: linux-2.6/Documentation/kdump/kdump.txt =================================--- linux-2.6.orig/Documentation/kdump/kdump.txt +++ linux-2.6/Documentation/kdump/kdump.txt
@@ -147,6 +147,15 @@ System kernel config options
analysis tools require a vmlinux with debug symbols in order to read and analyze a dump file.

+4) Enable "automatically reserve memory for kexec kernel" in
+ "Processor type and features."
+
+ CONFIG_KEXEC_AUTO_RESERVE=y
+

+   This will let you to use "crashkernel=auto", instead of specifying
+   numbers for "crashkernel=". Note, you need to have enough memory.
+   The threshold and reserved memory size are arch-dependent.

+
Dump-capture kernel config options (Arch Independent)
-----------------------------------------------------

@@ -266,6 +275,13 @@ This would mean:
2) if the RAM size is between 512M and 2G (exclusive), then reserve 64M
3) if the RAM size is larger than 2G, then reserve 128M

+Or you can use:
+
+ crashkernel=auto
+
+if you have enough memory. The threshold is 4G, below which this won't work. +Also the automatically reserved memory size would be 128M on x86, 256M on +other platforms that have KEXEC.

Boot into System Kernel