[Crash-utility] [PATCH] Fix for an abort in vm_stat_init() without CONFIG_NUMA
Dave Anderson
anderson at redhat.com
Wed Aug 22 17:27:37 UTC 2018
----- Original Message -----
> With recent kernels without CONFIG_NUMA (including Fedora 32-bit),
> the vm_stat_init() function aborts when getting numa_stat_item
> enum items, (probably) because it is not defined.
>
> crash> kmem -V
> double free or corruption (!prev)
> Aborted (core dumped)
>
> We can avoid the abort by checking whether the length of the
> vm_numa_stat array is also not zero.
>
> This patch tested OK with the following kernels:
> 4.17.0-0.rc5.git3.1.fc29.i686
> 4.18.0-0.rc5.git4.1.fc29.x86_64
> 3.10.0-862.el7.x86_64
>
> Signed-off-by: Kazuhito Hagio <k-hagio at ab.jp.nec.com>
Thanks Kazu, looks good. Queued for crash-7.2.4:
https://github.com/crash-utility/crash/commit/d2a164e5f1b774f2b8aec137a2ad9c7eb905b650
Dave
> ---
> defs.h | 1 +
> memory.c | 10 ++++++----
> symbols.c | 4 ++++
> 3 files changed, 11 insertions(+), 4 deletions(-)
>
> diff --git a/defs.h b/defs.h
> index f569a62..6fdb478 100644
> --- a/defs.h
> +++ b/defs.h
> @@ -2220,6 +2220,7 @@ struct array_table {
> int height_to_maxnodes;
> int task_struct_rlim;
> int signal_struct_rlim;
> + int vm_numa_stat;
> };
>
> /*
> diff --git a/memory.c b/memory.c
> index 7c0cb5f..e02ba68 100644
> --- a/memory.c
> +++ b/memory.c
> @@ -17454,11 +17454,12 @@ vm_stat_init(void)
> } else if (symbol_exists("vm_zone_stat") &&
> get_symbol_type("vm_zone_stat",
> NULL, NULL) == TYPE_CODE_ARRAY) {
> - if (symbol_exists("vm_numa_stat")) {
> + if (symbol_exists("vm_numa_stat") &&
> + get_array_length("vm_numa_stat", NULL, 0)) {
> vt->nr_vm_stat_items =
> get_array_length("vm_zone_stat", NULL, 0)
> + get_array_length("vm_node_stat", NULL, 0)
> - + get_array_length("vm_numa_stat", NULL, 0);
> + + ARRAY_LENGTH(vm_numa_stat);
> split_vmstat = 2;
> enumerator_value("NR_VM_ZONE_STAT_ITEMS", &zone_cnt);
> enumerator_value("NR_VM_NODE_STAT_ITEMS", &node_cnt);
> @@ -17599,7 +17600,7 @@ dump_vm_stat(char *item, long *retval, ulong zone)
> buf = GETBUF(sizeof(ulong) * vt->nr_vm_stat_items);
>
> if (symbol_exists("vm_node_stat") && symbol_exists("vm_zone_stat") &&
> - symbol_exists("vm_numa_stat"))
> + symbol_exists("vm_numa_stat") && ARRAY_LENGTH(vm_numa_stat))
> split_vmstat = 2;
> else if (symbol_exists("vm_node_stat") && symbol_exists("vm_zone_stat"))
> split_vmstat = 1;
> @@ -17666,7 +17667,8 @@ dump_vm_stat(char *item, long *retval, ulong zone)
> if (!zone) {
> if ((i == node_start) && symbol_exists("vm_node_stat"))
> fprintf(fp, "\n VM_NODE_STAT:\n");
> - if ((i == numa_start) && symbol_exists("vm_numa_stat"))
> + if ((i == numa_start) && symbol_exists("vm_numa_stat")
> + && ARRAY_LENGTH(vm_numa_stat))
> fprintf(fp, "\n VM_NUMA_STAT:\n");
> }
> fprintf(fp, "%s%s: %ld\n",
> diff --git a/symbols.c b/symbols.c
> index df84ee2..bee60ba 100644
> --- a/symbols.c
> +++ b/symbols.c
> @@ -8457,6 +8457,8 @@ builtin_array_length(char *s, int len, int *two_dim)
> lenptr = &array_table.task_struct_rlim;
> else if (STREQ(s, "signal_struct.rlim"))
> lenptr = &array_table.signal_struct_rlim;
> + else if (STREQ(s, "vm_numa_stat"))
> + lenptr = &array_table.vm_numa_stat;
>
> if (!lenptr) /* not stored */
> return(len);
> @@ -10594,6 +10596,8 @@ dump_offset_table(char *spec, ulong makestruct)
> ARRAY_LENGTH(task_struct_rlim));
> fprintf(fp, " signal_struct_rlim: %d\n",
> ARRAY_LENGTH(signal_struct_rlim));
> + fprintf(fp, " vm_numa_stat: %d\n",
> + ARRAY_LENGTH(vm_numa_stat));
>
> if (spec) {
> int in_size_table, in_array_table, arrays, offsets, sizes;
> --
> 1.8.3.1
>
> --
> Crash-utility mailing list
> Crash-utility at redhat.com
> https://www.redhat.com/mailman/listinfo/crash-utility
>
More information about the Crash-utility
mailing list