From 17cf870a7d26e4490aeec4d4ad03c105dea7bf8f Mon Sep 17 00:00:00 2001 From: CentOS Sources Date: Tue, 3 Nov 2020 07:07:52 -0500 Subject: [PATCH] import crash-7.2.8-7.el8 --- .crash.metadata | 3 +- .gitignore | 3 +- SOURCES/github_0f29a8ac6b73.patch | 60 + SOURCES/github_105a3e13_to_b5c2359f.patch | 1123 ------------- SOURCES/github_1c45cea02df7.patch | 40 + SOURCES/github_5cbb2fd8_to_6c1c8ac6.patch | 1485 ----------------- SOURCES/github_9596b4388ea5.patch | 909 ++++++++++ SOURCES/github_b80b16549e24.patch | 43 + .../github_b97e7fd4e826_to_8b50d94ada21.patch | 368 ++++ SOURCES/lzo_snappy.patch | 30 +- SOURCES/rhel8_build.patch | 19 +- SPECS/crash.spec | 56 +- 12 files changed, 1499 insertions(+), 2640 deletions(-) create mode 100644 SOURCES/github_0f29a8ac6b73.patch delete mode 100644 SOURCES/github_105a3e13_to_b5c2359f.patch create mode 100644 SOURCES/github_1c45cea02df7.patch delete mode 100644 SOURCES/github_5cbb2fd8_to_6c1c8ac6.patch create mode 100644 SOURCES/github_9596b4388ea5.patch create mode 100644 SOURCES/github_b80b16549e24.patch create mode 100644 SOURCES/github_b97e7fd4e826_to_8b50d94ada21.patch diff --git a/.crash.metadata b/.crash.metadata index 5b8318b..10ef077 100644 --- a/.crash.metadata +++ b/.crash.metadata @@ -1 +1,2 @@ -194a82c2cd9d45478559947fe767fd42be5a668f SOURCES/crash-7.2.7.tar.gz +334bce71a69ccf8abefaf8c4bc5eec67c9b43c9e SOURCES/crash-7.2.8.tar.gz +026f4c9e1c8152a2773354551c523acd32d7f00e SOURCES/gdb-7.6.tar.gz diff --git a/.gitignore b/.gitignore index d5365b1..c11877e 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ -SOURCES/crash-7.2.7.tar.gz +SOURCES/crash-7.2.8.tar.gz +SOURCES/gdb-7.6.tar.gz diff --git a/SOURCES/github_0f29a8ac6b73.patch b/SOURCES/github_0f29a8ac6b73.patch new file mode 100644 index 0000000..492be74 --- /dev/null +++ b/SOURCES/github_0f29a8ac6b73.patch @@ -0,0 +1,60 @@ +commit 0f29a8ac6b731be5bb47cf70355dc99ba6284741 +Author: Dave Anderson +Date: Fri May 8 11:46:04 2020 -0400 + + Replace people.redhat.com references with github equivalents. + (anderson@redhat.com) + +diff --git a/README b/README +index f401b0cf9f6b..bfbaef6d3b4b 100644 +--- a/README ++++ b/README +@@ -32,7 +32,8 @@ + A whitepaper with complete documentation concerning the use of this utility + can be found here: + +- http://people.redhat.com/anderson/crash_whitepaper ++ https://crash-utility.github.io/crash_whitepaper.html ++ + + These are the current prerequisites: + +diff --git a/configure.c b/configure.c +index 75006e881f5a..7f6d19e0b87e 100644 +--- a/configure.c ++++ b/configure.c +@@ -1339,7 +1339,7 @@ make_spec_file(struct supported_gdb_version *sp) + printf("License: %s\n", sp->GPL); + printf("Group: Development/Debuggers\n"); + printf("Source: %%{name}-%%{version}.tar.gz\n"); +- printf("URL: http://people.redhat.com/anderson\n"); ++ printf("URL: https://github.com/crash-utility\n"); + printf("Distribution: Linux 2.2 or greater\n"); + printf("Vendor: Red Hat, Inc.\n"); + printf("Packager: Dave Anderson \n"); +diff --git a/crash.8 b/crash.8 +index 994a2e05b8ab..136ae7859d99 100644 +--- a/crash.8 ++++ b/crash.8 +@@ -867,7 +867,7 @@ command within + .B crash + provides more complete and accurate documentation than this man page. + .PP +-.I http://people.redhat.com/anderson ++.I https://github.com/crash-utility + - the home page of the + .B crash + utility. +diff --git a/help.c b/help.c +index bd2cca80e79a..6476e28d54f9 100644 +--- a/help.c ++++ b/help.c +@@ -9357,7 +9357,7 @@ char *README[] = { + " A whitepaper with complete documentation concerning the use of this utility", + " can be found here:", + " ", +-" http://people.redhat.com/anderson/crash_whitepaper", ++" https://crash-utility.github.io/crash_whitepaper.html", + " ", + " These are the current prerequisites: ", + "", diff --git a/SOURCES/github_105a3e13_to_b5c2359f.patch b/SOURCES/github_105a3e13_to_b5c2359f.patch deleted file mode 100644 index 6c907b5..0000000 --- a/SOURCES/github_105a3e13_to_b5c2359f.patch +++ /dev/null @@ -1,1123 +0,0 @@ -commit 105a3e13167665dde5d3c12bf76ef9c916e82d0e -Author: Dave Anderson -Date: Thu Oct 10 14:07:22 2019 -0400 - - Fix for Linux 5.4-rc1 and later kernels that contain commit - 688fcbfc06e4fdfbb7e1d5a942a1460fe6379d2d, titled "mm/vmalloc: - modify struct vmap_area to reduce its size". Without the - patch "kmem -v" will display nothing; other architectures - that utilize the vmap_area_list to determine the base of - mapped/vmalloc address space will fail. - (anderson@redhat.com) - -diff --git a/memory.c b/memory.c -index 3a8b998..fe82fac 100644 ---- a/memory.c -+++ b/memory.c -@@ -401,9 +401,10 @@ vm_init(void) - STRUCT_SIZE_INIT(vmap_area, "vmap_area"); - if (VALID_MEMBER(vmap_area_va_start) && - VALID_MEMBER(vmap_area_va_end) && -- VALID_MEMBER(vmap_area_flags) && - VALID_MEMBER(vmap_area_list) && - VALID_MEMBER(vmap_area_vm) && -+ (VALID_MEMBER(vmap_area_flags) || -+ (OFFSET(vmap_area_vm) == MEMBER_OFFSET("vmap_area", "purge_list"))) && - kernel_symbol_exists("vmap_area_list")) - vt->flags |= USE_VMAP_AREA; - -@@ -8742,7 +8743,7 @@ static void - dump_vmap_area(struct meminfo *vi) - { - int i, cnt; -- ulong start, end, vm_struct, flags; -+ ulong start, end, vm_struct, flags, vm; - struct list_data list_data, *ld; - char *vmap_area_buf; - ulong size, pcheck, count, verified; -@@ -8790,9 +8791,15 @@ dump_vmap_area(struct meminfo *vi) - readmem(ld->list_ptr[i], KVADDR, vmap_area_buf, - SIZE(vmap_area), "vmap_area struct", FAULT_ON_ERROR); - -- flags = ULONG(vmap_area_buf + OFFSET(vmap_area_flags)); -- if (flags != VM_VM_AREA) -- continue; -+ if (VALID_MEMBER(vmap_area_flags)) { -+ flags = ULONG(vmap_area_buf + OFFSET(vmap_area_flags)); -+ if (flags != VM_VM_AREA) -+ continue; -+ } else { -+ vm = ULONG(vmap_area_buf + OFFSET(vmap_area_vm)); -+ if (!vm) -+ continue; -+ } - start = ULONG(vmap_area_buf + OFFSET(vmap_area_va_start)); - end = ULONG(vmap_area_buf + OFFSET(vmap_area_va_end)); - vm_struct = ULONG(vmap_area_buf + OFFSET(vmap_area_vm)); - -commit 82ce13bceb1082a7c53c1bda71e17ca9c2a5cbc4 -Author: Dave Anderson -Date: Fri Oct 11 11:14:28 2019 -0400 - - Fix for Linux 5.4-rc1 and later kernels that contain commit/merge - e0703556644a531e50b5dc61b9f6ea83af5f6604, titled "Merge tag 'modules- - for-v5.4' of git://git.kernel.org/pub/scm/linux/kernel/git/jeyu/linux - which introduces symbol namespaces. Without the patch, and depending - upon the architecture: - (1) the kernel module symbol list will contain garbage entries - (2) the session fails during session initialization with a dump of - the internal buffer allocation stats followed by the message - "crash: cannot allocate any more memory!" - (3) the session fails during session initialization with a - segmentation violation. - (anderson@redhat.com) - -diff --git a/defs.h b/defs.h -index 32bd147..502e7c2 100644 ---- a/defs.h -+++ b/defs.h -@@ -2694,6 +2694,7 @@ struct symbol_table_data { - ulong saved_command_line_vmlinux; - ulong pti_init_vmlinux; - ulong kaiser_init_vmlinux; -+ int kernel_symbol_type; - }; - - /* flags for st */ -diff --git a/symbols.c b/symbols.c -index 3ce8692..7af5e69 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -1607,39 +1607,100 @@ union kernel_symbol { - unsigned long value; - const char *name; - } v1; -- /* kernel 4.19 introduced relative symbol positionning */ -+ /* kernel 4.19 introduced relative symbol positioning */ - struct kernel_symbol_v2 { - int value_offset; - int name_offset; - } v2; -+ /* kernel 5.4 introduced symbol namespaces */ -+ struct kernel_symbol_v3 { -+ int value_offset; -+ int name_offset; -+ int namespace_offset; -+ } v3; -+ struct kernel_symbol_v4 { -+ unsigned long value; -+ const char *name; -+ const char *namespace; -+ } v4; - }; - -+static size_t -+kernel_symbol_type_init(void) -+{ -+ if (MEMBER_EXISTS("kernel_symbol", "value") && -+ MEMBER_EXISTS("kernel_symbol", "name")) { -+ if (MEMBER_EXISTS("kernel_symbol", "namespace")) { -+ st->kernel_symbol_type = 4; -+ return (sizeof(struct kernel_symbol_v4)); -+ } else { -+ st->kernel_symbol_type = 1; -+ return (sizeof(struct kernel_symbol_v1)); -+ } -+ } -+ if (MEMBER_EXISTS("kernel_symbol", "value_offset") && -+ MEMBER_EXISTS("kernel_symbol", "name_offset")) { -+ if (MEMBER_EXISTS("kernel_symbol", "namespace_offset")) { -+ st->kernel_symbol_type = 3; -+ return (sizeof(struct kernel_symbol_v3)); -+ } else { -+ st->kernel_symbol_type = 2; -+ return (sizeof(struct kernel_symbol_v2)); -+ } -+ } -+ -+ error(FATAL, "kernel_symbol data structure has changed\n"); -+ -+ return 0; -+} -+ - static ulong - modsym_name(ulong syms, union kernel_symbol *modsym, int i) - { -- if (VALID_MEMBER(kernel_symbol_value)) -+ switch (st->kernel_symbol_type) -+ { -+ case 1: - return (ulong)modsym->v1.name; -+ case 2: -+ return (syms + i * sizeof(struct kernel_symbol_v2) + -+ offsetof(struct kernel_symbol_v2, name_offset) + -+ modsym->v2.name_offset); -+ case 3: -+ return (syms + i * sizeof(struct kernel_symbol_v3) + -+ offsetof(struct kernel_symbol_v3, name_offset) + -+ modsym->v3.name_offset); -+ case 4: -+ return (ulong)modsym->v4.name; -+ } - -- return syms + i * sizeof(struct kernel_symbol_v2) + -- offsetof(struct kernel_symbol_v2, name_offset) + -- modsym->v2.name_offset; -+ return 0; - } - - static ulong - modsym_value(ulong syms, union kernel_symbol *modsym, int i) - { -- if (VALID_MEMBER(kernel_symbol_value)) -+ switch (st->kernel_symbol_type) -+ { -+ case 1: - return (ulong)modsym->v1.value; -+ case 2: -+ return (syms + i * sizeof(struct kernel_symbol_v2) + -+ offsetof(struct kernel_symbol_v2, value_offset) + -+ modsym->v2.value_offset); -+ case 3: -+ return (syms + i * sizeof(struct kernel_symbol_v3) + -+ offsetof(struct kernel_symbol_v3, value_offset) + -+ modsym->v3.value_offset); -+ case 4: -+ return (ulong)modsym->v4.value; -+ } - -- return syms + i * sizeof(struct kernel_symbol_v2) + -- offsetof(struct kernel_symbol_v2, value_offset) + -- modsym->v2.value_offset; -+ return 0; - } - - void - store_module_symbols_v2(ulong total, int mods_installed) - { -- - int i, m; - ulong mod, mod_next; - char *mod_name; -@@ -1675,12 +1736,7 @@ store_module_symbols_v2(ulong total, int mods_installed) - "re-initialization of module symbols not implemented yet!\n"); - } - -- MEMBER_OFFSET_INIT(kernel_symbol_value, "kernel_symbol", "value"); -- if (VALID_MEMBER(kernel_symbol_value)) { -- kernel_symbol_size = sizeof(struct kernel_symbol_v1); -- } else { -- kernel_symbol_size = sizeof(struct kernel_symbol_v2); -- } -+ kernel_symbol_size = kernel_symbol_type_init(); - - if ((st->ext_module_symtable = (struct syment *) - calloc(total, sizeof(struct syment))) == NULL) -@@ -3418,6 +3474,8 @@ dump_symbol_table(void) - fprintf(fp, "\n"); - } else - fprintf(fp, "(none)\n"); -+ -+ fprintf(fp, " kernel_symbol_type: v%d\n", st->kernel_symbol_type); - } - - - -commit c1ac656508ad064ef0ef222acb73621ae0bf4f00 -Author: Dave Anderson -Date: Tue Oct 15 11:21:55 2019 -0400 - - Fix for the "timer -r" option on Linux 5.4-rc1 and later kernels - that contain commit 511885d7061eda3eb1faf3f57dcc936ff75863f1, titled - "lib/timerqueue: Rely on rbtree semantics for next timer". Without - the patch, the option fails with the following error "timer: invalid - structure member offset: timerqueue_head_next". - (k-hagio@ab.jp.nec.com) - -diff --git a/defs.h b/defs.h -index 502e7c2..efa40b9 100644 ---- a/defs.h -+++ b/defs.h -@@ -2073,6 +2073,8 @@ struct offset_table { /* stash of commonly-used offsets */ - long cpu_context_save_r7; - long dentry_d_sb; - long device_private_knode_class; -+ long timerqueue_head_rb_root; -+ long rb_root_cached_rb_leftmost; - }; - - struct size_table { /* stash of commonly-used sizes */ -diff --git a/kernel.c b/kernel.c -index 375e1b4..c4cb001 100644 ---- a/kernel.c -+++ b/kernel.c -@@ -783,7 +783,13 @@ kernel_init() - MEMBER_OFFSET_INIT(timerqueue_node_expires, - "timerqueue_node", "expires"); - MEMBER_OFFSET_INIT(timerqueue_node_node, -- "timerqueue_node_node", "node"); -+ "timerqueue_node", "node"); -+ if (INVALID_MEMBER(timerqueue_head_next)) { -+ MEMBER_OFFSET_INIT(timerqueue_head_rb_root, -+ "timerqueue_head", "rb_root"); -+ MEMBER_OFFSET_INIT(rb_root_cached_rb_leftmost, -+ "rb_root_cached", "rb_leftmost"); -+ } - } - MEMBER_OFFSET_INIT(hrtimer_softexpires, "hrtimer", "_softexpires"); - MEMBER_OFFSET_INIT(hrtimer_function, "hrtimer", "function"); -@@ -7647,11 +7653,17 @@ next_one: - readmem((ulong)(base + OFFSET(hrtimer_clock_base_first)), - KVADDR, &curr, sizeof(curr), "hrtimer_clock_base first", - FAULT_ON_ERROR); -- else -+ else if (VALID_MEMBER(timerqueue_head_next)) - readmem((ulong)(base + OFFSET(hrtimer_clock_base_active) + - OFFSET(timerqueue_head_next)), - KVADDR, &curr, sizeof(curr), "hrtimer_clock base", - FAULT_ON_ERROR); -+ else -+ readmem((ulong)(base + OFFSET(hrtimer_clock_base_active) + -+ OFFSET(timerqueue_head_rb_root) + -+ OFFSET(rb_root_cached_rb_leftmost)), -+ KVADDR, &curr, sizeof(curr), -+ "hrtimer_clock_base active", FAULT_ON_ERROR); - - while (curr && i < next) { - curr = rb_next(curr); -diff --git a/symbols.c b/symbols.c -index 7af5e69..eb88ca1 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -10032,6 +10032,8 @@ dump_offset_table(char *spec, ulong makestruct) - OFFSET(rb_node_rb_left)); - fprintf(fp, " rb_node_rb_right: %ld\n", - OFFSET(rb_node_rb_right)); -+ fprintf(fp, " rb_root_cached_rb_leftmost: %ld\n", -+ OFFSET(rb_root_cached_rb_leftmost)); - - fprintf(fp, " x8664_pda_pcurrent: %ld\n", - OFFSET(x8664_pda_pcurrent)); -@@ -10388,6 +10390,8 @@ dump_offset_table(char *spec, ulong makestruct) - OFFSET(hrtimer_function)); - fprintf(fp, " timerqueue_head_next: %ld\n", - OFFSET(timerqueue_head_next)); -+ fprintf(fp, " timerqueue_head_rb_root: %ld\n", -+ OFFSET(timerqueue_head_rb_root)); - fprintf(fp, " timerqueue_node_expires: %ld\n", - OFFSET(timerqueue_node_expires)); - fprintf(fp, " timerqueue_node_node: %ld\n", - -commit e13fe8ba5a0b9c54edea103a309e9879784d9b94 -Author: Dave Anderson -Date: Tue Oct 15 16:29:30 2019 -0400 - - Fix for a "[-Wstringop-truncation]" compiler warning emitted when - symbols.c is built in a Fedora Rawhide environment with gcc-9.0.1 - or later. - (anderson@redhat.com) - -diff --git a/symbols.c b/symbols.c -index eb88ca1..55199fc 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -8174,8 +8174,10 @@ parse_for_member_extended(struct datatype_member *dm, - */ - - if (current && p && (p - p1 < BUFSIZE)) { -- strncpy(current->field_name, p1, p - p1); -+// strncpy(current->field_name, p1, p - p1); (NOTE: gcc-9.0.1 emits [-Wstringop-truncation] warning) - current->field_len = p - p1; -+ memcpy(current->field_name, p1, current->field_len); -+ current->field_name[current->field_len] = '\0'; - } - - if ( p && (*s_e != '{' || (*s_e == '{' && buf[len] == '}') )) { - -commit 9937878cce2fc049283d833685cb939caca462ca -Author: Dave Anderson -Date: Thu Oct 17 12:00:23 2019 -0400 - - Fix for the "kmem -n" option on Linux-5.4-rc1 and later kernels that - contain commit b6c88d3b9d38f9448e0fcf44847a075ea81d5ca2, titled - "drivers/base/memory.c: don't store end_section_nr in memory blocks". - Without the patch, the command option fails with the error message - "kmem: invalid structure member offset: memory_block_end_section_nr". - (msys.mizuma@gmail.com) - -diff --git a/help.c b/help.c -index a5218a7..cfd46c3 100644 ---- a/help.c -+++ b/help.c -@@ -7177,7 +7177,7 @@ char *help_kmem[] = { - " 6 ffff88003d4d90c0 ffffea0000000000 ffffea0000c00000 PM 196608", - " 7 ffff88003d4d90e0 ffffea0000000000 ffffea0000e00000 PM 229376", - " ", --" MEM_BLOCK NAME PHYSICAL RANGE STATE SECTIONS", -+" MEM_BLOCK NAME PHYSICAL RANGE STATE START_SECTION_NO", - " ffff88003a707c00 memory0 0 - 7ffffff ONLINE 0", - " ffff88003a6e0000 memory1 8000000 - fffffff ONLINE 1", - " ffff88003a6e1000 memory2 10000000 - 17ffffff ONLINE 2", -diff --git a/memory.c b/memory.c -index fe82fac..0a79838 100644 ---- a/memory.c -+++ b/memory.c -@@ -17402,20 +17402,18 @@ fill_memory_block_name(ulong memblock, char *name) - } - - static void --fill_memory_block_srange(ulong start_sec, ulong end_sec, char *srange) -+fill_memory_block_srange(ulong start_sec, char *srange) - { - memset(srange, 0, sizeof(*srange) * BUFSIZE); - -- if (start_sec == end_sec) -- sprintf(srange, "%lu", start_sec); -- else -- sprintf(srange, "%lu-%lu", start_sec, end_sec); -+ sprintf(srange, "%lu", start_sec); - } - - static void - print_memory_block(ulong memory_block) - { -- ulong start_sec, end_sec, start_pfn, end_pfn, nid; -+ ulong start_sec, end_sec, nid; -+ ulong memblock_size, mbs, start_addr, end_addr; - char statebuf[BUFSIZE]; - char srangebuf[BUFSIZE]; - char name[BUFSIZE]; -@@ -17430,15 +17428,25 @@ print_memory_block(ulong memory_block) - readmem(memory_block + OFFSET(memory_block_start_section_nr), KVADDR, - &start_sec, sizeof(void *), "memory_block start_section_nr", - FAULT_ON_ERROR); -- readmem(memory_block + OFFSET(memory_block_end_section_nr), KVADDR, -- &end_sec, sizeof(void *), "memory_block end_section_nr", -- FAULT_ON_ERROR); - -- start_pfn = section_nr_to_pfn(start_sec); -- end_pfn = section_nr_to_pfn(end_sec + 1); -+ start_addr = pfn_to_phys(section_nr_to_pfn(start_sec)); -+ -+ if (symbol_exists("memory_block_size_probed")) { -+ memblock_size = symbol_value("memory_block_size_probed"); -+ readmem(memblock_size, KVADDR, -+ &mbs, sizeof(ulong), "memory_block_size_probed", -+ FAULT_ON_ERROR); -+ end_addr = start_addr + mbs - 1; -+ } else { -+ readmem(memory_block + OFFSET(memory_block_end_section_nr), KVADDR, -+ &end_sec, sizeof(void *), "memory_block end_section_nr", -+ FAULT_ON_ERROR); -+ end_addr = pfn_to_phys(section_nr_to_pfn(end_sec + 1)) - 1; -+ } -+ - fill_memory_block_state(memory_block, statebuf); - fill_memory_block_name(memory_block, name); -- fill_memory_block_srange(start_sec, end_sec, srangebuf); -+ fill_memory_block_srange(start_sec, srangebuf); - - if (MEMBER_EXISTS("memory_block", "nid")) { - readmem(memory_block + OFFSET(memory_block_nid), KVADDR, &nid, -@@ -17448,9 +17456,9 @@ print_memory_block(ulong memory_block) - MKSTR(memory_block)), - mkstring(buf2, 12, CENTER, name), - mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX, -- MKSTR(pfn_to_phys(start_pfn))), -+ MKSTR(start_addr)), - mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX, -- MKSTR(pfn_to_phys(end_pfn) - 1)), -+ MKSTR(end_addr)), - mkstring(buf5, strlen("NODE"), CENTER|LONG_DEC, - MKSTR(nid)), - mkstring(buf6, strlen("CANCEL_OFFLINE"), LJUST, -@@ -17462,9 +17470,9 @@ print_memory_block(ulong memory_block) - MKSTR(memory_block)), - mkstring(buf2, 10, CENTER, name), - mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX, -- MKSTR(pfn_to_phys(start_pfn))), -+ MKSTR(start_addr)), - mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX, -- MKSTR(pfn_to_phys(end_pfn) - 1)), -+ MKSTR(end_addr)), - mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST, - statebuf), - mkstring(buf6, 12, LJUST, srangebuf)); -@@ -17552,14 +17560,14 @@ dump_memory_blocks(int initialize) - mkstring(buf3, PADDR_PRLEN*2 + 2, CENTER, "PHYSICAL RANGE"), - mkstring(buf4, strlen("NODE"), CENTER, "NODE"), - mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST, "STATE"), -- mkstring(buf6, 12, LJUST, "SECTIONS")); -+ mkstring(buf6, 12, LJUST, "START_SECTION_NO")); - else - sprintf(mb_hdr, "\n%s %s %s %s %s\n", - mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "MEM_BLOCK"), - mkstring(buf2, 10, CENTER, "NAME"), - mkstring(buf3, PADDR_PRLEN*2, CENTER, "PHYSICAL RANGE"), - mkstring(buf4, strlen("CANCEL_OFFLINE"), LJUST, "STATE"), -- mkstring(buf5, 12, LJUST, "SECTIONS")); -+ mkstring(buf5, 12, LJUST, "START_SECTION_NO")); - fprintf(fp, "%s", mb_hdr); - - for (i = 0; i < klistcnt; i++) { - -commit 1f9e0ac5d0b43004639e304f718177ff4c82343b -Author: Dave Anderson -Date: Sat Oct 19 16:43:16 2019 -0400 - - Fix for Linux 4.19.5 and later 4.19-based x86_64 kernels which - are NOT configured with CONFIG_RANDOMIZE_BASE and have backported - kernel commit d52888aa2753e3063a9d3a0c9f72f94aa9809c15, titled - "x86/mm: Move LDT remap out of KASLR region on 5-level paging", - which modified the 4-level and 5-level paging PAGE_OFFSET values. - Without this patch, the crash session fails during initialization - with the error message "crash: seek error: kernel virtual address: -
type: "tss_struct ist array". - (anderson@redhat.com) - -diff --git a/x86_64.c b/x86_64.c -index d57b602..c7967bd 100644 ---- a/x86_64.c -+++ b/x86_64.c -@@ -382,7 +382,7 @@ x86_64_init(int when) - - case POST_GDB: - if (!(machdep->flags & RANDOMIZED) && -- ((THIS_KERNEL_VERSION >= LINUX(4,20,0)) || -+ ((THIS_KERNEL_VERSION >= LINUX(4,19,5)) || - ((THIS_KERNEL_VERSION >= LINUX(4,14,84)) && - (THIS_KERNEL_VERSION < LINUX(4,15,0))))) { - machdep->machspec->page_offset = machdep->flags & VM_5LEVEL ? - -commit 1d2bc0c65792d15f94ebfd97c22da620b74634fa -Author: Dave Anderson -Date: Mon Oct 21 11:46:01 2019 -0400 - - Additional fix for the "kmem -n" option on Linux-5.4-rc1 and later - kernels that contain commit b6c88d3b9d38f9448e0fcf44847a075ea81d5ca2, - titled "drivers/base/memory.c: don't store end_section_nr in memory - blocks". The initial fix only addressed the x86_64 architecture; - this incremental patch addresses the other architectures. - (msys.mizuma@gmail.com) - -diff --git a/help.c b/help.c -index cfd46c3..2b2285b 100644 ---- a/help.c -+++ b/help.c -@@ -7177,15 +7177,15 @@ char *help_kmem[] = { - " 6 ffff88003d4d90c0 ffffea0000000000 ffffea0000c00000 PM 196608", - " 7 ffff88003d4d90e0 ffffea0000000000 ffffea0000e00000 PM 229376", - " ", --" MEM_BLOCK NAME PHYSICAL RANGE STATE START_SECTION_NO", --" ffff88003a707c00 memory0 0 - 7ffffff ONLINE 0", --" ffff88003a6e0000 memory1 8000000 - fffffff ONLINE 1", --" ffff88003a6e1000 memory2 10000000 - 17ffffff ONLINE 2", --" ffff88003a6e1400 memory3 18000000 - 1fffffff ONLINE 3", --" ffff88003a6e1800 memory4 20000000 - 27ffffff ONLINE 4", --" ffff88003a6e0400 memory5 28000000 - 2fffffff ONLINE 5", --" ffff88003a6e0800 memory6 30000000 - 37ffffff ONLINE 6", --" ffff88003a6e0c00 memory7 38000000 - 3fffffff ONLINE 7", -+" MEM_BLOCK NAME PHYSICAL RANGE STATE START_SECTION_NO", -+" ffff88003a707c00 memory0 0 - 7ffffff ONLINE 0", -+" ffff88003a6e0000 memory1 8000000 - fffffff ONLINE 1", -+" ffff88003a6e1000 memory2 10000000 - 17ffffff ONLINE 2", -+" ffff88003a6e1400 memory3 18000000 - 1fffffff ONLINE 3", -+" ffff88003a6e1800 memory4 20000000 - 27ffffff ONLINE 4", -+" ffff88003a6e0400 memory5 28000000 - 2fffffff ONLINE 5", -+" ffff88003a6e0800 memory6 30000000 - 37ffffff ONLINE 6", -+" ffff88003a6e0c00 memory7 38000000 - 3fffffff ONLINE 7", - - "\n Translate a page structure's flags field contents:\n", - " %s> kmem -g 4080", -diff --git a/memory.c b/memory.c -index 0a79838..f36685b 100644 ---- a/memory.c -+++ b/memory.c -@@ -17401,6 +17401,23 @@ fill_memory_block_name(ulong memblock, char *name) - read_string(value, name, BUFSIZE-1); - } - -+static void -+fill_memory_block_parange(ulong saddr, ulong eaddr, char *parange) -+{ -+ char buf1[BUFSIZE]; -+ char buf2[BUFSIZE]; -+ -+ memset(parange, 0, sizeof(*parange) * BUFSIZE); -+ -+ if (eaddr == ULLONG_MAX) -+ sprintf(parange, "%s", -+ mkstring(buf1, PADDR_PRLEN*2 + 3, CENTER|LONG_HEX, MKSTR(saddr))); -+ else -+ sprintf(parange, "%s - %s", -+ mkstring(buf1, PADDR_PRLEN, RJUST|LONG_HEX, MKSTR(saddr)), -+ mkstring(buf2, PADDR_PRLEN, RJUST|LONG_HEX, MKSTR(eaddr))); -+} -+ - static void - fill_memory_block_srange(ulong start_sec, char *srange) - { -@@ -17413,14 +17430,13 @@ static void - print_memory_block(ulong memory_block) - { - ulong start_sec, end_sec, nid; -- ulong memblock_size, mbs, start_addr, end_addr; -+ ulong memblock_size, mbs, start_addr, end_addr = ULLONG_MAX; - char statebuf[BUFSIZE]; - char srangebuf[BUFSIZE]; -+ char parangebuf[BUFSIZE]; - char name[BUFSIZE]; - char buf1[BUFSIZE]; - char buf2[BUFSIZE]; -- char buf3[BUFSIZE]; -- char buf4[BUFSIZE]; - char buf5[BUFSIZE]; - char buf6[BUFSIZE]; - char buf7[BUFSIZE]; -@@ -17437,7 +17453,7 @@ print_memory_block(ulong memory_block) - &mbs, sizeof(ulong), "memory_block_size_probed", - FAULT_ON_ERROR); - end_addr = start_addr + mbs - 1; -- } else { -+ } else if (MEMBER_EXISTS("memory_block", "end_section_nr")) { - readmem(memory_block + OFFSET(memory_block_end_section_nr), KVADDR, - &end_sec, sizeof(void *), "memory_block end_section_nr", - FAULT_ON_ERROR); -@@ -17446,34 +17462,29 @@ print_memory_block(ulong memory_block) - - fill_memory_block_state(memory_block, statebuf); - fill_memory_block_name(memory_block, name); -+ fill_memory_block_parange(start_addr, end_addr, parangebuf); - fill_memory_block_srange(start_sec, srangebuf); - - if (MEMBER_EXISTS("memory_block", "nid")) { - readmem(memory_block + OFFSET(memory_block_nid), KVADDR, &nid, - sizeof(void *), "memory_block nid", FAULT_ON_ERROR); -- fprintf(fp, " %s %s %s - %s %s %s %s\n", -+ fprintf(fp, " %s %s %s %s %s %s\n", - mkstring(buf1, VADDR_PRLEN, LJUST|LONG_HEX, - MKSTR(memory_block)), - mkstring(buf2, 12, CENTER, name), -- mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX, -- MKSTR(start_addr)), -- mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX, -- MKSTR(end_addr)), -+ parangebuf, - mkstring(buf5, strlen("NODE"), CENTER|LONG_DEC, - MKSTR(nid)), -- mkstring(buf6, strlen("CANCEL_OFFLINE"), LJUST, -+ mkstring(buf6, strlen("OFFLINE"), LJUST, - statebuf), - mkstring(buf7, 12, LJUST, srangebuf)); - } else -- fprintf(fp, " %s %s %s - %s %s %s\n", -+ fprintf(fp, " %s %s %s %s %s\n", - mkstring(buf1, VADDR_PRLEN, LJUST|LONG_HEX, - MKSTR(memory_block)), - mkstring(buf2, 10, CENTER, name), -- mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX, -- MKSTR(start_addr)), -- mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX, -- MKSTR(end_addr)), -- mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST, -+ parangebuf, -+ mkstring(buf5, strlen("OFFLINE"), LJUST, - statebuf), - mkstring(buf6, 12, LJUST, srangebuf)); - } -@@ -17537,6 +17548,7 @@ dump_memory_blocks(int initialize) - int klistcnt, i; - struct list_data list_data; - char mb_hdr[BUFSIZE]; -+ char paddr_hdr[BUFSIZE]; - char buf1[BUFSIZE]; - char buf2[BUFSIZE]; - char buf3[BUFSIZE]; -@@ -17553,20 +17565,26 @@ dump_memory_blocks(int initialize) - - init_memory_block(&list_data, &klistcnt, &klistbuf); - -+ if ((symbol_exists("memory_block_size_probed")) || -+ (MEMBER_EXISTS("memory_block", "end_section_nr"))) -+ sprintf(paddr_hdr, "%s", "PHYSICAL RANGE"); -+ else -+ sprintf(paddr_hdr, "%s", "PHYSICAL START"); -+ - if (MEMBER_EXISTS("memory_block", "nid")) -- sprintf(mb_hdr, "\n%s %s %s %s %s %s\n", -+ sprintf(mb_hdr, "\n%s %s %s %s %s %s\n", - mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "MEM_BLOCK"), - mkstring(buf2, 10, CENTER, "NAME"), -- mkstring(buf3, PADDR_PRLEN*2 + 2, CENTER, "PHYSICAL RANGE"), -+ mkstring(buf3, PADDR_PRLEN*2 + 2, CENTER, paddr_hdr), - mkstring(buf4, strlen("NODE"), CENTER, "NODE"), -- mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST, "STATE"), -+ mkstring(buf5, strlen("OFFLINE"), LJUST, "STATE"), - mkstring(buf6, 12, LJUST, "START_SECTION_NO")); - else -- sprintf(mb_hdr, "\n%s %s %s %s %s\n", -+ sprintf(mb_hdr, "\n%s %s %s %s %s\n", - mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "MEM_BLOCK"), - mkstring(buf2, 10, CENTER, "NAME"), -- mkstring(buf3, PADDR_PRLEN*2, CENTER, "PHYSICAL RANGE"), -- mkstring(buf4, strlen("CANCEL_OFFLINE"), LJUST, "STATE"), -+ mkstring(buf3, PADDR_PRLEN*2, CENTER, paddr_hdr), -+ mkstring(buf4, strlen("OFFLINE"), LJUST, "STATE"), - mkstring(buf5, 12, LJUST, "START_SECTION_NO")); - fprintf(fp, "%s", mb_hdr); - - -commit 869f3b24fc3f1dd236b58e1cff86fb4e68da76cf -Author: Dave Anderson -Date: Tue Oct 22 16:42:57 2019 -0400 - - In the unlikely event that the panic task in a dumpfile cannot be - determined by the normal means, scan the kernel log buffer for panic - keywords, and if found, generate the panic task from the CPU number - that is specified following the panic message. - (chenqiwu@xiaomi.com) - -diff --git a/task.c b/task.c -index 829c794..8dd2b96 100644 ---- a/task.c -+++ b/task.c -@@ -48,6 +48,9 @@ static void show_tgid_list(ulong); - static int compare_start_time(const void *, const void *); - static int start_time_timespec(void); - static ulonglong convert_start_time(ulonglong, ulonglong); -+static ulong search_panic_task_by_cpu(char *); -+static ulong search_panic_task_by_keywords(char *, int *); -+static ulong get_log_panic_task(void); - static ulong get_dumpfile_panic_task(void); - static ulong get_active_set_panic_task(void); - static void populate_panic_threads(void); -@@ -132,6 +135,23 @@ static struct sched_policy_info { - { ULONG_MAX, NULL } - }; - -+enum PANIC_TASK_FOUND_RESULT { -+ FOUND_NO_PANIC_KEYWORD, -+ FOUND_PANIC_KEYWORD, -+ FOUND_PANIC_TASK -+}; -+ -+const char *panic_keywords[] = { -+ "Unable to handle kernel", -+ "BUG: unable to handle kernel", -+ "Kernel BUG at", -+ "kernel BUG at", -+ "Bad mode in", -+ "Oops", -+ "Kernel panic", -+ NULL, -+}; -+ - /* - * Figure out how much space will be required to hold the task context - * data, malloc() it, and call refresh_task_table() to fill it up. -@@ -6116,8 +6136,8 @@ get_panic_ksp(struct bt_info *bt, ulong *ksp) - - /* - * Look for kcore's storage information for the system's panic state. -- * If it's not there (somebody else's dump format?), look through all the -- * stack traces for evidence of panic. -+ * If it's not there (somebody else's dump format?), look through all -+ * the stack traces or the log buffer for evidence of panic. - */ - static ulong - get_panic_context(void) -@@ -6321,6 +6341,13 @@ get_panicmsg(char *buf) - break; - } - } -+ rewind(pc->tmpfile); -+ while (!msg_found && fgets(buf, BUFSIZE, pc->tmpfile)) { -+ if (strstr(buf, "Bad mode in ")) { -+ msg_found = TRUE; -+ break; -+ } -+ } - - close_tmpfile(); - -@@ -7401,6 +7428,8 @@ panic_search(void) - - close_tmpfile(); - -+ pc->curcmd = pc->program_name; -+ - if (!found && (dietask > (NO_TASK+1)) && task_has_cpu(dietask, NULL)) { - lasttask = dietask; - found = TRUE; -@@ -7410,9 +7439,16 @@ panic_search(void) - error(WARNING, "multiple active tasks have called die\n\n"); - - if (CRASHDEBUG(1) && found) -- error(INFO, "panic_search: %lx (via foreach bt)\n", -+ error(INFO, "panic_search: %lx (via foreach bt)\n", - lasttask); - -+ if (!found) { -+ if (CRASHDEBUG(1)) -+ error(INFO, "panic_search: failed (via foreach bt)\n"); -+ if ((lasttask = get_log_panic_task())) -+ found = TRUE; -+ } -+ - found_panic_task: - populate_panic_threads(); - -@@ -7430,11 +7466,114 @@ found_panic_task: - } - - if (CRASHDEBUG(1)) -- error(INFO, "panic_search: failed (via foreach bt)\n"); -+ error(INFO, "panic_search: failed\n"); - - return NULL; - } - -+static ulong -+search_panic_task_by_cpu(char *buf) -+{ -+ int crashing_cpu; -+ char *p1, *p2; -+ ulong task = NO_TASK; -+ -+ p1 = NULL; -+ -+ if ((p1 = strstr(buf, "CPU: "))) -+ p1 += strlen("CPU: "); -+ else if (STRNEQ(buf, "CPU ")) -+ p1 = buf + strlen("CPU "); -+ -+ if (p1) { -+ p2 = p1; -+ while (!whitespace(*p2) && (*p2 != '\n')) -+ p2++; -+ *p2 = NULLCHAR; -+ crashing_cpu = dtol(p1, RETURN_ON_ERROR, NULL); -+ if ((crashing_cpu >= 0) && in_cpu_map(ONLINE_MAP, crashing_cpu)) { -+ task = tt->active_set[crashing_cpu]; -+ if (CRASHDEBUG(1)) -+ error(WARNING, -+ "get_log_panic_task: active_set[%d]: %lx\n", -+ crashing_cpu, tt->active_set[crashing_cpu]); -+ } -+ } -+ return task; -+} -+ -+static ulong -+search_panic_task_by_keywords(char *buf, int *found_flag) -+{ -+ char *p; -+ int i = 0; -+ ulong task; -+ -+ while (panic_keywords[i]) { -+ if ((p = strstr(buf, panic_keywords[i]))) { -+ if ((task = search_panic_task_by_cpu(p))) { -+ *found_flag = FOUND_PANIC_TASK; -+ return task; -+ } else { -+ *found_flag = FOUND_PANIC_KEYWORD; -+ return NO_TASK; -+ } -+ } -+ i++; -+ } -+ *found_flag = FOUND_NO_PANIC_KEYWORD; -+ return NO_TASK; -+} -+ -+/* -+ * Search for the panic task by seeking panic keywords from kernel log buffer. -+ * The panic keyword is generally followed by printing out the stack trace info -+ * of the panicking task. We can determine the panic task by finding the first -+ * instance of "CPU: " or "CPU " following the panic keywords. -+ */ -+static ulong -+get_log_panic_task(void) -+{ -+ int found_flag = FOUND_NO_PANIC_KEYWORD; -+ int found_panic_keyword = FALSE; -+ ulong task = NO_TASK; -+ char buf[BUFSIZE]; -+ -+ if (!get_active_set()) -+ goto fail; -+ -+ BZERO(buf, BUFSIZE); -+ open_tmpfile(); -+ dump_log(SHOW_LOG_TEXT); -+ rewind(pc->tmpfile); -+ while (fgets(buf, BUFSIZE, pc->tmpfile)) { -+ if (!found_panic_keyword) { -+ task = search_panic_task_by_keywords(buf, &found_flag); -+ switch (found_flag) { -+ case FOUND_PANIC_TASK: -+ goto found_panic_task; -+ case FOUND_PANIC_KEYWORD: -+ found_panic_keyword = TRUE; -+ continue; -+ default: -+ continue; -+ } -+ } else { -+ task = search_panic_task_by_cpu(buf); -+ if (task) -+ goto found_panic_task; -+ } -+ } -+ -+found_panic_task: -+ close_tmpfile(); -+fail: -+ if (CRASHDEBUG(1) && !task) -+ error(WARNING, "cannot determine the panic task from kernel log buffer\n"); -+ -+ return task; -+} -+ - /* - * Get the panic task from the appropriate dumpfile handler. - */ - -commit 6a466f8afbb0dcdf4ddc5ef37aec6d343c2636c6 -Author: Dave Anderson -Date: Mon Nov 4 11:56:28 2019 -0500 - - Adjust a crash-7.1.8 patch for support of /proc/kcore as the live - memory source in Linux 4.8 and later x86_64 kernels configured with - CONFIG_RANDOMIZE_BASE, which randomizes the unity-mapping PAGE_OFFSET - value. Since the problem only arises before the determination of the - randomized PAGE_OFFSET value, restrict the patch such that it only - takes effect during session initialization. - (anderson@redhat.com) - -diff --git a/netdump.c b/netdump.c -index 55b64e6..fdaecf3 100644 ---- a/netdump.c -+++ b/netdump.c -@@ -4269,7 +4269,8 @@ read_proc_kcore(int fd, void *bufptr, int cnt, ulong addr, physaddr_t paddr) - * If KASLR, the PAGE_OFFSET may be unknown early on, so try - * the (hopefully) mapped kernel address first. - */ -- if ((pc->curcmd_flags & MEMTYPE_KVADDR) && (kvaddr != addr)) { -+ if (!(pc->flags & RUNTIME) && -+ (pc->curcmd_flags & MEMTYPE_KVADDR) && (kvaddr != addr)) { - pc->curcmd_flags &= ~MEMTYPE_KVADDR; - for (i = 0; i < pkd->segments; i++) { - lp64 = pkd->load64 + i; - -commit c0bbd8fae4271159aee9e643350781909484c92f -Author: Dave Anderson -Date: Fri Nov 8 14:00:56 2019 -0500 - - Add support for extended numbering support in ELF dumpfiles to handle - more than PN_XNUM (0xffff) program headers. If the real number of - program header table entries is equal to or greater than PN_XNUM, the - e_phnum field of the ELF header is set to PN_XNUM, and the actual - number is set in the sh_info field of the section header at index 0. - (k-hagio@ab.jp.nec.com) - -diff --git a/netdump.c b/netdump.c -index fdaecf3..3ced87c 100644 ---- a/netdump.c -+++ b/netdump.c -@@ -28,12 +28,13 @@ static struct vmcore_data *nd = &vmcore_data; - static struct proc_kcore_data proc_kcore_data = { 0 }; - static struct proc_kcore_data *pkd = &proc_kcore_data; - static void netdump_print(char *, ...); --static size_t resize_elf_header(int, char *, char **, ulong); -+static size_t resize_elf_header(int, char *, char **, char **, ulong); - static void dump_Elf32_Ehdr(Elf32_Ehdr *); - static void dump_Elf32_Phdr(Elf32_Phdr *, int); - static size_t dump_Elf32_Nhdr(Elf32_Off offset, int); - static void dump_Elf64_Ehdr(Elf64_Ehdr *); - static void dump_Elf64_Phdr(Elf64_Phdr *, int); -+static void dump_Elf64_Shdr(Elf64_Shdr *shdr); - static size_t dump_Elf64_Nhdr(Elf64_Off offset, int); - static void get_netdump_regs_32(struct bt_info *, ulong *, ulong *); - static void get_netdump_regs_ppc(struct bt_info *, ulong *, ulong *); -@@ -116,7 +117,7 @@ is_netdump(char *file, ulong source_query) - Elf32_Phdr *load32; - Elf64_Ehdr *elf64; - Elf64_Phdr *load64; -- char *eheader; -+ char *eheader, *sect0; - char buf[BUFSIZE]; - size_t size, len, tot; - Elf32_Off offset32; -@@ -330,7 +331,8 @@ is_netdump(char *file, ulong source_query) - goto bailout; - } - -- if (!(size = resize_elf_header(fd, file, &eheader, format))) -+ sect0 = NULL; -+ if (!(size = resize_elf_header(fd, file, &eheader, §0, format))) - goto bailout; - - nd->ndfd = fd; -@@ -372,7 +374,17 @@ is_netdump(char *file, ulong source_query) - case KDUMP_ELF64: - nd->header_size = size; - nd->elf64 = (Elf64_Ehdr *)&nd->elf_header[0]; -- nd->num_pt_load_segments = nd->elf64->e_phnum - 1; -+ -+ /* -+ * Extended Numbering support -+ * See include/uapi/linux/elf.h and elf(5) for more information -+ */ -+ if (nd->elf64->e_phnum == PN_XNUM) { -+ nd->sect0_64 = (Elf64_Shdr *)sect0; -+ nd->num_pt_load_segments = nd->sect0_64->sh_info - 1; -+ } else -+ nd->num_pt_load_segments = nd->elf64->e_phnum - 1; -+ - if ((nd->pt_load_segments = (struct pt_load_segment *) - malloc(sizeof(struct pt_load_segment) * - nd->num_pt_load_segments)) == NULL) { -@@ -432,7 +444,8 @@ bailout: - */ - - static size_t --resize_elf_header(int fd, char *file, char **eheader_ptr, ulong format) -+resize_elf_header(int fd, char *file, char **eheader_ptr, char **sect0_ptr, -+ ulong format) - { - int i; - char buf[BUFSIZE]; -@@ -462,7 +475,44 @@ resize_elf_header(int fd, char *file, char **eheader_ptr, ulong format) - - case NETDUMP_ELF64: - case KDUMP_ELF64: -- num_pt_load_segments = elf64->e_phnum - 1; -+ /* -+ * Extended Numbering support -+ * See include/uapi/linux/elf.h and elf(5) for more information -+ */ -+ if (elf64->e_phnum == PN_XNUM) { -+ Elf64_Shdr *shdr64; -+ -+ shdr64 = (Elf64_Shdr *)malloc(sizeof(*shdr64)); -+ if (!shdr64) { -+ fprintf(stderr, -+ "cannot malloc a section header buffer\n"); -+ return 0; -+ } -+ if (FLAT_FORMAT()) { -+ if (!read_flattened_format(fd, elf64->e_shoff, -+ shdr64, elf64->e_shentsize)) -+ return 0; -+ } else { -+ if (lseek(fd, elf64->e_shoff, SEEK_SET) != -+ elf64->e_shoff) { -+ sprintf(buf, "%s: section header lseek", -+ file); -+ perror(buf); -+ return 0; -+ } -+ if (read(fd, shdr64, elf64->e_shentsize) != -+ elf64->e_shentsize) { -+ sprintf(buf, "%s: section header read", -+ file); -+ perror(buf); -+ return 0; -+ } -+ } -+ num_pt_load_segments = shdr64->sh_info - 1; -+ *sect0_ptr = (char *)shdr64; -+ } else -+ num_pt_load_segments = elf64->e_phnum - 1; -+ - header_size = sizeof(Elf64_Ehdr) + sizeof(Elf64_Phdr) + - (sizeof(Elf64_Phdr) * num_pt_load_segments); - break; -@@ -1168,6 +1218,7 @@ netdump_memory_dump(FILE *fp) - netdump_print(" elf64: %lx\n", nd->elf64); - netdump_print(" notes64: %lx\n", nd->notes64); - netdump_print(" load64: %lx\n", nd->load64); -+ netdump_print(" sect0_64: %lx\n", nd->sect0_64); - netdump_print(" nt_prstatus: %lx\n", nd->nt_prstatus); - netdump_print(" nt_prpsinfo: %lx\n", nd->nt_prpsinfo); - netdump_print(" nt_taskstruct: %lx\n", nd->nt_taskstruct); -@@ -1252,6 +1303,8 @@ netdump_memory_dump(FILE *fp) - dump_Elf64_Phdr(nd->notes64, ELFREAD); - for (i = 0; i < nd->num_pt_load_segments; i++) - dump_Elf64_Phdr(nd->load64 + i, ELFREAD); -+ if (nd->sect0_64) -+ dump_Elf64_Shdr(nd->sect0_64); - offset64 = nd->notes64->p_offset; - for (tot = 0; tot < nd->notes64->p_filesz; tot += len) { - if (!(len = dump_Elf64_Nhdr(offset64, ELFREAD))) -@@ -1763,6 +1816,32 @@ dump_Elf64_Phdr(Elf64_Phdr *prog, int store_pt_load_data) - netdump_print(" p_align: %lld\n", prog->p_align); - } - -+static void -+dump_Elf64_Shdr(Elf64_Shdr *shdr) -+{ -+ netdump_print("Elf64_Shdr:\n"); -+ netdump_print(" sh_name: %x\n", shdr->sh_name); -+ netdump_print(" sh_type: %x ", shdr->sh_type); -+ switch (shdr->sh_type) -+ { -+ case SHT_NULL: -+ netdump_print("(SHT_NULL)\n"); -+ break; -+ default: -+ netdump_print("\n"); -+ break; -+ } -+ netdump_print(" sh_flags: %lx\n", shdr->sh_flags); -+ netdump_print(" sh_addr: %lx\n", shdr->sh_addr); -+ netdump_print(" sh_offset: %lx\n", shdr->sh_offset); -+ netdump_print(" sh_size: %lx\n", shdr->sh_size); -+ netdump_print(" sh_link: %x\n", shdr->sh_link); -+ netdump_print(" sh_info: %x (%u)\n", shdr->sh_info, -+ shdr->sh_info); -+ netdump_print(" sh_addralign: %lx\n", shdr->sh_addralign); -+ netdump_print(" sh_entsize: %lx\n", shdr->sh_entsize); -+} -+ - /* - * VMCOREINFO - * -diff --git a/netdump.h b/netdump.h -index ad1fc77..7fa04f7 100644 ---- a/netdump.h -+++ b/netdump.h -@@ -61,6 +61,7 @@ struct vmcore_data { - Elf64_Ehdr *elf64; - Elf64_Phdr *notes64; - Elf64_Phdr *load64; -+ Elf64_Shdr *sect0_64; - void *nt_prstatus; - void *nt_prpsinfo; - void *nt_taskstruct; - -commit b5c2359f9f7347a2efa4896fa134dbf128601ca8 -Author: Dave Anderson -Date: Fri Nov 8 14:32:53 2019 -0500 - - Fix for a "warning: large integer implicitly truncated to unsigned - type [-Woverflow]" compiler message generated on 32-bit architectures - as a result of the "Additional fix for the kmem -n option" patch - above. - (anderson@redhat.com) - -diff --git a/memory.c b/memory.c -index f36685b..4f7b6a0 100644 ---- a/memory.c -+++ b/memory.c -@@ -17430,7 +17430,7 @@ static void - print_memory_block(ulong memory_block) - { - ulong start_sec, end_sec, nid; -- ulong memblock_size, mbs, start_addr, end_addr = ULLONG_MAX; -+ ulong memblock_size, mbs, start_addr, end_addr = (ulong)ULLONG_MAX; - char statebuf[BUFSIZE]; - char srangebuf[BUFSIZE]; - char parangebuf[BUFSIZE]; diff --git a/SOURCES/github_1c45cea02df7.patch b/SOURCES/github_1c45cea02df7.patch new file mode 100644 index 0000000..e513ac9 --- /dev/null +++ b/SOURCES/github_1c45cea02df7.patch @@ -0,0 +1,40 @@ +commit 1c45cea02df7f947b4296c1dcaefa1024235ef10 +Author: Bhupesh Sharma +Date: Tue Jul 14 01:14:49 2020 +0530 + + arm64: Change tcr_el1_t1sz variable name to TCR_EL1_T1SZ + + Since linux kernel commit bbdbc11804ff ("arm64/crash_core: Export + TCR_EL1.T1SZ in vmcoreinfo") [available in linux-next now], the name + of tcr_el1_t1sz vmcoreinfo variable has been changed to TCR_EL1_T1SZ. + + Make a similar change in crash-utility. + + Signed-off-by: Bhupesh Sharma + +diff --git a/arm64.c b/arm64.c +index 653225cd8cd6..fdf77bd5e0c1 100644 +--- a/arm64.c ++++ b/arm64.c +@@ -3922,7 +3922,7 @@ arm64_calc_VA_BITS(void) + } else if (ACTIVE()) + error(FATAL, "cannot determine VA_BITS_ACTUAL: please use /proc/kcore\n"); + else { +- if ((string = pc->read_vmcoreinfo("NUMBER(tcr_el1_t1sz)"))) { ++ if ((string = pc->read_vmcoreinfo("NUMBER(TCR_EL1_T1SZ)"))) { + /* See ARMv8 ARM for the description of + * TCR_EL1.T1SZ and how it can be used + * to calculate the vabits_actual +diff --git a/netdump.c b/netdump.c +index 406416af36bf..0054d6ab35b4 100644 +--- a/netdump.c ++++ b/netdump.c +@@ -1887,7 +1887,7 @@ vmcoreinfo_read_string(const char *key) + sprintf(value, "%ld", nd->arch_data2 & 0xffffffff); + return value; + } +- if (STREQ(key, "NUMBER(tcr_el1_t1sz)") && nd->arch_data2) { ++ if (STREQ(key, "NUMBER(TCR_EL1_T1SZ)") && nd->arch_data2) { + value = calloc(VADDR_PRLEN+1, sizeof(char)); + sprintf(value, "%lld", ((ulonglong)nd->arch_data2 >> 32) & 0xffffffff); + pc->read_vmcoreinfo = no_vmcoreinfo; diff --git a/SOURCES/github_5cbb2fd8_to_6c1c8ac6.patch b/SOURCES/github_5cbb2fd8_to_6c1c8ac6.patch deleted file mode 100644 index 305ccee..0000000 --- a/SOURCES/github_5cbb2fd8_to_6c1c8ac6.patch +++ /dev/null @@ -1,1485 +0,0 @@ -commit 5cbb2fd8c20c46793095522059b1efc8232df926 -Author: Dave Anderson -Date: Wed Nov 13 11:29:14 2019 -0500 - - Add support for handling openSUSE vmlinux files which will be shipped - in .xz compressed format. Without the patch, only gzip and bzip2 - formats are supported. - (jirislaby@gmail.com) - -diff --git a/symbols.c b/symbols.c -index 55199fc..7e1bca7 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -3655,6 +3655,7 @@ is_compressed_kernel(char *file, char **tmp) - - #define GZIP (1) - #define BZIP2 (2) -+#define XZ (3) - - #define FNAME (1 << 3) - -@@ -3704,6 +3705,19 @@ is_compressed_kernel(char *file, char **tmp) - type = BZIP2; - } - -+ if (!memcmp(header, "\xfd""7zXZ", 6)) { -+ if (!STRNEQ(basename(file), "vmlinux") && -+ !(st->flags & FORCE_DEBUGINFO)) { -+ error(INFO, "%s: compressed file name does not start " -+ "with \"vmlinux\"\n", file); -+ error(CONT, -+ "Use \"-f %s\" on command line to override.\n\n", -+ file); -+ return FALSE; -+ } -+ type = XZ; -+ } -+ - if (!type) - return FALSE; - -@@ -3739,6 +3753,12 @@ is_compressed_kernel(char *file, char **tmp) - "/bin/bunzip2" : "/usr/bin/bunzip2", - file, tempname); - break; -+ case XZ: -+ sprintf(command, "%s -c %s > %s", -+ file_exists("/bin/unxz", NULL) ? -+ "/bin/unxz" : "/usr/bin/unxz", -+ file, tempname); -+ break; - } - if (system(command) < 0) { - please_wait_done(); - -commit babd7ae62d4e8fd6f93fd30b88040d9376522aa3 -Author: Dave Anderson -Date: Fri Nov 15 09:55:34 2019 -0500 - - Fix for the determination of the ARM64 page size on Linux 4.4 and - earlier kernels that do not have vmcoreinfo data. Without the patch, - the crash session fails during initialization with the error message - "crash: "cannot determine page size". - (chenqiwu@xiaomi.com) - -diff --git a/arm64.c b/arm64.c -index 5ee5f1a..af7147d 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -179,17 +179,16 @@ arm64_init(int when) - - } - -+ /* -+ * This code section will only be executed if the kernel is -+ * earlier than Linux 4.4 (if there is no vmcoreinfo) -+ */ - if (!machdep->pagesize && - kernel_symbol_exists("swapper_pg_dir") && - kernel_symbol_exists("idmap_pg_dir")) { -- if (kernel_symbol_exists("tramp_pg_dir")) -- value = symbol_value("tramp_pg_dir"); -- else if (kernel_symbol_exists("reserved_ttbr0")) -- value = symbol_value("reserved_ttbr0"); -- else -- value = symbol_value("swapper_pg_dir"); -+ value = symbol_value("swapper_pg_dir") - -+ symbol_value("idmap_pg_dir"); - -- value -= symbol_value("idmap_pg_dir"); - /* - * idmap_pg_dir is 2 pages prior to 4.1, - * and 3 pages thereafter. Only 4K and 64K - -commit bfd9a651f9426d86250295ac875d7e33d8de2a97 -Author: Dave Anderson -Date: Tue Nov 19 10:19:55 2019 -0500 - - Determine the ARM64 kernel's "vabits_actual" value by reading the - new TCR_EL1.T1SZ vmcoreinfo entry. - (bhsharma@redhat.com) - -diff --git a/arm64.c b/arm64.c -index af7147d..0834913 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -3856,8 +3856,17 @@ arm64_calc_VA_BITS(void) - } else if (ACTIVE()) - error(FATAL, "cannot determine VA_BITS_ACTUAL: please use /proc/kcore\n"); - else { -- if ((string = pc->read_vmcoreinfo("NUMBER(VA_BITS_ACTUAL)"))) { -- value = atol(string); -+ if ((string = pc->read_vmcoreinfo("NUMBER(tcr_el1_t1sz)"))) { -+ /* See ARMv8 ARM for the description of -+ * TCR_EL1.T1SZ and how it can be used -+ * to calculate the vabits_actual -+ * supported by underlying kernel. -+ * -+ * Basically: -+ * vabits_actual = 64 - T1SZ; -+ */ -+ value = 64 - strtoll(string, NULL, 0); -+ fprintf(fp, "vmcoreinfo : vabits_actual: %ld\n", value); - free(string); - machdep->machspec->VA_BITS_ACTUAL = value; - machdep->machspec->VA_BITS = value; - -commit f1c71de4ef66508108c5929e79e21a85b147787b -Author: Dave Anderson -Date: Wed Nov 20 11:59:00 2019 -0500 - - Fix to determine the ARM64 kernel's "vabits_actual" value from the - ELF header of a dumpfile created with the "snap.so" extension module. - (anderson@redhat.com) - -diff --git a/netdump.c b/netdump.c -index 3ced87c..406416a 100644 ---- a/netdump.c -+++ b/netdump.c -@@ -1887,7 +1887,7 @@ vmcoreinfo_read_string(const char *key) - sprintf(value, "%ld", nd->arch_data2 & 0xffffffff); - return value; - } -- if (STREQ(key, "NUMBER(VA_BITS_ACTUAL)") && nd->arch_data2) { -+ if (STREQ(key, "NUMBER(tcr_el1_t1sz)") && nd->arch_data2) { - value = calloc(VADDR_PRLEN+1, sizeof(char)); - sprintf(value, "%lld", ((ulonglong)nd->arch_data2 >> 32) & 0xffffffff); - pc->read_vmcoreinfo = no_vmcoreinfo; - -commit b259940b228cc7025904f9b7372348b56f73a4d2 -Author: Dave Anderson -Date: Thu Nov 21 09:27:52 2019 -0500 - - Fix two typos in the examples section of the "help bt" display, which - mistakenly show "bf -f" and "bf -FF" instead of "bt -f" and "bt -FF". - (austindh.kim@gmail.com) - -diff --git a/help.c b/help.c -index 2b2285b..eed249b 100644 ---- a/help.c -+++ b/help.c -@@ -2117,7 +2117,7 @@ char *help_bt[] = { - " The following three examples show the difference in the display of", - " the same stack frame's contents using -f, -F, and -FF:", - " ", --" %s> bf -f", -+" %s> bt -f", - " ...", - " #4 [ffff810072b47f10] vfs_write at ffffffff800789d8", - " ffff810072b47f18: ffff81007e020380 ffff81007e2c2880 ", -@@ -2133,7 +2133,7 @@ char *help_bt[] = { - " ffff810072b47f38: 00002b141825d000 sys_write+69 ", - " #5 [ffff810072b47f40] sys_write at ffffffff80078f75", - " ...", --" %s> bf -FF", -+" %s> bt -FF", - " ...", - " #4 [ffff810072b47f10] vfs_write at ffffffff800789d8", - " ffff810072b47f18: [ffff81007e020380:files_cache] [ffff81007e2c2880:filp]", - -commit 5171ef5a7e85805f61ef98b15801da06648a8e39 -Author: Dave Anderson -Date: Fri Nov 22 13:39:40 2019 -0500 - - Similar to ARM64, the X86_64, PPC64 and S390x architectures will use - the exported value of MAX_PHYSMEM_BITS from the vmcoreinfo data as - the preferred method if it is available. - (anderson@redhat.com) - -diff --git a/ppc64.c b/ppc64.c -index 0936551..f368bf8 100644 ---- a/ppc64.c -+++ b/ppc64.c -@@ -225,6 +225,13 @@ static int ppc64_is_vmaddr(ulong addr) - static int set_ppc64_max_physmem_bits(void) - { - int dimension; -+ char *string; -+ -+ if ((string = pc->read_vmcoreinfo("NUMBER(MAX_PHYSMEM_BITS)"))) { -+ machdep->max_physmem_bits = atol(string); -+ free(string); -+ return 0; -+ } - - get_array_length("mem_section", &dimension, 0); - -diff --git a/s390x.c b/s390x.c -index 0055890..4a1a466 100644 ---- a/s390x.c -+++ b/s390x.c -@@ -240,6 +240,13 @@ static int - set_s390x_max_physmem_bits(void) - { - int array_len, dimension; -+ char *string; -+ -+ if ((string = pc->read_vmcoreinfo("NUMBER(MAX_PHYSMEM_BITS)"))) { -+ machdep->max_physmem_bits = atol(string); -+ free(string); -+ return TRUE; -+ } - - machdep->max_physmem_bits = _MAX_PHYSMEM_BITS_OLD; - -diff --git a/x86_64.c b/x86_64.c -index c7967bd..a4138ed 100644 ---- a/x86_64.c -+++ b/x86_64.c -@@ -665,7 +665,10 @@ x86_64_init(int when) - } - machdep->section_size_bits = _SECTION_SIZE_BITS; - if (!machdep->max_physmem_bits) { -- if (machdep->flags & VM_5LEVEL) -+ if ((string = pc->read_vmcoreinfo("NUMBER(MAX_PHYSMEM_BITS)"))) { -+ machdep->max_physmem_bits = atol(string); -+ free(string); -+ } else if (machdep->flags & VM_5LEVEL) - machdep->max_physmem_bits = - _MAX_PHYSMEM_BITS_5LEVEL; - else if (THIS_KERNEL_VERSION >= LINUX(2,6,31)) - -commit 6664cb3f4ea2eac1b6d482e541b56d7792a4be04 -Author: Dave Anderson -Date: Tue Nov 26 12:18:02 2019 -0500 - - If an S390X kernel crashes before vmcoreinfo initialization, there is - no way to extract the KASLR offset for such early dumps. In a new - S390X kernel patch, the KASLR offset will be stored in the lowcore - memory during early boot and then overwritten after vmcoreinfo is - initialized. This patch allows crash to identify the KASLR offset - that is stored in the lowcore memory. - (zaslonko@linux.ibm.com) - -diff --git a/s390x.c b/s390x.c -index 4a1a466..8840cc7 100644 ---- a/s390x.c -+++ b/s390x.c -@@ -46,6 +46,8 @@ - - #define S390X_PSW_MASK_PSTATE 0x0001000000000000UL - -+#define S390X_LC_VMCORE_INFO 0xe0c -+ - /* - * Flags for Region and Segment table entries. - */ -@@ -460,6 +462,8 @@ static void s390x_check_live(void) - void - s390x_init(int when) - { -+ ulong s390x_lc_kaslr; -+ - switch (when) - { - case SETUP_ENV: -@@ -486,6 +490,24 @@ s390x_init(int when) - machdep->verify_paddr = generic_verify_paddr; - machdep->get_kvaddr_ranges = s390x_get_kvaddr_ranges; - machdep->ptrs_per_pgd = PTRS_PER_PGD; -+ if (DUMPFILE() && !(kt->flags & RELOC_SET)) { -+ /* Read the value from well-known lowcore location*/ -+ if (readmem(S390X_LC_VMCORE_INFO, PHYSADDR, &s390x_lc_kaslr, -+ sizeof(s390x_lc_kaslr), "s390x_lc_kaslr", -+ QUIET|RETURN_ON_ERROR)) { -+ /* Check for explicit kaslr offset flag */ -+ if (s390x_lc_kaslr & 0x1UL) { -+ /* Drop the last bit to get an offset value */ -+ s390x_lc_kaslr &= ~(0x1UL); -+ /* Make sure the offset is aligned by 0x1000 */ -+ if (s390x_lc_kaslr && !(s390x_lc_kaslr & 0xfff)) { -+ kt->relocate = s390x_lc_kaslr * (-1); -+ kt->flags |= RELOC_SET; -+ kt->flags2 |= KASLR; -+ } -+ } -+ } -+ } - break; - - case PRE_GDB: - -commit b265bad21cdb394b230431360605551b02fc5053 -Author: Dave Anderson -Date: Sun Dec 1 14:06:59 2019 -0500 - - Fix for a crash-7.2.7 regression that determined the value of the - ARM64 kernel SECTION_SIZE_BITS by reading the in-kernel configuration - data if there is no VMCOREINFO data available. In that case, without - the patch, a double-free exception may occur. - (anderson@redhat.com) - -diff --git a/arm64.c b/arm64.c -index 0834913..233029d 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -1073,10 +1073,8 @@ arm64_get_section_size_bits(void) - free(string); - } else if (kt->ikconfig_flags & IKCONFIG_AVAIL) { - if ((ret = get_kernel_config("CONFIG_MEMORY_HOTPLUG", NULL)) == IKCONFIG_Y) { -- if ((ret = get_kernel_config("CONFIG_HOTPLUG_SIZE_BITS", &string)) == IKCONFIG_STR) { -+ if ((ret = get_kernel_config("CONFIG_HOTPLUG_SIZE_BITS", &string)) == IKCONFIG_STR) - machdep->section_size_bits = atol(string); -- free(string); -- } - } - } - - -commit e13b51a59645fd8c3884082b157a0b494cf77ec6 -Author: Dave Anderson -Date: Sun Dec 1 14:18:41 2019 -0500 - - Fix for segmentation violation if the gdb_readmem_callback() function - gets called from other than a crash command, such as from an epython - command from the mypkdump.so extension module. - (anderson@redhat.com) - -diff --git a/gdb_interface.c b/gdb_interface.c -index 608da86..562d2ac 100644 ---- a/gdb_interface.c -+++ b/gdb_interface.c -@@ -1,8 +1,8 @@ - /* gdb_interface.c - core analysis suite - * - * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. -- * Copyright (C) 2002-2015,2018 David Anderson -- * Copyright (C) 2002-2015,2018 Red Hat, Inc. All rights reserved. -+ * Copyright (C) 2002-2015,2018-2019 David Anderson -+ * Copyright (C) 2002-2015,2018-2019 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by -@@ -831,6 +831,11 @@ gdb_readmem_callback(ulong addr, void *buf, int len, int write) - if (write) - return FALSE; - -+ if (!(pc->cur_req)) { -+ return(readmem(addr, KVADDR, buf, len, -+ "gdb_readmem_callback", RETURN_ON_ERROR)); -+ } -+ - if (pc->cur_req->flags & GNU_NO_READMEM) - return TRUE; - - -commit da4a22029aa55fa55200d52f98866fce48ba720e -Author: Dave Anderson -Date: Tue Dec 3 11:41:19 2019 -0500 - - Fix for the "dis -s" option when running against kernels that have - been configured with CONFIG_RANDOMIZE_BASE=y (KASLR). Without the - patch, the command option indicates that the FILE and LINE numbers - are "(unknown)", and that "source code is not available". - (anderson@redhat.com) - -diff --git a/kernel.c b/kernel.c -index c4cb001..80486ba 100644 ---- a/kernel.c -+++ b/kernel.c -@@ -1459,12 +1459,20 @@ list_source_code(struct gnu_request *req, int count_entered) - char *argv[MAXARGS]; - struct syment *sp; - ulong remaining, offset; -+ struct load_module *lm; - char *p1; - - sp = value_search(req->addr, &offset); - if (!sp || !is_symbol_text(sp)) - error(FATAL, "%lx: not a kernel text address\n", req->addr); - -+ if (module_symbol(req->addr, NULL, &lm, NULL, 0)) { -+ if (!(lm->mod_flags & MOD_LOAD_SYMS)) -+ error(FATAL, "%s: module source code is not available\n", lm->mod_name); -+ get_line_number(req->addr, buf1, FALSE); -+ } else if (kt->flags2 & KASLR) -+ req->addr -= (kt->relocate * -1); -+ - sprintf(buf1, "list *0x%lx", req->addr); - open_tmpfile(); - if (!gdb_pass_through(buf1, pc->tmpfile, GNU_RETURN_ON_ERROR)) { - -commit 4e4e5859731da650d3520150d7ea2ef07094c7af -Author: Dave Anderson -Date: Thu Dec 12 12:08:11 2019 -0500 - - Fix for newer Xen hypervisors, which fail during initialization with - the error message "crash: cannot resolve init_tss". This is caused - by a change in the Xen hypervisor with commit 78884406256, from - 4.12.0-rc5-763-g7888440625. In that patch the tss_struct structure - was renamed to tss64 and the tss_page structure was introduced, - which contains a single tss64. Now tss information is accessible - via the symbol "per_cpu__tss_page". - (dietmar.hahn@ts.fujitsu.com) - -diff --git a/x86.c b/x86.c -index 88562b6..de0d3d3 100644 ---- a/x86.c -+++ b/x86.c -@@ -5600,18 +5600,18 @@ x86_get_stackbase_hyper(ulong task) - - if (symbol_exists("init_tss")) { - init_tss = symbol_value("init_tss"); -- init_tss += XEN_HYPER_SIZE(tss_struct) * pcpu; -+ init_tss += XEN_HYPER_SIZE(tss) * pcpu; - } else { - init_tss = symbol_value("per_cpu__init_tss"); - init_tss = xen_hyper_per_cpu(init_tss, pcpu); - } - -- buf = GETBUF(XEN_HYPER_SIZE(tss_struct)); -+ buf = GETBUF(XEN_HYPER_SIZE(tss)); - if (!readmem(init_tss, KVADDR, buf, -- XEN_HYPER_SIZE(tss_struct), "init_tss", RETURN_ON_ERROR)) { -+ XEN_HYPER_SIZE(tss), "init_tss", RETURN_ON_ERROR)) { - error(FATAL, "cannot read init_tss.\n"); - } -- esp = ULONG(buf + XEN_HYPER_OFFSET(tss_struct_esp0)); -+ esp = ULONG(buf + XEN_HYPER_OFFSET(tss_esp0)); - FREEBUF(buf); - base = esp & (~(STACKSIZE() - 1)); - -@@ -5745,8 +5745,8 @@ x86_init_hyper(int when) - #endif - XEN_HYPER_STRUCT_SIZE_INIT(cpu_time, "cpu_time"); - XEN_HYPER_STRUCT_SIZE_INIT(cpuinfo_x86, "cpuinfo_x86"); -- XEN_HYPER_STRUCT_SIZE_INIT(tss_struct, "tss_struct"); -- XEN_HYPER_MEMBER_OFFSET_INIT(tss_struct_esp0, "tss_struct", "esp0"); -+ XEN_HYPER_STRUCT_SIZE_INIT(tss, "tss_struct"); -+ XEN_HYPER_MEMBER_OFFSET_INIT(tss_esp0, "tss_struct", "esp0"); - XEN_HYPER_MEMBER_OFFSET_INIT(cpu_time_local_tsc_stamp, "cpu_time", "local_tsc_stamp"); - XEN_HYPER_MEMBER_OFFSET_INIT(cpu_time_stime_local_stamp, "cpu_time", "stime_local_stamp"); - XEN_HYPER_MEMBER_OFFSET_INIT(cpu_time_stime_master_stamp, "cpu_time", "stime_master_stamp"); -diff --git a/x86_64.c b/x86_64.c -index a4138ed..4f1a6d7 100644 ---- a/x86_64.c -+++ b/x86_64.c -@@ -7973,13 +7973,23 @@ x86_64_init_hyper(int when) - - case POST_GDB: - XEN_HYPER_STRUCT_SIZE_INIT(cpuinfo_x86, "cpuinfo_x86"); -- XEN_HYPER_STRUCT_SIZE_INIT(tss_struct, "tss_struct"); -- if (MEMBER_EXISTS("tss_struct", "__blh")) { -- XEN_HYPER_ASSIGN_OFFSET(tss_struct_rsp0) = MEMBER_OFFSET("tss_struct", "__blh") + sizeof(short unsigned int); -+ if (symbol_exists("per_cpu__tss_page")) { -+ XEN_HYPER_STRUCT_SIZE_INIT(tss, "tss64"); -+ XEN_HYPER_ASSIGN_OFFSET(tss_rsp0) = -+ MEMBER_OFFSET("tss64", "rsp0"); -+ XEN_HYPER_MEMBER_OFFSET_INIT(tss_ist, "tss64", "ist"); - } else { -- XEN_HYPER_ASSIGN_OFFSET(tss_struct_rsp0) = MEMBER_OFFSET("tss_struct", "rsp0"); -+ XEN_HYPER_STRUCT_SIZE_INIT(tss, "tss_struct"); -+ XEN_HYPER_MEMBER_OFFSET_INIT(tss_ist, "tss_struct", "ist"); -+ if (MEMBER_EXISTS("tss_struct", "__blh")) { -+ XEN_HYPER_ASSIGN_OFFSET(tss_rsp0) = -+ MEMBER_OFFSET("tss_struct", "__blh") + -+ sizeof(short unsigned int); -+ } else { -+ XEN_HYPER_ASSIGN_OFFSET(tss_rsp0) = -+ MEMBER_OFFSET("tss_struct", "rsp0"); -+ } - } -- XEN_HYPER_MEMBER_OFFSET_INIT(tss_struct_ist, "tss_struct", "ist"); - if (symbol_exists("cpu_data")) { - xht->cpu_data_address = symbol_value("cpu_data"); - } -diff --git a/xen_hyper.c b/xen_hyper.c -index f2f00e6..1030c0a 100644 ---- a/xen_hyper.c -+++ b/xen_hyper.c -@@ -338,33 +338,35 @@ xen_hyper_x86_pcpu_init(void) - if((xhpct->pcpu_struct = malloc(XEN_HYPER_SIZE(cpu_info))) == NULL) { - error(FATAL, "cannot malloc pcpu struct space.\n"); - } -- - /* get physical cpu context */ - xen_hyper_alloc_pcpu_context_space(XEN_HYPER_MAX_CPUS()); - if (symbol_exists("per_cpu__init_tss")) { - init_tss_base = symbol_value("per_cpu__init_tss"); - flag = TRUE; -+ } else if (symbol_exists("per_cpu__tss_page")) { -+ init_tss_base = symbol_value("per_cpu__tss_page"); -+ flag = TRUE; - } else { - init_tss_base = symbol_value("init_tss"); - flag = FALSE; - } -- buf = GETBUF(XEN_HYPER_SIZE(tss_struct)); -+ buf = GETBUF(XEN_HYPER_SIZE(tss)); - for_cpu_indexes(i, cpuid) - { - if (flag) - init_tss = xen_hyper_per_cpu(init_tss_base, cpuid); - else - init_tss = init_tss_base + -- XEN_HYPER_SIZE(tss_struct) * cpuid; -+ XEN_HYPER_SIZE(tss) * cpuid; - if (!readmem(init_tss, KVADDR, buf, -- XEN_HYPER_SIZE(tss_struct), "init_tss", RETURN_ON_ERROR)) { -+ XEN_HYPER_SIZE(tss), "init_tss", RETURN_ON_ERROR)) { - error(FATAL, "cannot read init_tss.\n"); - } - if (machine_type("X86")) { -- sp = ULONG(buf + XEN_HYPER_OFFSET(tss_struct_esp0)); -+ sp = ULONG(buf + XEN_HYPER_OFFSET(tss_esp0)); - } else if (machine_type("X86_64")) { -- sp = ULONG(buf + XEN_HYPER_OFFSET(tss_struct_rsp0)); -- } else -+ sp = ULONG(buf + XEN_HYPER_OFFSET(tss_rsp0)); -+ } else - sp = 0; - cpu_info = XEN_HYPER_GET_CPU_INFO(sp); - if (CRASHDEBUG(1)) { -@@ -1777,10 +1779,10 @@ xen_hyper_store_pcpu_context_tss(struct xen_hyper_pcpu_context *pcc, - - pcc->init_tss = init_tss; - if (machine_type("X86")) { -- pcc->sp.esp0 = ULONG(tss + XEN_HYPER_OFFSET(tss_struct_esp0)); -+ pcc->sp.esp0 = ULONG(tss + XEN_HYPER_OFFSET(tss_esp0)); - } else if (machine_type("X86_64")) { -- pcc->sp.rsp0 = ULONG(tss + XEN_HYPER_OFFSET(tss_struct_rsp0)); -- ist_p = (uint64_t *)(tss + XEN_HYPER_OFFSET(tss_struct_ist)); -+ pcc->sp.rsp0 = ULONG(tss + XEN_HYPER_OFFSET(tss_rsp0)); -+ ist_p = (uint64_t *)(tss + XEN_HYPER_OFFSET(tss_ist)); - for (i = 0; i < XEN_HYPER_TSS_IST_MAX; i++, ist_p++) { - pcc->ist[i] = ULONG(ist_p); - } -diff --git a/xen_hyper_defs.h b/xen_hyper_defs.h -index b871bdd..acf910a 100644 ---- a/xen_hyper_defs.h -+++ b/xen_hyper_defs.h -@@ -598,7 +598,7 @@ struct xen_hyper_size_table { - long scheduler; - long shared_info; - long timer; -- long tss_struct; -+ long tss; - long vcpu; - long vcpu_runstate_info; - long xen_crash_xen_regs_t; /* elf note v2 */ -@@ -727,9 +727,9 @@ struct xen_hyper_offset_table { - long timer_heap_offset; - long timer_killed; - /* tss */ -- long tss_struct_rsp0; -- long tss_struct_esp0; -- long tss_struct_ist; -+ long tss_rsp0; -+ long tss_esp0; -+ long tss_ist; - /* vcpu */ - long vcpu_vcpu_id; - long vcpu_processor; -diff --git a/xen_hyper_dump_tables.c b/xen_hyper_dump_tables.c -index eb646b6..0360d25 100644 ---- a/xen_hyper_dump_tables.c -+++ b/xen_hyper_dump_tables.c -@@ -636,8 +636,8 @@ xen_hyper_dump_xen_hyper_size_table(char *spec, ulong makestruct) - (buf, "%ld\n", xen_hyper_size_table.shared_info)); - XEN_HYPER_PRI(fp, len, "timer: ", buf, flag, - (buf, "%ld\n", xen_hyper_size_table.timer)); -- XEN_HYPER_PRI(fp, len, "tss_struct: ", buf, flag, -- (buf, "%ld\n", xen_hyper_size_table.tss_struct)); -+ XEN_HYPER_PRI(fp, len, "tss: ", buf, flag, -+ (buf, "%ld\n", xen_hyper_size_table.tss)); - XEN_HYPER_PRI(fp, len, "vcpu: ", buf, flag, - (buf, "%ld\n", xen_hyper_size_table.vcpu)); - XEN_HYPER_PRI(fp, len, "vcpu_runstate_info: ", buf, flag, -@@ -868,9 +868,9 @@ xen_hyper_dump_xen_hyper_offset_table(char *spec, ulong makestruct) - (buf, "%ld\n", xen_hyper_offset_table.timer_killed)); - - XEN_HYPER_PRI(fp, len, "tss_struct_rsp0: ", buf, flag, -- (buf, "%ld\n", xen_hyper_offset_table.tss_struct_rsp0)); -+ (buf, "%ld\n", xen_hyper_offset_table.tss_rsp0)); - XEN_HYPER_PRI(fp, len, "tss_struct_esp0: ", buf, flag, -- (buf, "%ld\n", xen_hyper_offset_table.tss_struct_esp0)); -+ (buf, "%ld\n", xen_hyper_offset_table.tss_esp0)); - - XEN_HYPER_PRI(fp, len, "vcpu_vcpu_id: ", buf, flag, - (buf, "%ld\n", xen_hyper_offset_table.vcpu_vcpu_id)); - -commit c408862daff0b07f0d98a1c309febcf6590ccf0c -Author: Dave Anderson -Date: Sun Dec 15 12:24:13 2019 -0500 - - When accessing the ARM64 kernel's "crash_notes" array, continue to - read the per-cpu NT_PRSTATUS note contents if an invalid note is - encountered. Without the patch, if an invalid note is found, all - other notes were ignored, and subsequent "bt" attempts on the active - tasks would fail. - (chenqiwu@xiaomi.com, anderson@redhat.com) - -diff --git a/arm64.c b/arm64.c -index 233029d..1b024a4 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -81,7 +81,7 @@ static int arm64_on_irq_stack(int, ulong); - static void arm64_set_irq_stack(struct bt_info *); - static void arm64_set_process_stack(struct bt_info *); - static int arm64_get_kvaddr_ranges(struct vaddr_range *); --static int arm64_get_crash_notes(void); -+static void arm64_get_crash_notes(void); - static void arm64_calc_VA_BITS(void); - static int arm64_is_uvaddr(ulong, struct task_context *); - -@@ -465,11 +465,8 @@ arm64_init(int when) - * of the crash. We need this information to extract correct - * backtraces from the panic task. - */ -- if (!LIVE() && !arm64_get_crash_notes()) -- error(WARNING, -- "cannot retrieve registers for active task%s\n\n", -- kt->cpus > 1 ? "s" : ""); -- -+ if (!LIVE()) -+ arm64_get_crash_notes(); - break; - - case LOG_ONLY: -@@ -3578,7 +3575,7 @@ arm64_get_smp_cpus(void) - /* - * Retrieve task registers for the time of the crash. - */ --static int -+static void - arm64_get_crash_notes(void) - { - struct machine_specific *ms = machdep->machspec; -@@ -3587,10 +3584,10 @@ arm64_get_crash_notes(void) - ulong offset; - char *buf, *p; - ulong *notes_ptrs; -- ulong i; -+ ulong i, found; - - if (!symbol_exists("crash_notes")) -- return FALSE; -+ return; - - crash_notes = symbol_value("crash_notes"); - -@@ -3602,9 +3599,9 @@ arm64_get_crash_notes(void) - */ - if (!readmem(crash_notes, KVADDR, ¬es_ptrs[kt->cpus-1], - sizeof(notes_ptrs[kt->cpus-1]), "crash_notes", RETURN_ON_ERROR)) { -- error(WARNING, "cannot read crash_notes\n"); -+ error(WARNING, "cannot read \"crash_notes\"\n"); - FREEBUF(notes_ptrs); -- return FALSE; -+ return; - } - - if (symbol_exists("__per_cpu_offset")) { -@@ -3620,12 +3617,11 @@ arm64_get_crash_notes(void) - if (!(ms->panic_task_regs = calloc((size_t)kt->cpus, sizeof(struct arm64_pt_regs)))) - error(FATAL, "cannot calloc panic_task_regs space\n"); - -- for (i = 0; i < kt->cpus; i++) { -- -+ for (i = found = 0; i < kt->cpus; i++) { - if (!readmem(notes_ptrs[i], KVADDR, buf, SIZE(note_buf), - "note_buf_t", RETURN_ON_ERROR)) { -- error(WARNING, "failed to read note_buf_t\n"); -- goto fail; -+ error(WARNING, "cpu %d: cannot read NT_PRSTATUS note\n", i); -+ continue; - } - - /* -@@ -3655,19 +3651,24 @@ arm64_get_crash_notes(void) - note->n_descsz == notesz) - BCOPY((char *)note, buf, notesz); - } else { -- error(WARNING, -- "cannot find NT_PRSTATUS note for cpu: %d\n", i); -+ error(WARNING, "cpu %d: cannot find NT_PRSTATUS note\n", i); - continue; - } - } - -+ /* -+ * Check the sanity of NT_PRSTATUS note only for each online cpu. -+ * If this cpu has invalid note, continue to find the crash notes -+ * for other online cpus. -+ */ - if (note->n_type != NT_PRSTATUS) { -- error(WARNING, "invalid note (n_type != NT_PRSTATUS)\n"); -- goto fail; -+ error(WARNING, "cpu %d: invalid NT_PRSTATUS note (n_type != NT_PRSTATUS)\n", i); -+ continue; - } -- if (p[0] != 'C' || p[1] != 'O' || p[2] != 'R' || p[3] != 'E') { -- error(WARNING, "invalid note (name != \"CORE\"\n"); -- goto fail; -+ -+ if (!STRNEQ(p, "CORE")) { -+ error(WARNING, "cpu %d: invalid NT_PRSTATUS note (name != \"CORE\")\n", i); -+ continue; - } - - /* -@@ -3680,18 +3681,17 @@ arm64_get_crash_notes(void) - - BCOPY(p + OFFSET(elf_prstatus_pr_reg), &ms->panic_task_regs[i], - sizeof(struct arm64_pt_regs)); -+ -+ found++; - } - - FREEBUF(buf); - FREEBUF(notes_ptrs); -- return TRUE; - --fail: -- FREEBUF(buf); -- FREEBUF(notes_ptrs); -- free(ms->panic_task_regs); -- ms->panic_task_regs = NULL; -- return FALSE; -+ if (!found) { -+ free(ms->panic_task_regs); -+ ms->panic_task_regs = NULL; -+ } - } - - static void - -commit 63df9c067de0b2017f50f5d236954890bbb42fe3 -Author: Dave Anderson -Date: Mon Dec 16 11:28:46 2019 -0500 - - When accessing the 32-bit ARM kernel's "crash_notes" array, continue - to read the per-cpu NT_PRSTATUS note contents if an invalid note is - encountered. Without the patch, if an invalid note is found, all - other notes were ignored, and subsequent "bt" attempts on the active - tasks would fail. - (chenqiwu@xiaomi.com, anderson@redhat.com) - -diff --git a/arm.c b/arm.c -index b05b0b3..e52d29f 100644 ---- a/arm.c -+++ b/arm.c -@@ -26,7 +26,7 @@ - #include "defs.h" - - static void arm_parse_cmdline_args(void); --static int arm_get_crash_notes(void); -+static void arm_get_crash_notes(void); - static int arm_verify_symbol(const char *, ulong, char); - static int arm_is_module_addr(ulong); - static int arm_is_kvaddr(ulong); -@@ -348,10 +348,8 @@ arm_init(int when) - * of the crash. We need this information to extract correct - * backtraces from the panic task. - */ -- if (!ACTIVE() && !arm_get_crash_notes()) -- error(WARNING, -- "cannot retrieve registers for active task%s\n\n", -- kt->cpus > 1 ? "s" : ""); -+ if (!ACTIVE()) -+ arm_get_crash_notes(); - - if (init_unwind_tables()) { - if (CRASHDEBUG(1)) -@@ -543,7 +541,7 @@ arm_parse_cmdline_args(void) - /* - * Retrieve task registers for the time of the crash. - */ --static int -+static void - arm_get_crash_notes(void) - { - struct machine_specific *ms = machdep->machspec; -@@ -552,10 +550,10 @@ arm_get_crash_notes(void) - ulong offset; - char *buf, *p; - ulong *notes_ptrs; -- ulong i; -+ ulong i, found; - - if (!symbol_exists("crash_notes")) -- return FALSE; -+ return; - - crash_notes = symbol_value("crash_notes"); - -@@ -570,11 +568,10 @@ arm_get_crash_notes(void) - RETURN_ON_ERROR)) { - error(WARNING, "cannot read crash_notes\n"); - FREEBUF(notes_ptrs); -- return FALSE; -+ return; - } - - if (symbol_exists("__per_cpu_offset")) { -- - /* Add __per_cpu_offset for each cpu to form the pointer to the notes */ - for (i = 0; icpus; i++) - notes_ptrs[i] = notes_ptrs[kt->cpus-1] + kt->__per_cpu_offset[i]; -@@ -585,12 +582,11 @@ arm_get_crash_notes(void) - if (!(panic_task_regs = calloc((size_t)kt->cpus, sizeof(*panic_task_regs)))) - error(FATAL, "cannot calloc panic_task_regs space\n"); - -- for (i=0;icpus;i++) { -- -+ for (i = found = 0; icpus; i++) { - if (!readmem(notes_ptrs[i], KVADDR, buf, SIZE(note_buf), "note_buf_t", - RETURN_ON_ERROR)) { -- error(WARNING, "failed to read note_buf_t\n"); -- goto fail; -+ error(WARNING, "cpu %d: cannot read NT_PRSTATUS note\n", i); -+ continue; - } - - /* -@@ -620,19 +616,23 @@ arm_get_crash_notes(void) - note->n_descsz == notesz) - BCOPY((char *)note, buf, notesz); - } else { -- error(WARNING, -- "cannot find NT_PRSTATUS note for cpu: %d\n", i); -+ error(WARNING, "cpu %d: cannot find NT_PRSTATUS note\n", i); - continue; - } - } -- -+ /* -+ * Check the sanity of NT_PRSTATUS note only for each online cpu. -+ * If this cpu has invalid note, continue to find the crash notes -+ * for other online cpus. -+ */ - if (note->n_type != NT_PRSTATUS) { -- error(WARNING, "invalid note (n_type != NT_PRSTATUS)\n"); -- goto fail; -+ error(WARNING, "cpu %d: invalid NT_PRSTATUS note (n_type != NT_PRSTATUS)\n", i); -+ continue; - } -- if (p[0] != 'C' || p[1] != 'O' || p[2] != 'R' || p[3] != 'E') { -- error(WARNING, "invalid note (name != \"CORE\"\n"); -- goto fail; -+ -+ if (!STRNEQ(p, "CORE")) { -+ error(WARNING, "cpu %d: invalid NT_PRSTATUS note (name != \"CORE\")\n", i); -+ continue; - } - - /* -@@ -646,6 +646,7 @@ arm_get_crash_notes(void) - BCOPY(p + OFFSET(elf_prstatus_pr_reg), &panic_task_regs[i], - sizeof(panic_task_regs[i])); - -+ found++; - } - - /* -@@ -656,13 +657,10 @@ arm_get_crash_notes(void) - - FREEBUF(buf); - FREEBUF(notes_ptrs); -- return TRUE; -- --fail: -- FREEBUF(buf); -- FREEBUF(notes_ptrs); -- free(panic_task_regs); -- return FALSE; -+ if (!found) { -+ free(panic_task_regs); -+ ms->crash_task_regs = NULL; -+ } - } - - /* - -commit af7f78dc501b8acf7fee3f924f69e93513d0a74b -Author: Dave Anderson -Date: Fri Dec 20 14:33:11 2019 -0500 - - Fix for the "log -a" option. The kernel's sk_buff.len field is a - 32-bit unsigned int, but crash was reading its 32-bit value into a - 64-bit unsigned long stack variable. All extra bits that pre-existed - in the upper 32-bits of the stack variable were passed along as part - of a buffer size request; if the upper 32-bit bits were non-zero, - then the command would fail with a dump of the internal buffer - allocation stats followed by the message "log: cannot allocate any - more memory!". - (anderson@redhat.com) - -diff --git a/kernel.c b/kernel.c -index 80486ba..68ee282 100644 ---- a/kernel.c -+++ b/kernel.c -@@ -11284,7 +11284,8 @@ dump_audit_skb_queue(ulong audit_skb_queue) - - p = skb_buff_head_next; - do { -- ulong data, len, data_len; -+ ulong data, data_len; -+ uint len; - uint16_t nlmsg_type; - char *buf = NULL; - -@@ -11295,7 +11296,7 @@ dump_audit_skb_queue(ulong audit_skb_queue) - KVADDR, - &len, - SIZE(sk_buff_len), -- "sk_buff.data", -+ "sk_buff.len", - FAULT_ON_ERROR); - - data_len = len - roundup(SIZE(nlmsghdr), NLMSG_ALIGNTO); - -commit 5e975dd8c817ea6aea35e1e15b83c378aee9c136 -Author: Dave Anderson -Date: Tue Dec 24 08:43:52 2019 -0500 - - When determining the ARM64 kernel's "vabits_actual" value by reading - the new TCR_EL1.T1SZ vmcoreinfo entry, display its value during - session initialization only when invoking crash with "-d1" or larger - -d debug value. - (anderson@redhat.com) - -diff --git a/arm64.c b/arm64.c -index 1b024a4..6c2c58f 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -3864,7 +3864,8 @@ arm64_calc_VA_BITS(void) - * vabits_actual = 64 - T1SZ; - */ - value = 64 - strtoll(string, NULL, 0); -- fprintf(fp, "vmcoreinfo : vabits_actual: %ld\n", value); -+ if (CRASHDEBUG(1)) -+ fprintf(fp, "vmcoreinfo : vabits_actual: %ld\n", value); - free(string); - machdep->machspec->VA_BITS_ACTUAL = value; - machdep->machspec->VA_BITS = value; - -commit 0ab7ac3bea5deaa3da894247ffab9ef2433c1b9b -Author: Dave Anderson -Date: Tue Jan 7 09:34:38 2020 -0500 - - Update copyright to 2020 in crash version output. - -diff --git a/help.c b/help.c -index eed249b..a481850 100644 ---- a/help.c -+++ b/help.c -@@ -1,8 +1,8 @@ - /* help.c - core analysis suite - * - * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. -- * Copyright (C) 2002-2019 David Anderson -- * Copyright (C) 2002-2019 Red Hat, Inc. All rights reserved. -+ * Copyright (C) 2002-2020 David Anderson -+ * Copyright (C) 2002-2020 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by -@@ -8269,7 +8269,7 @@ display_version(void) - static - char *version_info[] = { - --"Copyright (C) 2002-2019 Red Hat, Inc.", -+"Copyright (C) 2002-2020 Red Hat, Inc.", - "Copyright (C) 2004, 2005, 2006, 2010 IBM Corporation", - "Copyright (C) 1999-2006 Hewlett-Packard Co", - "Copyright (C) 2005, 2006, 2011, 2012 Fujitsu Limited", - -commit 08b01834641b0a387c86adf651c660df0fe37ae1 -Author: Dave Anderson -Date: Tue Jan 7 11:07:12 2020 -0500 - - Fix for ARM64 when running against Linux 5.5-rc1 and later kernels - that contain commit b6e43c0e3129ffe87e65c85f20fcbdf0eb86fba0, titled - "arm64: remove __exception annotations". Without the patch, the - ARM64 crash session fails during initialization with the error - message "crash: cannot resolve __exception_text_start". - (anderson@redhat.com) - -diff --git a/arm64.c b/arm64.c -index 6c2c58f..7662d71 100644 ---- a/arm64.c -+++ b/arm64.c -@@ -1,8 +1,8 @@ - /* - * arm64.c - core analysis suite - * -- * Copyright (C) 2012-2019 David Anderson -- * Copyright (C) 2012-2019 Red Hat, Inc. All rights reserved. -+ * Copyright (C) 2012-2020 David Anderson -+ * Copyright (C) 2012-2020 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by -@@ -1644,10 +1644,11 @@ arm64_stackframe_init(void) - machdep->machspec->kern_eframe_offset = SIZE(pt_regs); - } - -- machdep->machspec->__exception_text_start = -- symbol_value("__exception_text_start"); -- machdep->machspec->__exception_text_end = -- symbol_value("__exception_text_end"); -+ if ((sp1 = kernel_symbol_search("__exception_text_start")) && -+ (sp2 = kernel_symbol_search("__exception_text_end"))) { -+ machdep->machspec->__exception_text_start = sp1->value; -+ machdep->machspec->__exception_text_end = sp2->value; -+ } - if ((sp1 = kernel_symbol_search("__irqentry_text_start")) && - (sp2 = kernel_symbol_search("__irqentry_text_end"))) { - machdep->machspec->__irqentry_text_start = sp1->value; -@@ -1856,20 +1857,38 @@ arm64_eframe_search(struct bt_info *bt) - return count; - } - -+static char *arm64_exception_functions[] = { -+ "do_undefinstr", -+ "do_sysinstr", -+ "do_debug_exception", -+ "do_mem_abort", -+ "do_el0_irq_bp_hardening", -+ "do_sp_pc_abort", -+ NULL -+}; -+ - static int - arm64_in_exception_text(ulong ptr) - { - struct machine_specific *ms = machdep->machspec; -- -- if ((ptr >= ms->__exception_text_start) && -- (ptr < ms->__exception_text_end)) -- return TRUE; -+ char *name, **func; - - if (ms->__irqentry_text_start && ms->__irqentry_text_end && - ((ptr >= ms->__irqentry_text_start) && - (ptr < ms->__irqentry_text_end))) - return TRUE; - -+ if (ms->__exception_text_start && ms->__exception_text_end) { -+ if ((ptr >= ms->__exception_text_start) && -+ (ptr < ms->__exception_text_end)) -+ return TRUE; -+ } else if ((name = closest_symbol(ptr))) { /* Linux 5.5 and later */ -+ for (func = &arm64_exception_functions[0]; *func; func++) { -+ if (STREQ(name, *func)) -+ return TRUE; -+ } -+ } -+ - return FALSE; - } - - -commit 7c2d41e1b25e9fec50d525361bcfa29bdaa410b2 -Author: Dave Anderson -Date: Wed Jan 8 14:28:39 2020 -0500 - - Fix for support of ELF format kdump vmcores from S390X KASLR kernels. - Without the patch, the crash session fails during initialization with - the error message "crash: vmlinux and vmcore do not match!". - (anderson@redhat.com) - -diff --git a/symbols.c b/symbols.c -index 7e1bca7..82ac549 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -1,8 +1,8 @@ - /* symbols.c - core analysis suite - * - * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. -- * Copyright (C) 2002-2019 David Anderson -- * Copyright (C) 2002-2019 Red Hat, Inc. All rights reserved. -+ * Copyright (C) 2002-2020 David Anderson -+ * Copyright (C) 2002-2020 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by -@@ -597,6 +597,11 @@ kaslr_init(void) - !machine_type("S390X")) || (kt->flags & RELOC_SET)) - return; - -+ if ((string = pc->read_vmcoreinfo("SYMBOL(_stext)"))) { -+ kt->vmcoreinfo._stext_SYMBOL = htol(string, RETURN_ON_ERROR, NULL); -+ free(string); -+ } -+ - /* - * --kaslr=auto - */ -@@ -609,8 +614,7 @@ kaslr_init(void) - st->_stext_vmlinux = UNINITIALIZED; - } - -- if (machine_type("S390X") && /* Linux 5.2 */ -- (symbol_value_from_proc_kallsyms("__kaslr_offset") != BADVAL)) { -+ if (machine_type("S390X")) { - kt->flags2 |= (RELOC_AUTO|KASLR); - st->_stext_vmlinux = UNINITIALIZED; - } -@@ -622,12 +626,6 @@ kaslr_init(void) - kt->flags2 |= KASLR_CHECK; - } - } else if (KDUMP_DUMPFILE() || DISKDUMP_DUMPFILE()) { -- if ((string = pc->read_vmcoreinfo("SYMBOL(_stext)"))) { -- kt->vmcoreinfo._stext_SYMBOL = -- htol(string, RETURN_ON_ERROR, NULL); -- free(string); -- } -- - /* Linux 3.14 */ - if ((string = pc->read_vmcoreinfo("KERNELOFFSET"))) { - free(string); - -commit 6e033fe099f8faea8fe284b9f7c08da7bc3af7a7 -Author: Dave Anderson -Date: Thu Jan 16 11:46:10 2020 -0500 - - Fix for support of S390X standalone dumpfiles and LKCD dumpfiles that - were taken from S390X KASLR kernels. - (zaslonko@linux.ibm.com) - -diff --git a/defs.h b/defs.h -index efa40b9..88a47d6 100644 ---- a/defs.h -+++ b/defs.h -@@ -6267,6 +6267,8 @@ void get_s390_panicmsg(char *); - /* - * s390x.c - */ -+ulong get_stext_relocated_s390x(void); -+ - #ifdef S390X - void s390x_init(int); - void s390x_dump_machdep_table(ulong); -diff --git a/s390x.c b/s390x.c -index 8840cc7..e030f93 100644 ---- a/s390x.c -+++ b/s390x.c -@@ -455,6 +455,78 @@ static void s390x_check_live(void) - pc->flags2 |= LIVE_DUMP; - } - -+static char * -+vmcoreinfo_read_string_s390x(const char *vmcoreinfo, const char *key) -+{ -+ char *value_string = NULL; -+ size_t value_length; -+ char keybuf[128]; -+ char *p1, *p2; -+ -+ sprintf(keybuf, "%s=", key); -+ -+ if ((p1 = strstr(vmcoreinfo, keybuf))) { -+ p2 = p1 + strlen(keybuf); -+ p1 = strstr(p2, "\n"); -+ value_length = p1-p2; -+ value_string = calloc(value_length + 1, sizeof(char)); -+ strncpy(value_string, p2, value_length); -+ value_string[value_length] = NULLCHAR; -+ } -+ -+ return value_string; -+} -+ -+/* -+ * Read _stext symbol from vmcoreinfo when lowcore vmcoreinfo pointer is present -+ * in the dump (can be relevant for s390 and lkcd dump formats). -+ */ -+ulong get_stext_relocated_s390x(void) -+{ -+ char *_stext_string, *vmcoreinfo; -+ Elf64_Nhdr note; -+ char str[128]; -+ ulong val = 0; -+ ulong addr; -+ -+ if (!readmem(S390X_LC_VMCORE_INFO, PHYSADDR, &addr, -+ sizeof(addr), "s390x vmcoreinfo ptr", -+ QUIET|RETURN_ON_ERROR)) -+ return 0; -+ if (addr == 0 || addr & 0x1) -+ return 0; -+ if (!readmem(addr, PHYSADDR, ¬e, -+ sizeof(note), "Elf64_Nhdr vmcoreinfo", -+ QUIET|RETURN_ON_ERROR)) -+ return 0; -+ memset(str, 0, sizeof(str)); -+ if (!readmem(addr + sizeof(note), PHYSADDR, str, -+ note.n_namesz, "VMCOREINFO", -+ QUIET|RETURN_ON_ERROR)) -+ return 0; -+ if (memcmp(str, "VMCOREINFO", sizeof("VMCOREINFO")) != 0) -+ return 0; -+ if ((vmcoreinfo = malloc(note.n_descsz + 1)) == NULL) { -+ error(INFO, "s390x: cannot malloc vmcoreinfo buffer\n"); -+ return 0; -+ } -+ addr = addr + sizeof(note) + note.n_namesz + 1; -+ if (!readmem(addr, PHYSADDR, vmcoreinfo, -+ note.n_descsz, "s390x vmcoreinfo", -+ QUIET|RETURN_ON_ERROR)) { -+ free(vmcoreinfo); -+ return 0; -+ } -+ vmcoreinfo[note.n_descsz] = 0; -+ if ((_stext_string = vmcoreinfo_read_string_s390x(vmcoreinfo, -+ "SYMBOL(_stext)"))) { -+ val = htol(_stext_string, RETURN_ON_ERROR, NULL); -+ free(_stext_string); -+ } -+ free(vmcoreinfo); -+ return val; -+} -+ - /* - * Do all necessary machine-specific setup here. This is called several - * times during initialization. -@@ -1948,4 +2020,10 @@ s390x_get_kvaddr_ranges(struct vaddr_range *vrp) - - return cnt; - } --#endif -+#else -+#include "defs.h" -+ulong get_stext_relocated_s390x(void) -+{ -+ return 0; -+} -+#endif /* S390X */ -diff --git a/symbols.c b/symbols.c -index 82ac549..6df3358 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -614,7 +614,9 @@ kaslr_init(void) - st->_stext_vmlinux = UNINITIALIZED; - } - -- if (machine_type("S390X")) { -+ if (machine_type("S390X")) { -+ if (!kt->vmcoreinfo._stext_SYMBOL) -+ kt->vmcoreinfo._stext_SYMBOL = get_stext_relocated_s390x(); - kt->flags2 |= (RELOC_AUTO|KASLR); - st->_stext_vmlinux = UNINITIALIZED; - } - -commit c6b19715495221dca52a57690419f9df9777573d -Author: Dave Anderson -Date: Fri Jan 17 13:34:53 2020 -0500 - - Rework the previous patch for support of S390X standalone dumpfiles - and LKCD dumpfiles that were taken from S390X KASLR kernels to avoid - calling an s390x-specific function from generic code. - (zaslonko@linux.ibm.com) - -diff --git a/defs.h b/defs.h -index 88a47d6..efa40b9 100644 ---- a/defs.h -+++ b/defs.h -@@ -6267,8 +6267,6 @@ void get_s390_panicmsg(char *); - /* - * s390x.c - */ --ulong get_stext_relocated_s390x(void); -- - #ifdef S390X - void s390x_init(int); - void s390x_dump_machdep_table(ulong); -diff --git a/s390x.c b/s390x.c -index e030f93..c07d283 100644 ---- a/s390x.c -+++ b/s390x.c -@@ -478,53 +478,72 @@ vmcoreinfo_read_string_s390x(const char *vmcoreinfo, const char *key) - } - - /* -- * Read _stext symbol from vmcoreinfo when lowcore vmcoreinfo pointer is present -- * in the dump (can be relevant for s390 and lkcd dump formats). -+ * Check the value in well-known lowcore location and process it as either -+ * an explicit KASLR offset (early dump case) or as vmcoreinfo pointer to -+ * read the relocated _stext symbol value (important for s390 and lkcd dump -+ * formats). - */ --ulong get_stext_relocated_s390x(void) -+static void s390x_check_kaslr(void) - { - char *_stext_string, *vmcoreinfo; - Elf64_Nhdr note; - char str[128]; -- ulong val = 0; - ulong addr; - -+ /* Read the value from well-known lowcore location*/ - if (!readmem(S390X_LC_VMCORE_INFO, PHYSADDR, &addr, - sizeof(addr), "s390x vmcoreinfo ptr", - QUIET|RETURN_ON_ERROR)) -- return 0; -- if (addr == 0 || addr & 0x1) -- return 0; -+ return; -+ if (addr == 0) -+ return; -+ /* Check for explicit kaslr offset flag */ -+ if (addr & 0x1UL) { -+ /* Drop the last bit to get an offset value */ -+ addr &= ~(0x1UL); -+ /* Make sure the offset is aligned by 0x1000 */ -+ if (addr && !(addr & 0xfff)) { -+ kt->relocate = addr * (-1); -+ kt->flags |= RELOC_SET; -+ kt->flags2 |= KASLR; -+ } -+ return; -+ } -+ /* Use the addr value as vmcoreinfo pointer */ - if (!readmem(addr, PHYSADDR, ¬e, - sizeof(note), "Elf64_Nhdr vmcoreinfo", - QUIET|RETURN_ON_ERROR)) -- return 0; -+ return; - memset(str, 0, sizeof(str)); - if (!readmem(addr + sizeof(note), PHYSADDR, str, - note.n_namesz, "VMCOREINFO", - QUIET|RETURN_ON_ERROR)) -- return 0; -+ return; - if (memcmp(str, "VMCOREINFO", sizeof("VMCOREINFO")) != 0) -- return 0; -+ return; - if ((vmcoreinfo = malloc(note.n_descsz + 1)) == NULL) { -- error(INFO, "s390x: cannot malloc vmcoreinfo buffer\n"); -- return 0; -+ error(INFO, "s390x_check_kaslr: cannot malloc vmcoreinfo buffer\n"); -+ return; - } - addr = addr + sizeof(note) + note.n_namesz + 1; - if (!readmem(addr, PHYSADDR, vmcoreinfo, - note.n_descsz, "s390x vmcoreinfo", - QUIET|RETURN_ON_ERROR)) { - free(vmcoreinfo); -- return 0; -+ return; - } -- vmcoreinfo[note.n_descsz] = 0; -+ vmcoreinfo[note.n_descsz] = NULLCHAR; -+ /* -+ * Read relocated _stext symbol value and store it in the kernel_table -+ * for further processing within derive_kaslr_offset(). -+ */ - if ((_stext_string = vmcoreinfo_read_string_s390x(vmcoreinfo, - "SYMBOL(_stext)"))) { -- val = htol(_stext_string, RETURN_ON_ERROR, NULL); -+ kt->vmcoreinfo._stext_SYMBOL = htol(_stext_string, -+ RETURN_ON_ERROR, NULL); - free(_stext_string); - } - free(vmcoreinfo); -- return val; - } - - /* -@@ -534,8 +553,6 @@ ulong get_stext_relocated_s390x(void) - void - s390x_init(int when) - { -- ulong s390x_lc_kaslr; -- - switch (when) - { - case SETUP_ENV: -@@ -562,24 +579,8 @@ s390x_init(int when) - machdep->verify_paddr = generic_verify_paddr; - machdep->get_kvaddr_ranges = s390x_get_kvaddr_ranges; - machdep->ptrs_per_pgd = PTRS_PER_PGD; -- if (DUMPFILE() && !(kt->flags & RELOC_SET)) { -- /* Read the value from well-known lowcore location*/ -- if (readmem(S390X_LC_VMCORE_INFO, PHYSADDR, &s390x_lc_kaslr, -- sizeof(s390x_lc_kaslr), "s390x_lc_kaslr", -- QUIET|RETURN_ON_ERROR)) { -- /* Check for explicit kaslr offset flag */ -- if (s390x_lc_kaslr & 0x1UL) { -- /* Drop the last bit to get an offset value */ -- s390x_lc_kaslr &= ~(0x1UL); -- /* Make sure the offset is aligned by 0x1000 */ -- if (s390x_lc_kaslr && !(s390x_lc_kaslr & 0xfff)) { -- kt->relocate = s390x_lc_kaslr * (-1); -- kt->flags |= RELOC_SET; -- kt->flags2 |= KASLR; -- } -- } -- } -- } -+ if (DUMPFILE() && !(kt->flags & RELOC_SET)) -+ s390x_check_kaslr(); - break; - - case PRE_GDB: -@@ -2020,10 +2021,4 @@ s390x_get_kvaddr_ranges(struct vaddr_range *vrp) - - return cnt; - } --#else --#include "defs.h" --ulong get_stext_relocated_s390x(void) --{ -- return 0; --} - #endif /* S390X */ -diff --git a/symbols.c b/symbols.c -index 6df3358..f04e8b5 100644 ---- a/symbols.c -+++ b/symbols.c -@@ -597,7 +597,8 @@ kaslr_init(void) - !machine_type("S390X")) || (kt->flags & RELOC_SET)) - return; - -- if ((string = pc->read_vmcoreinfo("SYMBOL(_stext)"))) { -+ if (!kt->vmcoreinfo._stext_SYMBOL && -+ (string = pc->read_vmcoreinfo("SYMBOL(_stext)"))) { - kt->vmcoreinfo._stext_SYMBOL = htol(string, RETURN_ON_ERROR, NULL); - free(string); - } -@@ -615,8 +616,6 @@ kaslr_init(void) - } - - if (machine_type("S390X")) { -- if (!kt->vmcoreinfo._stext_SYMBOL) -- kt->vmcoreinfo._stext_SYMBOL = get_stext_relocated_s390x(); - kt->flags2 |= (RELOC_AUTO|KASLR); - st->_stext_vmlinux = UNINITIALIZED; - } - -commit 6c1c8ac6b3c877e6facd6f2807ba721ddbc4597b -Author: Dave Anderson -Date: Wed Jan 29 11:10:26 2020 -0500 - - Fix for a gcc-10 compilation error. Without the patch, the build of - the crash library fails with a stream of error messages indicating - "multiple definition of 'diskdump_flags'" - (anderson@redhat.com) - -diff --git a/defs.h b/defs.h -index efa40b9..ac24a5d 100644 ---- a/defs.h -+++ b/defs.h -@@ -1,8 +1,8 @@ - /* defs.h - core analysis suite - * - * Copyright (C) 1999, 2000, 2001, 2002 Mission Critical Linux, Inc. -- * Copyright (C) 2002-2019 David Anderson -- * Copyright (C) 2002-2019 Red Hat, Inc. All rights reserved. -+ * Copyright (C) 2002-2020 David Anderson -+ * Copyright (C) 2002-2020 Red Hat, Inc. All rights reserved. - * Copyright (C) 2002 Silicon Graphics, Inc. - * - * This program is free software; you can redistribute it and/or modify -@@ -6447,7 +6447,7 @@ FILE *set_diskdump_fp(FILE *); - void get_diskdump_regs(struct bt_info *, ulong *, ulong *); - int diskdump_phys_base(unsigned long *); - int diskdump_set_phys_base(unsigned long); --ulong *diskdump_flags; -+extern ulong *diskdump_flags; - int is_partial_diskdump(void); - int get_dump_level(void); - int dumpfile_is_split(void); diff --git a/SOURCES/github_9596b4388ea5.patch b/SOURCES/github_9596b4388ea5.patch new file mode 100644 index 0000000..9607aa2 --- /dev/null +++ b/SOURCES/github_9596b4388ea5.patch @@ -0,0 +1,909 @@ +commit 9596b4388ea5ebbf7de79f0e377a497de1616654 +Author: Bhupesh Sharma +Date: Thu Aug 6 13:17:26 2020 +0530 + + crash/arm64: Revert to implementation used in crash-7.2.3-17.el8 [Support for CONFIG_ARM64_USER_VA_BITS_52 and CONFIG_ARM64_PA_BITS=52] + + Signed-off-by: Bhupesh Sharma + +diff --git a/arm64.c b/arm64.c +index 49e25733f094..dfcde6e11359 100644 +--- a/arm64.c ++++ b/arm64.c +@@ -27,12 +27,9 @@ + static struct machine_specific arm64_machine_specific = { 0 }; + static int arm64_verify_symbol(const char *, ulong, char); + static void arm64_parse_cmdline_args(void); +-static int arm64_search_for_kimage_voffset(ulong); +-static int verify_kimage_voffset(void); + static void arm64_calc_kimage_voffset(void); + static void arm64_calc_phys_offset(void); + static void arm64_calc_virtual_memory_ranges(void); +-static void arm64_get_section_size_bits(void); + static int arm64_kdump_phys_base(ulong *); + static ulong arm64_processor_speed(void); + static void arm64_init_kernel_pgd(void); +@@ -81,7 +78,7 @@ static int arm64_on_irq_stack(int, ulong); + static void arm64_set_irq_stack(struct bt_info *); + static void arm64_set_process_stack(struct bt_info *); + static int arm64_get_kvaddr_ranges(struct vaddr_range *); +-static void arm64_get_crash_notes(void); ++static int arm64_get_crash_notes(void); + static void arm64_calc_VA_BITS(void); + static int arm64_is_uvaddr(ulong, struct task_context *); + +@@ -147,12 +144,6 @@ arm64_init(int when) + if (kernel_symbol_exists("kimage_voffset")) + machdep->flags |= NEW_VMEMMAP; + +- if (!machdep->pagesize && +- (string = pc->read_vmcoreinfo("PAGESIZE"))) { +- machdep->pagesize = atoi(string); +- free(string); +- } +- + if (!machdep->pagesize) { + /* + * Kerneldoc Documentation/arm64/booting.txt describes +@@ -179,16 +170,17 @@ arm64_init(int when) + + } + +- /* +- * This code section will only be executed if the kernel is +- * earlier than Linux 4.4 (if there is no vmcoreinfo) +- */ + if (!machdep->pagesize && + kernel_symbol_exists("swapper_pg_dir") && + kernel_symbol_exists("idmap_pg_dir")) { +- value = symbol_value("swapper_pg_dir") - +- symbol_value("idmap_pg_dir"); ++ if (kernel_symbol_exists("tramp_pg_dir")) ++ value = symbol_value("tramp_pg_dir"); ++ else if (kernel_symbol_exists("reserved_ttbr0")) ++ value = symbol_value("reserved_ttbr0"); ++ else ++ value = symbol_value("swapper_pg_dir"); + ++ value -= symbol_value("idmap_pg_dir"); + /* + * idmap_pg_dir is 2 pages prior to 4.1, + * and 3 pages thereafter. Only 4K and 64K +@@ -214,19 +206,12 @@ arm64_init(int when) + + arm64_calc_VA_BITS(); + ms = machdep->machspec; +- if (ms->VA_BITS_ACTUAL) { +- ms->page_offset = ARM64_PAGE_OFFSET_ACTUAL; +- machdep->identity_map_base = ARM64_PAGE_OFFSET_ACTUAL; +- machdep->kvbase = ARM64_PAGE_OFFSET_ACTUAL; +- ms->userspace_top = ARM64_USERSPACE_TOP_ACTUAL; +- } else { +- ms->page_offset = ARM64_PAGE_OFFSET; +- machdep->identity_map_base = ARM64_PAGE_OFFSET; +- machdep->kvbase = ARM64_VA_START; +- ms->userspace_top = ARM64_USERSPACE_TOP; +- } ++ ms->page_offset = ARM64_PAGE_OFFSET; ++ machdep->identity_map_base = ARM64_PAGE_OFFSET; ++ machdep->kvbase = ARM64_VA_START; + machdep->is_kvaddr = generic_is_kvaddr; + machdep->kvtop = arm64_kvtop; ++ ms->userspace_top = ARM64_USERSPACE_TOP; + if (machdep->flags & NEW_VMEMMAP) { + struct syment *sp; + +@@ -235,15 +220,11 @@ arm64_init(int when) + sp = kernel_symbol_search("_end"); + ms->kimage_end = (sp ? sp->value : 0); + +- if (ms->VA_BITS_ACTUAL) { +- ms->modules_vaddr = (st->_stext_vmlinux & TEXT_OFFSET_MASK) - ARM64_MODULES_VSIZE; +- ms->modules_end = ms->modules_vaddr + ARM64_MODULES_VSIZE -1; +- } else { +- ms->modules_vaddr = ARM64_VA_START; +- if (kernel_symbol_exists("kasan_init")) +- ms->modules_vaddr += ARM64_KASAN_SHADOW_SIZE; +- ms->modules_end = ms->modules_vaddr + ARM64_MODULES_VSIZE -1; +- } ++ ms->modules_vaddr = ARM64_VA_START; ++ if (kernel_symbol_exists("kasan_init")) ++ ms->modules_vaddr += ARM64_KASAN_SHADOW_SIZE; ++ ms->modules_end = ms->modules_vaddr ++ + ARM64_MODULES_VSIZE -1; + + ms->vmalloc_start_addr = ms->modules_end + 1; + +@@ -285,7 +266,7 @@ arm64_init(int when) + case 65536: + if (kernel_symbol_exists("idmap_ptrs_per_pgd") && + readmem(symbol_value("idmap_ptrs_per_pgd"), KVADDR, +- &value, sizeof(ulong), "idmap_ptrs_per_pgd", QUIET|RETURN_ON_ERROR)) ++ &value, sizeof(ulong), "idmap_ptrs_per_pgd", RETURN_ON_ERROR)) + machdep->ptrs_per_pgd = value; + + if (machdep->machspec->VA_BITS > PGDIR_SHIFT_L3_64K) { +@@ -335,6 +316,10 @@ arm64_init(int when) + + machdep->uvtop = arm64_uvtop; + machdep->is_uvaddr = arm64_is_uvaddr; ++ if (kernel_symbol_exists("vabits_user") && ++ readmem(symbol_value("vabits_user"), KVADDR, ++ &value, sizeof(ulong), "vabits_user", RETURN_ON_ERROR)) ++ machdep->machspec->vabits_user = value; + machdep->eframe_search = arm64_eframe_search; + machdep->back_trace = arm64_back_trace_cmd; + machdep->in_alternate_stack = arm64_in_alternate_stack; +@@ -375,8 +360,7 @@ arm64_init(int when) + + case POST_GDB: + arm64_calc_virtual_memory_ranges(); +- arm64_get_section_size_bits(); +- ++ machdep->section_size_bits = _SECTION_SIZE_BITS; + if (!machdep->max_physmem_bits) { + if ((string = pc->read_vmcoreinfo("NUMBER(MAX_PHYSMEM_BITS)"))) { + machdep->max_physmem_bits = atol(string); +@@ -388,24 +372,8 @@ arm64_init(int when) + else + machdep->max_physmem_bits = _MAX_PHYSMEM_BITS; + } +- + ms = machdep->machspec; + +- if (CRASHDEBUG(1)) { +- if (ms->VA_BITS_ACTUAL) { +- fprintf(fp, "CONFIG_ARM64_VA_BITS: %ld\n", ms->CONFIG_ARM64_VA_BITS); +- fprintf(fp, " VA_BITS_ACTUAL: %ld\n", ms->VA_BITS_ACTUAL); +- fprintf(fp, "(calculated) VA_BITS: %ld\n", ms->VA_BITS); +- fprintf(fp, " PAGE_OFFSET: %lx\n", ARM64_PAGE_OFFSET_ACTUAL); +- fprintf(fp, " VA_START: %lx\n", ms->VA_START); +- fprintf(fp, " modules: %lx - %lx\n", ms->modules_vaddr, ms->modules_end); +- fprintf(fp, " vmalloc: %lx - %lx\n", ms->vmalloc_start_addr, ms->vmalloc_end); +- fprintf(fp, "kernel image: %lx - %lx\n", ms->kimage_text, ms->kimage_end); +- fprintf(fp, " vmemmap: %lx - %lx\n\n", ms->vmemmap_vaddr, ms->vmemmap_end); +- } +- } +- +- + if (THIS_KERNEL_VERSION >= LINUX(4,0,0)) { + ms->__SWP_TYPE_BITS = 6; + ms->__SWP_TYPE_SHIFT = 2; +@@ -465,8 +433,11 @@ arm64_init(int when) + * of the crash. We need this information to extract correct + * backtraces from the panic task. + */ +- if (!LIVE()) +- arm64_get_crash_notes(); ++ if (!LIVE() && !arm64_get_crash_notes()) ++ error(WARNING, ++ "cannot retrieve registers for active task%s\n\n", ++ kt->cpus > 1 ? "s" : ""); ++ + break; + + case LOG_ONLY: +@@ -648,15 +619,9 @@ arm64_dump_machdep_table(ulong arg) + + fprintf(fp, " machspec: %lx\n", (ulong)ms); + fprintf(fp, " VA_BITS: %ld\n", ms->VA_BITS); +- fprintf(fp, " CONFIG_ARM64_VA_BITS: %ld\n", ms->CONFIG_ARM64_VA_BITS); +- fprintf(fp, " VA_START: "); +- if (ms->VA_START) +- fprintf(fp, "%lx\n", ms->VA_START); +- else +- fprintf(fp, "(unused)\n"); +- fprintf(fp, " VA_BITS_ACTUAL: "); +- if (ms->VA_BITS_ACTUAL) +- fprintf(fp, "%ld\n", ms->VA_BITS_ACTUAL); ++ fprintf(fp, " vabits_user: "); ++ if (ms->vabits_user) ++ fprintf(fp, "%ld\n", ms->vabits_user); + else + fprintf(fp, "(unused)\n"); + fprintf(fp, " userspace_top: %016lx\n", ms->userspace_top); +@@ -745,12 +710,12 @@ arm64_parse_machdep_arg_l(char *argstring, char *param, ulong *value) + int flags = RETURN_ON_ERROR | QUIET; + int err = 0; + +- if (STRNEQ(argstring, "max_physmem_bits")) { +- *value = dtol(p, flags, &err); +- } else if (megabytes) { ++ if (megabytes) { + *value = dtol(p, flags, &err); + if (!err) + *value = MEGABYTES(*value); ++ } else if (STRNEQ(argstring, "max_physmem_bits")) { ++ *value = dtol(p, flags, &err); + } else { + *value = htol(p, flags, &err); + } +@@ -824,60 +789,11 @@ arm64_parse_cmdline_args(void) + } + } + +-#define MIN_KIMG_ALIGN (0x00200000) /* kimage load address must be aligned 2M */ +-/* +- * Traverse the entire dumpfile to find/verify kimage_voffset. +- */ +-static int +-arm64_search_for_kimage_voffset(ulong phys_base) +-{ +- ulong kimage_load_addr; +- ulong phys_end; +- struct machine_specific *ms = machdep->machspec; +- +- if (!arm_kdump_phys_end(&phys_end)) +- return FALSE; +- +- for (kimage_load_addr = phys_base; +- kimage_load_addr <= phys_end; kimage_load_addr += MIN_KIMG_ALIGN) { +- ms->kimage_voffset = ms->vmalloc_start_addr - kimage_load_addr; +- +- if ((kt->flags2 & KASLR) && (kt->flags & RELOC_SET)) +- ms->kimage_voffset += (kt->relocate * - 1); +- +- if (verify_kimage_voffset()) { +- if (CRASHDEBUG(1)) +- error(INFO, +- "dumpfile searched for kimage_voffset: %lx\n\n", +- ms->kimage_voffset); +- break; +- } +- } +- +- if (kimage_load_addr > phys_end) +- return FALSE; +- +- return TRUE; +-} +- +-static int +-verify_kimage_voffset(void) +-{ +- ulong kimage_voffset; +- +- if (!readmem(symbol_value("kimage_voffset"), KVADDR, &kimage_voffset, +- sizeof(kimage_voffset), "verify kimage_voffset", QUIET|RETURN_ON_ERROR)) +- return FALSE; +- +- return (machdep->machspec->kimage_voffset == kimage_voffset); +-} +- + static void + arm64_calc_kimage_voffset(void) + { + struct machine_specific *ms = machdep->machspec; +- ulong phys_addr = 0; +- int errflag; ++ ulong phys_addr; + + if (ms->kimage_voffset) /* vmcoreinfo, ioctl, or --machdep override */ + return; +@@ -885,6 +801,7 @@ arm64_calc_kimage_voffset(void) + if (ACTIVE()) { + char buf[BUFSIZE]; + char *p1; ++ int errflag; + FILE *iomem; + ulong kimage_voffset, vaddr; + +@@ -925,24 +842,9 @@ arm64_calc_kimage_voffset(void) + if (errflag) + return; + +- } else if (KDUMP_DUMPFILE()) { +- errflag = 1; +- if (arm_kdump_phys_base(&phys_addr)) { /* Get start address of first memory block */ +- ms->kimage_voffset = ms->vmalloc_start_addr - phys_addr; +- if ((kt->flags2 & KASLR) && (kt->flags & RELOC_SET)) +- ms->kimage_voffset += (kt->relocate * -1); +- if (verify_kimage_voffset() || arm64_search_for_kimage_voffset(phys_addr)) +- errflag = 0; +- } +- +- if (errflag) { +- error(WARNING, +- "kimage_voffset cannot be determined from the dumpfile.\n"); +- error(CONT, +- "Try using the command line option: --machdep kimage_voffset=\n"); +- } +- return; +- } else { ++ } else if (KDUMP_DUMPFILE()) ++ arm_kdump_phys_base(&phys_addr); /* Get start address of first memory block */ ++ else { + error(WARNING, + "kimage_voffset cannot be determined from the dumpfile.\n"); + error(CONT, +@@ -981,16 +883,10 @@ arm64_calc_phys_offset(void) + physaddr_t paddr; + ulong vaddr; + struct syment *sp; +- char *string; + + if ((machdep->flags & NEW_VMEMMAP) && + ms->kimage_voffset && (sp = kernel_symbol_search("memstart_addr"))) { + if (pc->flags & PROC_KCORE) { +- if ((string = pc->read_vmcoreinfo("NUMBER(PHYS_OFFSET)"))) { +- ms->phys_offset = htol(string, QUIET, NULL); +- free(string); +- return; +- } + vaddr = symbol_value_from_proc_kallsyms("memstart_addr"); + if (vaddr == BADVAL) + vaddr = sp->value; +@@ -1053,31 +949,6 @@ arm64_calc_phys_offset(void) + fprintf(fp, "using %lx as phys_offset\n", ms->phys_offset); + } + +-/* +- * Determine SECTION_SIZE_BITS either by reading VMCOREINFO or the kernel +- * config, otherwise use the 64-bit ARM default definiton. +- */ +-static void +-arm64_get_section_size_bits(void) +-{ +- int ret; +- char *string; +- +- machdep->section_size_bits = _SECTION_SIZE_BITS; +- +- if ((string = pc->read_vmcoreinfo("NUMBER(SECTION_SIZE_BITS)"))) { +- machdep->section_size_bits = atol(string); +- free(string); +- } else if (kt->ikconfig_flags & IKCONFIG_AVAIL) { +- if ((ret = get_kernel_config("CONFIG_MEMORY_HOTPLUG", NULL)) == IKCONFIG_Y) { +- if ((ret = get_kernel_config("CONFIG_HOTPLUG_SIZE_BITS", &string)) == IKCONFIG_STR) +- machdep->section_size_bits = atol(string); +- } +- } +- +- if (CRASHDEBUG(1)) +- fprintf(fp, "SECTION_SIZE_BITS: %ld\n", machdep->section_size_bits); +-} + + /* + * Determine PHYS_OFFSET either by reading VMCOREINFO or the kernel +@@ -1133,12 +1004,6 @@ ulong + arm64_VTOP(ulong addr) + { + if (machdep->flags & NEW_VMEMMAP) { +- if (machdep->machspec->VA_START && +- (addr >= machdep->machspec->kimage_text) && +- (addr <= machdep->machspec->kimage_end)) { +- return addr - machdep->machspec->kimage_voffset; +- } +- + if (addr >= machdep->machspec->page_offset) + return machdep->machspec->phys_offset + + (addr - machdep->machspec->page_offset); +@@ -1215,11 +1080,6 @@ arm64_uvtop(struct task_context *tc, ulong uvaddr, physaddr_t *paddr, int verbos + } + } + +-#define PTE_ADDR_LOW ((((1UL) << (48 - machdep->pageshift)) - 1) << machdep->pageshift) +-#define PTE_ADDR_HIGH ((0xfUL) << 12) +-#define PTE_TO_PHYS(pteval) (machdep->max_physmem_bits == 52 ? \ +- (((pteval & PTE_ADDR_LOW) | ((pteval & PTE_ADDR_HIGH) << 36))) : (pteval & PTE_ADDR_LOW)) +- + #define PMD_TYPE_MASK 3 + #define PMD_TYPE_SECT 1 + #define PMD_TYPE_TABLE 2 +@@ -1312,7 +1172,7 @@ arm64_vtop_3level_64k(ulong pgd, ulong vaddr, physaddr_t *paddr, int verbose) + * #define __PAGETABLE_PUD_FOLDED + */ + +- pmd_base = (ulong *)PTOV(PTE_TO_PHYS(pgd_val)); ++ pmd_base = (ulong *)PTOV(pgd_val & PHYS_MASK & (s32)machdep->pagemask); + FILL_PMD(pmd_base, KVADDR, PTRS_PER_PMD_L3_64K * sizeof(ulong)); + pmd_ptr = pmd_base + (((vaddr) >> PMD_SHIFT_L3_64K) & (PTRS_PER_PMD_L3_64K - 1)); + pmd_val = ULONG(machdep->pmd + PAGEOFFSET(pmd_ptr)); +@@ -1322,7 +1182,7 @@ arm64_vtop_3level_64k(ulong pgd, ulong vaddr, physaddr_t *paddr, int verbose) + goto no_page; + + if ((pmd_val & PMD_TYPE_MASK) == PMD_TYPE_SECT) { +- ulong sectionbase = PTE_TO_PHYS(pmd_val) & SECTION_PAGE_MASK_512MB; ++ ulong sectionbase = (pmd_val & SECTION_PAGE_MASK_512MB) & PHYS_MASK; + if (verbose) { + fprintf(fp, " PAGE: %lx (512MB)\n\n", sectionbase); + arm64_translate_pte(pmd_val, 0, 0); +@@ -1331,7 +1191,7 @@ arm64_vtop_3level_64k(ulong pgd, ulong vaddr, physaddr_t *paddr, int verbose) + return TRUE; + } + +- pte_base = (ulong *)PTOV(PTE_TO_PHYS(pmd_val)); ++ pte_base = (ulong *)PTOV(pmd_val & PHYS_MASK & (s32)machdep->pagemask); + FILL_PTBL(pte_base, KVADDR, PTRS_PER_PTE_L3_64K * sizeof(ulong)); + pte_ptr = pte_base + (((vaddr) >> machdep->pageshift) & (PTRS_PER_PTE_L3_64K - 1)); + pte_val = ULONG(machdep->ptbl + PAGEOFFSET(pte_ptr)); +@@ -1341,7 +1201,7 @@ arm64_vtop_3level_64k(ulong pgd, ulong vaddr, physaddr_t *paddr, int verbose) + goto no_page; + + if (pte_val & PTE_VALID) { +- *paddr = PTE_TO_PHYS(pte_val) + PAGEOFFSET(vaddr); ++ *paddr = (PAGEBASE(pte_val) & PHYS_MASK) + PAGEOFFSET(vaddr); + if (verbose) { + fprintf(fp, " PAGE: %lx\n\n", PAGEBASE(*paddr)); + arm64_translate_pte(pte_val, 0, 0); +@@ -1644,11 +1504,10 @@ arm64_stackframe_init(void) + machdep->machspec->kern_eframe_offset = SIZE(pt_regs); + } + +- if ((sp1 = kernel_symbol_search("__exception_text_start")) && +- (sp2 = kernel_symbol_search("__exception_text_end"))) { +- machdep->machspec->__exception_text_start = sp1->value; +- machdep->machspec->__exception_text_end = sp2->value; +- } ++ machdep->machspec->__exception_text_start = ++ symbol_value("__exception_text_start"); ++ machdep->machspec->__exception_text_end = ++ symbol_value("__exception_text_end"); + if ((sp1 = kernel_symbol_search("__irqentry_text_start")) && + (sp2 = kernel_symbol_search("__irqentry_text_end"))) { + machdep->machspec->__irqentry_text_start = sp1->value; +@@ -1857,38 +1716,20 @@ arm64_eframe_search(struct bt_info *bt) + return count; + } + +-static char *arm64_exception_functions[] = { +- "do_undefinstr", +- "do_sysinstr", +- "do_debug_exception", +- "do_mem_abort", +- "do_el0_irq_bp_hardening", +- "do_sp_pc_abort", +- NULL +-}; +- + static int + arm64_in_exception_text(ulong ptr) + { + struct machine_specific *ms = machdep->machspec; +- char *name, **func; ++ ++ if ((ptr >= ms->__exception_text_start) && ++ (ptr < ms->__exception_text_end)) ++ return TRUE; + + if (ms->__irqentry_text_start && ms->__irqentry_text_end && + ((ptr >= ms->__irqentry_text_start) && + (ptr < ms->__irqentry_text_end))) + return TRUE; + +- if (ms->__exception_text_start && ms->__exception_text_end) { +- if ((ptr >= ms->__exception_text_start) && +- (ptr < ms->__exception_text_end)) +- return TRUE; +- } else if ((name = closest_symbol(ptr))) { /* Linux 5.5 and later */ +- for (func = &arm64_exception_functions[0]; *func; func++) { +- if (STREQ(name, *func)) +- return TRUE; +- } +- } +- + return FALSE; + } + +@@ -3297,7 +3138,7 @@ arm64_translate_pte(ulong pte, void *physaddr, ulonglong unused) + char *arglist[MAXARGS]; + int page_present; + +- paddr = PTE_TO_PHYS(pte); ++ paddr = pte & PHYS_MASK & (s32)machdep->pagemask; + page_present = pte & (PTE_VALID | machdep->machspec->PTE_PROT_NONE); + + if (physaddr) { +@@ -3563,8 +3404,8 @@ arm64_display_machine_stats(void) + fprintf(fp, " HZ: %d\n", machdep->hz); + fprintf(fp, " PAGE SIZE: %d\n", PAGESIZE()); + fprintf(fp, "KERNEL VIRTUAL BASE: %lx\n", machdep->machspec->page_offset); +- fprintf(fp, "KERNEL MODULES BASE: %lx\n", machdep->machspec->modules_vaddr); + fprintf(fp, "KERNEL VMALLOC BASE: %lx\n", machdep->machspec->vmalloc_start_addr); ++ fprintf(fp, "KERNEL MODULES BASE: %lx\n", machdep->machspec->modules_vaddr); + fprintf(fp, "KERNEL VMEMMAP BASE: %lx\n", machdep->machspec->vmemmap_vaddr); + fprintf(fp, " KERNEL STACK SIZE: %ld\n", STACKSIZE()); + if (machdep->machspec->irq_stack_size) { +@@ -3594,7 +3435,7 @@ arm64_get_smp_cpus(void) + /* + * Retrieve task registers for the time of the crash. + */ +-static void ++static int + arm64_get_crash_notes(void) + { + struct machine_specific *ms = machdep->machspec; +@@ -3603,10 +3444,10 @@ arm64_get_crash_notes(void) + ulong offset; + char *buf, *p; + ulong *notes_ptrs; +- ulong i, found; ++ ulong i; + + if (!symbol_exists("crash_notes")) +- return; ++ return FALSE; + + crash_notes = symbol_value("crash_notes"); + +@@ -3618,9 +3459,9 @@ arm64_get_crash_notes(void) + */ + if (!readmem(crash_notes, KVADDR, ¬es_ptrs[kt->cpus-1], + sizeof(notes_ptrs[kt->cpus-1]), "crash_notes", RETURN_ON_ERROR)) { +- error(WARNING, "cannot read \"crash_notes\"\n"); ++ error(WARNING, "cannot read crash_notes\n"); + FREEBUF(notes_ptrs); +- return; ++ return FALSE; + } + + if (symbol_exists("__per_cpu_offset")) { +@@ -3636,11 +3477,12 @@ arm64_get_crash_notes(void) + if (!(ms->panic_task_regs = calloc((size_t)kt->cpus, sizeof(struct arm64_pt_regs)))) + error(FATAL, "cannot calloc panic_task_regs space\n"); + +- for (i = found = 0; i < kt->cpus; i++) { ++ for (i = 0; i < kt->cpus; i++) { ++ + if (!readmem(notes_ptrs[i], KVADDR, buf, SIZE(note_buf), + "note_buf_t", RETURN_ON_ERROR)) { +- error(WARNING, "cpu %d: cannot read NT_PRSTATUS note\n", i); +- continue; ++ error(WARNING, "failed to read note_buf_t\n"); ++ goto fail; + } + + /* +@@ -3670,24 +3512,19 @@ arm64_get_crash_notes(void) + note->n_descsz == notesz) + BCOPY((char *)note, buf, notesz); + } else { +- error(WARNING, "cpu %d: cannot find NT_PRSTATUS note\n", i); ++ error(WARNING, ++ "cannot find NT_PRSTATUS note for cpu: %d\n", i); + continue; + } + } + +- /* +- * Check the sanity of NT_PRSTATUS note only for each online cpu. +- * If this cpu has invalid note, continue to find the crash notes +- * for other online cpus. +- */ + if (note->n_type != NT_PRSTATUS) { +- error(WARNING, "cpu %d: invalid NT_PRSTATUS note (n_type != NT_PRSTATUS)\n", i); +- continue; ++ error(WARNING, "invalid note (n_type != NT_PRSTATUS)\n"); ++ goto fail; + } +- +- if (!STRNEQ(p, "CORE")) { +- error(WARNING, "cpu %d: invalid NT_PRSTATUS note (name != \"CORE\")\n", i); +- continue; ++ if (p[0] != 'C' || p[1] != 'O' || p[2] != 'R' || p[3] != 'E') { ++ error(WARNING, "invalid note (name != \"CORE\"\n"); ++ goto fail; + } + + /* +@@ -3700,17 +3537,18 @@ arm64_get_crash_notes(void) + + BCOPY(p + OFFSET(elf_prstatus_pr_reg), &ms->panic_task_regs[i], + sizeof(struct arm64_pt_regs)); +- +- found++; + } + + FREEBUF(buf); + FREEBUF(notes_ptrs); ++ return TRUE; + +- if (!found) { +- free(ms->panic_task_regs); +- ms->panic_task_regs = NULL; +- } ++fail: ++ FREEBUF(buf); ++ FREEBUF(notes_ptrs); ++ free(ms->panic_task_regs); ++ ms->panic_task_regs = NULL; ++ return FALSE; + } + + static void +@@ -3834,9 +3672,6 @@ arm64_IS_VMALLOC_ADDR(ulong vaddr) + (vaddr <= machdep->machspec->kimage_end)) + return FALSE; + +- if (ms->VA_START && (vaddr >= ms->VA_START)) +- return TRUE; +- + return ((vaddr >= ms->vmalloc_start_addr && vaddr <= ms->vmalloc_end) || + ((machdep->flags & VMEMMAP) && + (vaddr >= ms->vmemmap_vaddr && vaddr <= ms->vmemmap_end)) || +@@ -3848,54 +3683,9 @@ arm64_calc_VA_BITS(void) + { + int bitval; + struct syment *sp; +- ulong vabits_actual, value; ++ ulong value; + char *string; + +- if ((string = pc->read_vmcoreinfo("NUMBER(VA_BITS)"))) { +- value = atol(string); +- free(string); +- machdep->machspec->CONFIG_ARM64_VA_BITS = value; +- } +- +- if (kernel_symbol_exists("vabits_actual")) { +- if (pc->flags & PROC_KCORE) { +- vabits_actual = symbol_value_from_proc_kallsyms("vabits_actual"); +- if ((vabits_actual != BADVAL) && (READMEM(pc->mfd, &value, sizeof(ulong), +- vabits_actual, KCORE_USE_VADDR) > 0)) { +- if (CRASHDEBUG(1)) +- fprintf(fp, +- "/proc/kcore: vabits_actual: %ld\n", value); +- machdep->machspec->VA_BITS_ACTUAL = value; +- machdep->machspec->VA_BITS = value; +- machdep->machspec->VA_START = _VA_START(machdep->machspec->VA_BITS_ACTUAL); +- } else +- error(FATAL, "/proc/kcore: cannot read vabits_actual\n"); +- } else if (ACTIVE()) +- error(FATAL, "cannot determine VA_BITS_ACTUAL: please use /proc/kcore\n"); +- else { +- if ((string = pc->read_vmcoreinfo("NUMBER(TCR_EL1_T1SZ)"))) { +- /* See ARMv8 ARM for the description of +- * TCR_EL1.T1SZ and how it can be used +- * to calculate the vabits_actual +- * supported by underlying kernel. +- * +- * Basically: +- * vabits_actual = 64 - T1SZ; +- */ +- value = 64 - strtoll(string, NULL, 0); +- if (CRASHDEBUG(1)) +- fprintf(fp, "vmcoreinfo : vabits_actual: %ld\n", value); +- free(string); +- machdep->machspec->VA_BITS_ACTUAL = value; +- machdep->machspec->VA_BITS = value; +- machdep->machspec->VA_START = _VA_START(machdep->machspec->VA_BITS_ACTUAL); +- } else +- error(FATAL, "cannot determine VA_BITS_ACTUAL\n"); +- } +- +- return; +- } +- + if (!(sp = symbol_search("swapper_pg_dir")) && + !(sp = symbol_search("idmap_pg_dir")) && + !(sp = symbol_search("_text")) && +@@ -3924,12 +3714,14 @@ arm64_calc_VA_BITS(void) + /* + * Verify against dumpfiles that export VA_BITS in vmcoreinfo + */ +- if (machdep->machspec->CONFIG_ARM64_VA_BITS && +- (machdep->machspec->VA_BITS != machdep->machspec->CONFIG_ARM64_VA_BITS)) { +- error(WARNING, "VA_BITS: calculated: %ld vmcoreinfo: %ld\n", +- machdep->machspec->VA_BITS, machdep->machspec->CONFIG_ARM64_VA_BITS); +- machdep->machspec->VA_BITS = machdep->machspec->CONFIG_ARM64_VA_BITS; +- } ++ if ((string = pc->read_vmcoreinfo("NUMBER(VA_BITS)"))) { ++ value = atol(string); ++ free(string); ++ if (machdep->machspec->VA_BITS != value) ++ error(WARNING, "VA_BITS: calculated: %ld vmcoreinfo: %ld\n", ++ machdep->machspec->VA_BITS, value); ++ } ++ + + if (CRASHDEBUG(1)) + fprintf(fp, "VA_BITS: %ld\n", machdep->machspec->VA_BITS); +@@ -3947,15 +3739,6 @@ arm64_calc_VA_BITS(void) + * + * Since VMEMMAP_SIZE is dependent upon the size of a struct page, + * the two ranges cannot be determined until POST_GDB. +- * +- * Since 52-bit VA was introduced: +- * +- * #define STRUCT_PAGE_MAX_SHIFT 6 +- * #define VMEMMAP_SIZE (UL(1) << (VA_BITS - PAGE_SHIFT - 1 + STRUCT_PAGE_MAX_SHIFT)) +- * #define VMEMMAP_START (-VMEMMAP_SIZE) +- * #define VMALLOC_START (MODULES_END) +- * #define VMALLOC_END (- PUD_SIZE - VMEMMAP_SIZE - SZ_64K) +- * #define vmemmap ((struct page *)VMEMMAP_START - (memstart_addr >> PAGE_SHIFT)) + */ + + #define ALIGN(x, a) __ALIGN_KERNEL((x), (a)) +@@ -3967,18 +3750,10 @@ static void + arm64_calc_virtual_memory_ranges(void) + { + struct machine_specific *ms = machdep->machspec; +- ulong value, vmemmap_start, vmemmap_end, vmemmap_size, vmalloc_end; +- char *string; ++ ulong vmemmap_start, vmemmap_end, vmemmap_size; ++ ulong vmalloc_end; + ulong PUD_SIZE = UNINITIALIZED; + +- if (!machdep->machspec->CONFIG_ARM64_VA_BITS) { +- if ((string = pc->read_vmcoreinfo("NUMBER(VA_BITS)"))) { +- value = atol(string); +- free(string); +- machdep->machspec->CONFIG_ARM64_VA_BITS = value; +- } +- } +- + if (THIS_KERNEL_VERSION < LINUX(3,17,0)) /* use original hardwired values */ + return; + +@@ -3997,19 +3772,8 @@ arm64_calc_virtual_memory_ranges(void) + break; + } + +-#define STRUCT_PAGE_MAX_SHIFT 6 +- +- if (ms->VA_BITS_ACTUAL) { +- vmemmap_size = (1UL) << (ms->CONFIG_ARM64_VA_BITS - machdep->pageshift - 1 + STRUCT_PAGE_MAX_SHIFT); +- vmalloc_end = (- PUD_SIZE - vmemmap_size - KILOBYTES(64)); +- vmemmap_start = (-vmemmap_size); +- ms->vmalloc_end = vmalloc_end - 1; +- ms->vmemmap_vaddr = vmemmap_start; +- ms->vmemmap_end = -1; +- return; +- } +- + if (machdep->flags & NEW_VMEMMAP) ++#define STRUCT_PAGE_MAX_SHIFT 6 + vmemmap_size = 1UL << (ms->VA_BITS - machdep->pageshift - 1 + + STRUCT_PAGE_MAX_SHIFT); + else +@@ -4033,7 +3797,7 @@ arm64_calc_virtual_memory_ranges(void) + static int + arm64_is_uvaddr(ulong addr, struct task_context *tc) + { +- return (addr < machdep->machspec->userspace_top); ++ return (addr < ARM64_USERSPACE_TOP); + } + + +diff --git a/defs.h b/defs.h +index ac24a5d730d5..d0b021f61c67 100644 +--- a/defs.h ++++ b/defs.h +@@ -3148,17 +3148,9 @@ typedef signed int s32; + */ + #define ARM64_VA_START ((0xffffffffffffffffUL) \ + << machdep->machspec->VA_BITS) +-#define _VA_START(va) ((0xffffffffffffffffUL) - \ +- ((1UL) << ((va) - 1)) + 1) +-#define TEXT_OFFSET_MASK (~((MEGABYTES(2UL))-1)) +- + #define ARM64_PAGE_OFFSET ((0xffffffffffffffffUL) \ + << (machdep->machspec->VA_BITS - 1)) +-#define ARM64_PAGE_OFFSET_ACTUAL ((0xffffffffffffffffUL) \ +- - ((1UL) << machdep->machspec->VA_BITS_ACTUAL) + 1) +- + #define ARM64_USERSPACE_TOP ((1UL) << machdep->machspec->VA_BITS) +-#define ARM64_USERSPACE_TOP_ACTUAL ((1UL) << machdep->machspec->VA_BITS_ACTUAL) + + /* only used for v4.6 or later */ + #define ARM64_MODULES_VSIZE MEGABYTES(128) +@@ -3261,9 +3253,7 @@ struct machine_specific { + ulong kern_eframe_offset; + ulong machine_kexec_start; + ulong machine_kexec_end; +- ulong VA_BITS_ACTUAL; +- ulong CONFIG_ARM64_VA_BITS; +- ulong VA_START; ++ ulong vabits_user; + }; + + struct arm64_stackframe { +diff --git a/netdump.c b/netdump.c +index 0054d6ab35b4..31ab6fae5ccd 100644 +--- a/netdump.c ++++ b/netdump.c +@@ -1228,19 +1228,7 @@ netdump_memory_dump(FILE *fp) + if (machine_type("X86_64")) + netdump_print("%lx (relocate)\n", nd->arch_data1); + else if (machine_type("ARM64")) +- netdump_print("%lx (kimage_voffset)\n", nd->arch_data1); +- } else +- netdump_print("(unused)\n"); +- netdump_print(" arch_data2: "); +- if (nd->arch_data2) { +- if (machine_type("ARM64")) +- netdump_print("%016lx\n" +- " CONFIG_ARM64_VA_BITS: %ld\n" +- " VA_BITS_ACTUAL: %lld\n", +- nd->arch_data2, nd->arch_data2 & 0xffffffff, +- ((ulonglong)nd->arch_data2 >> 32)); +- else +- netdump_print("%016lx (?)\n", nd->arch_data2); ++ netdump_print("%lx (kimage_voffset)\n", nd->arch_data); + } else + netdump_print("(unused)\n"); + netdump_print(" switch_stack: %lx\n", nd->switch_stack); +@@ -1865,8 +1853,7 @@ vmcoreinfo_read_string(const char *key) + int i, j, end; + size_t value_length; + size_t key_length = strlen(key); +- char *vmcoreinfo; +- uint size_vmcoreinfo; ++ char *vmcoreinfo = (char *)nd->vmcoreinfo; + char *value = NULL; + + /* +@@ -1875,49 +1862,25 @@ vmcoreinfo_read_string(const char *key) + * the NT_TASKSTRUCT note. + */ + if ((pc->flags2 & SNAP)) { +- if (STREQ(key, "NUMBER(kimage_voffset)") && nd->arch_data1) { ++ if (STREQ(key, "NUMBER(kimage_voffset)") && nd->arch_data) { + value = calloc(VADDR_PRLEN+1, sizeof(char)); +- sprintf(value, "%lx", nd->arch_data1); +- if (nd->arch_data2 == 0) +- pc->read_vmcoreinfo = no_vmcoreinfo; +- return value; +- } +- if (STREQ(key, "NUMBER(VA_BITS)") && nd->arch_data2) { +- value = calloc(VADDR_PRLEN+1, sizeof(char)); +- sprintf(value, "%ld", nd->arch_data2 & 0xffffffff); +- return value; +- } +- if (STREQ(key, "NUMBER(TCR_EL1_T1SZ)") && nd->arch_data2) { +- value = calloc(VADDR_PRLEN+1, sizeof(char)); +- sprintf(value, "%lld", ((ulonglong)nd->arch_data2 >> 32) & 0xffffffff); ++ sprintf(value, "%lx", nd->arch_data); + pc->read_vmcoreinfo = no_vmcoreinfo; + return value; + } +- if (STREQ(key, "relocate") && nd->arch_data1) { ++ if (STREQ(key, "relocate") && nd->arch_data) { + value = calloc(VADDR_PRLEN+1, sizeof(char)); +- sprintf(value, "%lx", nd->arch_data1); ++ sprintf(value, "%lx", nd->arch_data); + pc->read_vmcoreinfo = no_vmcoreinfo; + return value; + } +- return NULL; +- } +- +- if (nd->vmcoreinfo) { +- vmcoreinfo = (char *)nd->vmcoreinfo; +- size_vmcoreinfo = nd->size_vmcoreinfo; +- } else if (ACTIVE() && pkd->vmcoreinfo) { +- vmcoreinfo = (char *)pkd->vmcoreinfo; +- size_vmcoreinfo = pkd->size_vmcoreinfo; +- } else { +- vmcoreinfo = NULL; +- size_vmcoreinfo = 0; + } + +- if (!vmcoreinfo) ++ if (!nd->vmcoreinfo) + return NULL; + + /* the '+ 1' is the equal sign */ +- for (i = 0; i < (int)(size_vmcoreinfo - key_length + 1); i++) { ++ for (i = 0; i < (nd->size_vmcoreinfo - key_length + 1); i++) { + /* + * We must also check if we're at the beginning of VMCOREINFO + * or the separating newline is there, and of course if we +@@ -1931,7 +1894,7 @@ vmcoreinfo_read_string(const char *key) + + /* Found -- search for the next newline. */ + for (j = i + key_length + 1; +- j < size_vmcoreinfo; j++) { ++ j < nd->size_vmcoreinfo; j++) { + if (vmcoreinfo[j] == '\n') { + end = j; + break; +@@ -1944,7 +1907,7 @@ vmcoreinfo_read_string(const char *key) + */ + if (end == -1) { + /* Point after the end. */ +- end = size_vmcoreinfo + 1; ++ end = nd->size_vmcoreinfo + 1; + } + + value_length = end - (1+ i + key_length); diff --git a/SOURCES/github_b80b16549e24.patch b/SOURCES/github_b80b16549e24.patch new file mode 100644 index 0000000..975ea2e --- /dev/null +++ b/SOURCES/github_b80b16549e24.patch @@ -0,0 +1,43 @@ +commit b80b16549e24769c7d5fe3a10c4b1a1c4b5161f3 +Author: Dave Anderson +Date: Mon Mar 23 15:52:11 2020 -0400 + + Fix for reading compressed kdump dumpfiles from systems with physical + memory located at extraordinarily high addresses. In a system with + a physical address range from 0x602770ecf000 to 0x6027ffffffff, the + crash utility fails during session initialization due to an integer + overflow, ending with the error message "crash: vmlinux and vmcore + do not match!". + (chenjialong@huawei.com) + +diff --git crash-7.2.8/diskdump.c crash-7.2.8/diskdump.c +index e88243e616cc..328c932dad5a 100644 +--- crash-7.2.8/diskdump.c ++++ crash-7.2.8/diskdump.c +@@ -233,7 +233,7 @@ clean_diskdump_data(void) + } + + static inline int +-get_bit(char *map, int byte, int bit) ++get_bit(char *map, unsigned long byte, int bit) + { + return map[byte] & (1<max_mapnr = header->max_mapnr; + + /* read memory bitmap */ +- bitmap_len = block_size * header->bitmap_blocks; ++ bitmap_len = (off_t)block_size * header->bitmap_blocks; + dd->bitmap_len = bitmap_len; + + offset = (off_t)block_size * (1 + header->sub_hdr_size); +@@ -744,7 +744,7 @@ restart: + memcpy(dd->dumpable_bitmap, dd->bitmap, bitmap_len); + + dd->data_offset +- = (1 + header->sub_hdr_size + header->bitmap_blocks) ++ = (1UL + header->sub_hdr_size + header->bitmap_blocks) + * header->block_size; + + dd->header = header; diff --git a/SOURCES/github_b97e7fd4e826_to_8b50d94ada21.patch b/SOURCES/github_b97e7fd4e826_to_8b50d94ada21.patch new file mode 100644 index 0000000..3c9e547 --- /dev/null +++ b/SOURCES/github_b97e7fd4e826_to_8b50d94ada21.patch @@ -0,0 +1,368 @@ +From b97e7fd4e8268d5c46f1b30b41ce1f6ca9ceb216 Mon Sep 17 00:00:00 2001 +From: HATAYAMA Daisuke +Date: Mon, 27 Jul 2020 19:00:19 +0900 +Subject: [PATCH 1/4] symbols: Add linux_banner_vmlinux in symbol table + +Add linux_banner_vmlinux in symbol table, which we'll later use in +calc_kaslr_offset() to do a sanity check in calculation of +kaslr_offset and phys_base. + +Signed-off-by: HATAYAMA Daisuke +--- + defs.h | 1 + + symbols.c | 10 ++++++++++ + 2 files changed, 11 insertions(+) + +diff --git a/defs.h b/defs.h +index d7adb23b86d5..17e98763362b 100644 +--- a/defs.h ++++ b/defs.h +@@ -2714,6 +2714,7 @@ struct symbol_table_data { + ulong pti_init_vmlinux; + ulong kaiser_init_vmlinux; + int kernel_symbol_type; ++ ulong linux_banner_vmlinux; + }; + + /* flags for st */ +diff --git a/symbols.c b/symbols.c +index 3b1f08af43ff..b9de4a179d93 100644 +--- a/symbols.c ++++ b/symbols.c +@@ -3226,6 +3226,11 @@ dump_symbol_table(void) + fprintf(fp, " kaiser_init_vmlinux: (unused)\n"); + } + ++ if (SADUMP_DUMPFILE()) ++ fprintf(fp, "linux_banner_vmlinux: %lx\n", st->linux_banner_vmlinux); ++ else ++ fprintf(fp, "linux_banner_vmlinux: (unused)\n"); ++ + fprintf(fp, " symval_hash[%d]: %lx\n", SYMVAL_HASH, + (ulong)&st->symval_hash[0]); + +@@ -12687,6 +12692,11 @@ numeric_forward(const void *P_x, const void *P_y) + else if (STREQ(y->name, "idt_table")) + st->idt_table_vmlinux = valueof(y); + ++ if (STREQ(x->name, "linux_banner")) ++ st->linux_banner_vmlinux = valueof(x); ++ else if (STREQ(y->name, "linux_banner")) ++ st->linux_banner_vmlinux = valueof(y); ++ + if (STREQ(x->name, "saved_command_line")) + st->saved_command_line_vmlinux = valueof(x); + else if (STREQ(y->name, "saved_command_line")) +-- +2.7.4 + + +From d494fabe99b90cea8d717a90951e44e6dbda84bb Mon Sep 17 00:00:00 2001 +From: HATAYAMA Daisuke +Date: Mon, 27 Jul 2020 19:00:20 +0900 +Subject: [PATCH 2/4] symbols: fix initialization of st->{pti_init, + kaiser}_vmlinux + +In numeric_forward(), care must be taken both for x- and y- positions, +but either of kaiser_init and pti_init is only for x- or y- position +only. Fix this. Also, move the code in an appropriate position +according to each symbol name in the alphabetical order. + +Signed-off-by: HATAYAMA Daisuke +--- + symbols.c | 15 ++++++++++----- + 1 file changed, 10 insertions(+), 5 deletions(-) + +diff --git a/symbols.c b/symbols.c +index b9de4a179d93..2fecaee093a2 100644 +--- a/symbols.c ++++ b/symbols.c +@@ -12692,20 +12692,25 @@ numeric_forward(const void *P_x, const void *P_y) + else if (STREQ(y->name, "idt_table")) + st->idt_table_vmlinux = valueof(y); + ++ if (STREQ(x->name, "kaiser_init")) ++ st->kaiser_init_vmlinux = valueof(x); ++ else if (STREQ(y->name, "kaiser_init")) ++ st->kaiser_init_vmlinux = valueof(y); ++ + if (STREQ(x->name, "linux_banner")) + st->linux_banner_vmlinux = valueof(x); + else if (STREQ(y->name, "linux_banner")) + st->linux_banner_vmlinux = valueof(y); + ++ if (STREQ(x->name, "pti_init")) ++ st->pti_init_vmlinux = valueof(x); ++ else if (STREQ(y->name, "pti_init")) ++ st->pti_init_vmlinux = valueof(y); ++ + if (STREQ(x->name, "saved_command_line")) + st->saved_command_line_vmlinux = valueof(x); + else if (STREQ(y->name, "saved_command_line")) + st->saved_command_line_vmlinux = valueof(y); +- +- if (STREQ(x->name, "pti_init")) +- st->pti_init_vmlinux = valueof(x); +- else if (STREQ(y->name, "kaiser_init")) +- st->kaiser_init_vmlinux = valueof(y); + } + + xs = bfd_get_section(x); +-- +2.7.4 + + +From ff45c8da8cafed350940b1a56dce65f58051db5e Mon Sep 17 00:00:00 2001 +From: HATAYAMA Daisuke +Date: Mon, 27 Jul 2020 19:00:22 +0900 +Subject: [PATCH 3/4] kaslr: cleanup how to set values to the arguments of + calc_kaslr_offset() + +Setting values of the arguments of calc_kaslr_offset() should be done +at the end of the function. Currently, they are set in the middle +where their values could still be changed according to +get_kaslr_offset_from_vmcoreinfo(). This behavior will be problematic +in the later commits when we implement a trial-and-error approach +because the value of kaslr_offset could be passed to the outside of +calc_kaslr_offset() unexpectedly. Thus, fix this first. + +Signed-off-by: HATAYAMA Daisuke +--- + kaslr_helper.c | 22 +++++++++++++--------- + 1 file changed, 13 insertions(+), 9 deletions(-) + +diff --git a/kaslr_helper.c b/kaslr_helper.c +index fe5909caa937..acbb5c2692e2 100644 +--- a/kaslr_helper.c ++++ b/kaslr_helper.c +@@ -394,10 +394,11 @@ quit: + #define PTI_USER_PGTABLE_MASK (1 << PTI_USER_PGTABLE_BIT) + #define CR3_PCID_MASK 0xFFFull + int +-calc_kaslr_offset(ulong *kaslr_offset, ulong *phys_base) ++calc_kaslr_offset(ulong *ko, ulong *pb) + { + uint64_t cr3 = 0, idtr = 0, pgd = 0, idtr_paddr; + ulong divide_error_vmcore; ++ ulong kaslr_offset, phys_base; + ulong kaslr_offset_kdump, phys_base_kdump; + int ret = FALSE; + int verbose = CRASHDEBUG(1)? 1: 0; +@@ -445,9 +446,9 @@ calc_kaslr_offset(ulong *kaslr_offset, ulong *phys_base) + + /* Now we can calculate kaslr_offset and phys_base */ + divide_error_vmcore = get_vec0_addr(idtr_paddr); +- *kaslr_offset = divide_error_vmcore - st->divide_error_vmlinux; +- *phys_base = idtr_paddr - +- (st->idt_table_vmlinux + *kaslr_offset - __START_KERNEL_map); ++ kaslr_offset = divide_error_vmcore - st->divide_error_vmlinux; ++ phys_base = idtr_paddr - ++ (st->idt_table_vmlinux + kaslr_offset - __START_KERNEL_map); + + if (CRASHDEBUG(1)) { + fprintf(fp, "calc_kaslr_offset: idtr=%lx\n", idtr); +@@ -465,9 +466,9 @@ calc_kaslr_offset(ulong *kaslr_offset, ulong *phys_base) + * from vmcoreinfo + */ + if (get_kaslr_offset_from_vmcoreinfo( +- *kaslr_offset, &kaslr_offset_kdump, &phys_base_kdump)) { +- *kaslr_offset = kaslr_offset_kdump; +- *phys_base = phys_base_kdump; ++ kaslr_offset, &kaslr_offset_kdump, &phys_base_kdump)) { ++ kaslr_offset = kaslr_offset_kdump; ++ phys_base = phys_base_kdump; + } else if (CRASHDEBUG(1)) { + fprintf(fp, "kaslr_helper: failed to determine which kernel was running at crash,\n"); + fprintf(fp, "kaslr_helper: asssuming the kdump 1st kernel.\n"); +@@ -475,10 +476,13 @@ calc_kaslr_offset(ulong *kaslr_offset, ulong *phys_base) + + if (CRASHDEBUG(1)) { + fprintf(fp, "calc_kaslr_offset: kaslr_offset=%lx\n", +- *kaslr_offset); +- fprintf(fp, "calc_kaslr_offset: phys_base=%lx\n", *phys_base); ++ kaslr_offset); ++ fprintf(fp, "calc_kaslr_offset: phys_base=%lx\n", phys_base); + } + ++ *ko = kaslr_offset; ++ *pb = phys_base; ++ + ret = TRUE; + quit: + vt->kernel_pgd[0] = 0; +-- +2.7.4 + + +From 8b50d94ada21f403665a5e562f40191f111e0313 Mon Sep 17 00:00:00 2001 +From: HATAYAMA Daisuke +Date: Mon, 27 Jul 2020 19:00:23 +0900 +Subject: [PATCH 4/4] kaslr: fix failure of calculating kaslr_offset due to an + sadump format restriction + +We faced recently a memory dump collected by sadump where unused part +of register values are non-zero. For the crash dump, calculating +kaslr_offset fails because it is based on the assumption that unused +part of register values in the sadump format are always zero cleared. + +The problem is that used and unused part of register values are +rigorously indistinguishable in the sadump format. Although there is +kernel data structure that represents a map between logical cpu +numbers and lapic ids, they cannot be used in order to calculate +kaslr_offset. + +To fix this, we have no choice but use a trial-and-error approach: try +to use each entry of register values in order until we find a good +pair of cr3 and idtr by which we can refer to linux_banner symbol as +expected. + +This fix is for the sadump specific issue, so there is no functional +change for the other crash dump formats. + + [ lijiang: adjust the code indent. ] + +Signed-off-by: HATAYAMA Daisuke +--- + kaslr_helper.c | 39 +++++++++++++++++++++++++++++++++++---- + sadump.c | 52 ++++++++++++++++++++++++++++------------------------ + 2 files changed, 63 insertions(+), 28 deletions(-) + +diff --git a/kaslr_helper.c b/kaslr_helper.c +index acbb5c2692e2..bb19e548d04e 100644 +--- a/kaslr_helper.c ++++ b/kaslr_helper.c +@@ -406,6 +406,7 @@ calc_kaslr_offset(ulong *ko, ulong *pb) + if (!machine_type("X86_64")) + return FALSE; + ++retry: + if (SADUMP_DUMPFILE()) { + if (!sadump_get_cr3_idtr(&cr3, &idtr)) + return FALSE; +@@ -437,12 +438,20 @@ calc_kaslr_offset(ulong *ko, ulong *pb) + machdep->machspec->pgdir_shift = PGDIR_SHIFT; + machdep->machspec->ptrs_per_pgd = PTRS_PER_PGD; + if (!readmem(pgd, PHYSADDR, machdep->pgd, PAGESIZE(), +- "pgd", RETURN_ON_ERROR)) +- goto quit; ++ "pgd", RETURN_ON_ERROR)) { ++ if (SADUMP_DUMPFILE()) ++ goto retry; ++ else ++ goto quit; ++ } + + /* Convert virtual address of IDT table to physical address */ +- if (!kvtop(NULL, idtr, &idtr_paddr, verbose)) +- goto quit; ++ if (!kvtop(NULL, idtr, &idtr_paddr, verbose)) { ++ if (SADUMP_DUMPFILE()) ++ goto retry; ++ else ++ goto quit; ++ } + + /* Now we can calculate kaslr_offset and phys_base */ + divide_error_vmcore = get_vec0_addr(idtr_paddr); +@@ -450,6 +459,28 @@ calc_kaslr_offset(ulong *ko, ulong *pb) + phys_base = idtr_paddr - + (st->idt_table_vmlinux + kaslr_offset - __START_KERNEL_map); + ++ if (SADUMP_DUMPFILE()) { ++ char buf[sizeof("Linux version")]; ++ ulong linux_banner_paddr; ++ ++ if (!kvtop(NULL, ++ st->linux_banner_vmlinux + kaslr_offset, ++ &linux_banner_paddr, ++ verbose)) ++ goto retry; ++ ++ if (!readmem(linux_banner_paddr, ++ PHYSADDR, ++ buf, ++ sizeof(buf), ++ "linux_banner", ++ RETURN_ON_ERROR)) ++ goto retry; ++ ++ if (!STRNEQ(buf, "Linux version")) ++ goto retry; ++ } ++ + if (CRASHDEBUG(1)) { + fprintf(fp, "calc_kaslr_offset: idtr=%lx\n", idtr); + fprintf(fp, "calc_kaslr_offset: pgd=%lx\n", pgd); +diff --git a/sadump.c b/sadump.c +index 35f7cf0fcf8f..009e17a4a44a 100644 +--- a/sadump.c ++++ b/sadump.c +@@ -1664,29 +1664,32 @@ get_sadump_data(void) + static int + get_sadump_smram_cpu_state_any(struct sadump_smram_cpu_state *smram) + { +- ulong offset; +- struct sadump_header *sh = sd->dump_header; +- int apicid; +- struct sadump_smram_cpu_state scs, zero; +- +- offset = sd->sub_hdr_offset + sizeof(uint32_t) + +- sd->dump_header->nr_cpus * sizeof(struct sadump_apic_state); +- +- memset(&zero, 0, sizeof(zero)); +- +- for (apicid = 0; apicid < sh->nr_cpus; ++apicid) { +- if (!read_device(&scs, sizeof(scs), &offset)) { +- error(INFO, "sadump: cannot read sub header " +- "cpu_state\n"); +- return FALSE; +- } +- if (memcmp(&scs, &zero, sizeof(scs)) != 0) { +- *smram = scs; +- return TRUE; +- } +- } +- +- return FALSE; ++ ulong offset; ++ struct sadump_header *sh = sd->dump_header; ++ static int apicid; ++ struct sadump_smram_cpu_state scs; ++ ++ if (apicid >= sh->nr_cpus) ++ return FALSE; ++ ++ offset = sd->sub_hdr_offset + sizeof(uint32_t) + ++ sd->dump_header->nr_cpus * sizeof(struct sadump_apic_state) + ++ apicid * sizeof(scs); ++ ++ while (apicid < sh->nr_cpus) { ++ apicid++; ++ if (!read_device(&scs, sizeof(scs), &offset)) { ++ error(INFO, "sadump: cannot read sub header " ++ "cpu_state\n"); ++ return FALSE; ++ } ++ if (scs.Cr3 && (scs.IdtUpper || scs.IdtLower)) { ++ *smram = scs; ++ return TRUE; ++ } ++ } ++ ++ return FALSE; + } + + int +@@ -1695,7 +1698,8 @@ sadump_get_cr3_idtr(ulong *cr3, ulong *idtr) + struct sadump_smram_cpu_state scs; + + memset(&scs, 0, sizeof(scs)); +- get_sadump_smram_cpu_state_any(&scs); ++ if (!get_sadump_smram_cpu_state_any(&scs)) ++ return FALSE; + + *cr3 = scs.Cr3; + *idtr = ((uint64_t)scs.IdtUpper)<<32 | (uint64_t)scs.IdtLower; +-- +2.7.4 + diff --git a/SOURCES/lzo_snappy.patch b/SOURCES/lzo_snappy.patch index 61af0cc..88ab067 100644 --- a/SOURCES/lzo_snappy.patch +++ b/SOURCES/lzo_snappy.patch @@ -1,16 +1,7 @@ ---- crash-7.1.5/diskdump.c.orig -+++ crash-7.1.5/diskdump.c -@@ -23,6 +23,8 @@ - * GNU General Public License for more details. - */ - -+#define LZO -+#define SNAPPY - #include "defs.h" - #include "diskdump.h" - #include "xen_dom0.h" ---- crash-7.1.5/Makefile.orig -+++ crash-7.1.5/Makefile +diff --git crash-7.2.8/Makefile crash-7.2.8/Makefile +index 745541012f43..d0574d8f07d3 100644 +--- crash-7.2.8/Makefile ++++ crash-7.2.8/Makefile @@ -228,7 +228,7 @@ all: make_configure gdb_merge: force @if [ ! -f ${GDB}/README ]; then \ @@ -20,3 +11,16 @@ @echo "../../${PROGRAM} ../../${PROGRAM}lib.a" > ${GDB}/gdb/mergeobj @rm -f ${PROGRAM} @if [ ! -f ${GDB}/config.status ]; then \ +diff --git crash-7.2.8/diskdump.c crash-7.2.8/diskdump.c +index e88243e616cc..9ccf7039231b 100644 +--- crash-7.2.8/diskdump.c ++++ crash-7.2.8/diskdump.c +@@ -23,6 +23,8 @@ + * GNU General Public License for more details. + */ + ++#define LZO ++#define SNAPPY + #include "defs.h" + #include "diskdump.h" + #include "xen_dom0.h" diff --git a/SOURCES/rhel8_build.patch b/SOURCES/rhel8_build.patch index 33bdb99..864d6ae 100644 --- a/SOURCES/rhel8_build.patch +++ b/SOURCES/rhel8_build.patch @@ -1,5 +1,7 @@ ---- crash-7.2.3/Makefile.orig -+++ crash-7.2.3/Makefile +diff --git crash-7.2.8/Makefile crash-7.2.8/Makefile +index d0574d8f07d3..9dbb61d0dbc8 100644 +--- crash-7.2.8/Makefile ++++ crash-7.2.8/Makefile @@ -198,7 +198,7 @@ GDB_FLAGS= # TARGET_CFLAGS will be configured automatically by configure TARGET_CFLAGS= @@ -7,7 +9,7 @@ -CRASH_CFLAGS=-g -D${TARGET} ${TARGET_CFLAGS} ${GDB_FLAGS} ${CFLAGS} +CRASH_CFLAGS=-g -D${TARGET} ${TARGET_CFLAGS} ${GDB_FLAGS} ${CFLAGS} ${CPPFLAGS} -fPIE - GPL_FILES=COPYING3 + GPL_FILES= TAR_FILES=${SOURCE_FILES} Makefile ${GPL_FILES} README .rh_rpm_package crash.8 \ @@ -228,7 +228,7 @@ all: make_configure gdb_merge: force @@ -18,15 +20,16 @@ @echo "../../${PROGRAM} ../../${PROGRAM}lib.a" > ${GDB}/gdb/mergeobj @rm -f ${PROGRAM} @if [ ! -f ${GDB}/config.status ]; then \ ---- crash-7.2.3/configure.c.orig -+++ crash-7.2.3/configure.c -@@ -780,7 +780,8 @@ build_configure(struct supported_gdb_ver +diff --git crash-7.2.8/configure.c crash-7.2.8/configure.c +index 75006e881f5a..06c94d58c56c 100644 +--- crash-7.2.8/configure.c ++++ crash-7.2.8/configure.c +@@ -780,7 +780,8 @@ build_configure(struct supported_gdb_version *sp) fprintf(fp2, "%s\n", sp->GDB); sprintf(target_data.gdb_version, "%s", &sp->GDB[4]); } else if (strncmp(buf, "LDFLAGS=", strlen("LDFLAGS=")) == 0) { - fprintf(fp2, "LDFLAGS=%s\n", ldflags ? ldflags : ""); + if (ldflags) -+ fprintf(fp2, "LDFLAGS=%s\n", ldflags ? ldflags : ""); ++ fprintf(fp2, "LDFLAGS=%s\n", ldflags ? ldflags : ""); } else fprintf(fp2, "%s", buf); - diff --git a/SPECS/crash.spec b/SPECS/crash.spec index a0c8969..e20f26b 100644 --- a/SPECS/crash.spec +++ b/SPECS/crash.spec @@ -3,21 +3,26 @@ # Summary: Kernel analysis utility for live systems, netdump, diskdump, kdump, LKCD or mcore dumpfiles Name: crash -Version: 7.2.7 -Release: 3%{?dist} +Version: 7.2.8 +Release: 7%{?dist} License: GPLv3 Group: Development/Debuggers -Source: http://people.redhat.com/anderson/crash-%{version}.tar.gz -URL: http://people.redhat.com/anderson +Source0: https://github.com/crash-utility/crash/archive/crash-%{version}.tar.gz +Source1: http://ftp.gnu.org/gnu/gdb/gdb-7.6.tar.gz +URL: https://crash-utility.github.io ExclusiveOS: Linux ExclusiveArch: %{ix86} ia64 x86_64 ppc ppc64 s390 s390x %{arm} aarch64 ppc64le Buildroot: %{_tmppath}/%{name}-%{version}-%{release}-buildroot-%(%{__id_u} -n) BuildRequires: ncurses-devel zlib-devel lzo-devel bison snappy-devel Requires: binutils +Provides: bundled(gdb) = 7.6 Patch0: lzo_snappy.patch Patch1: rhel8_build.patch -Patch2: github_105a3e13_to_b5c2359f.patch -Patch3: github_5cbb2fd8_to_6c1c8ac6.patch +Patch2: github_b80b16549e24.patch +Patch3: github_0f29a8ac6b73.patch +Patch4: github_1c45cea02df7.patch +Patch5: github_9596b4388ea5.patch +Patch6: github_b97e7fd4e826_to_8b50d94ada21.patch %description The core analysis suite is a self-contained tool that can be used to @@ -40,11 +45,16 @@ offered by Mission Critical Linux, or the LKCD kernel patch. %setup -n %{name}-%{version} -q %patch0 -p1 -b lzo_snappy.patch %patch1 -p1 -b rhel8_build.patch -%patch2 -p1 -b github_105a3e13_to_b5c2359f.patch -%patch3 -p1 -b github_5cbb2fd8_to_6c1c8ac6.patch +%patch2 -p1 -b github_b80b16549e24.patch +%patch3 -p1 -b github_0f29a8ac6b73.patch +%patch4 -p1 -b github_1c45cea02df7.patch +%patch5 -p1 -b github_9596b4388ea5.patch +%patch6 -p1 -b github_b97e7fd4e826_to_8b50d94ada21.patch %build -make RPMPKG="%{version}-%{release}" CFLAGS="%{optflags}" +cp %{SOURCE1} . +#make RPMPKG="%{version}-%{release}" CFLAGS="%{optflags}" +make RPMPKG="%{version}-%{release}" CFLAGS="%{optflags}" LDFLAGS="%{build_ldflags}" %install rm -rf %{buildroot} @@ -70,6 +80,34 @@ rm -rf %{buildroot} %{_includedir}/* %changelog +* Mon Aug 17 2020 Bhupesh Sharma - 7.2.8-7 +- crash/sadump, kaslr: fix failure of calculating kaslr_offset due to an sadump format restriction + Resolves: rhbz#1855527 + +* Fri Aug 7 2020 Bhupesh Sharma - 7.2.8-6 +- aarch64: Revert to reading CONFIG_ARM64_USER_VA_BITS_52 and CONFIG_ARM64_PA_BITS=52 for 52-bit VA/PA space. + Resolves: rhbz#1861086 + +* Mon Jul 27 2020 Bhupesh Sharma - 7.2.8-5 +- aarch64: Support reading extended 52-bit address space via crash-utility + Resolves: rhbz#1861086 + +* Fri Jul 10 2020 Bhupesh Sharma - 7.2.8-4 +- Replace people.redhat.com references with github equivalents. + Resolves: rhbz#1851745 + +* Mon Jun 22 2020 Bhupesh Sharma - 7.2.8-3 +- Fix for reading compressed kdump dumpfiles from systems with physical memory + Resolves: rhbz#1819606 + +* Mon Jun 8 2020 Bhupesh Sharma - 7.2.8-2 +- Remove wget from BuildRequires section + Resolves: rhbz#1838322 + +* Fri Jun 5 2020 Bhupesh Sharma - 7.2.8-1 +- Rebase to latest upstream release 7.2.8 + Resolves: rhbz#1838322 + * Mon Feb 3 2020 Dave Anderson - 7.2.7-3 - Rebase to github commit 6c1c8ac6 Resolves: rhbz#1738619