[Crash-utility] Re: [PATCH] Fix 'rd' command for zram data display in Linux 6.2+

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Chengen,

thank you for the patch.

On 2023/11/09 11:54, Chengen Du wrote:
> A kernel commit 7ac07a26dea7 (zram: preparation for multi-zcomp support)
> in Linux replaces "compressor" with "comp_algs" in the zram struct.
> If not fixed, the issue triggers the following error:
>    rd: WARNING: Some pages are swapped out to zram. Please run mod -s zram.
>    rd: invalid user virtual address: ffff7d23f010  type: "64-bit UVADDR"
> 
> Signed-off-by: Chengen Du <chengen.du@xxxxxxxxxxxxx>
> ---
>   defs.h     |  1 +
>   diskdump.c | 61 +++++++++++++++++++++++++++++++++++-------------------
>   2 files changed, 41 insertions(+), 21 deletions(-)
> 
> diff --git a/defs.h b/defs.h
> index 788f63a..2cae5b6 100644
> --- a/defs.h
> +++ b/defs.h
> @@ -2227,6 +2227,7 @@ struct offset_table {                    /* stash of commonly-used offsets */
>   	long module_memory_size;
>   	long irq_data_irq;
>   	long zspage_huge;
> +	long zram_comp_algs;
>   };
>   
>   struct size_table {         /* stash of commonly-used sizes */
> diff --git a/diskdump.c b/diskdump.c
> index 0fe46f4..0103221 100644
> --- a/diskdump.c
> +++ b/diskdump.c
> @@ -2757,6 +2757,8 @@ diskdump_device_dump_info(FILE *ofp)
>   
>   static ulong ZRAM_FLAG_SHIFT;
>   static ulong ZRAM_FLAG_SAME_BIT;
> +static ulong ZRAM_COMP_PRIORITY_BIT1;
> +static ulong ZRAM_COMP_PRIORITY_MASK;
>   
>   static void
>   zram_init(void)
> @@ -2764,7 +2766,10 @@ zram_init(void)
>   	long zram_flag_shift;
>   
>   	MEMBER_OFFSET_INIT(zram_mempoll, "zram", "mem_pool");
> -	MEMBER_OFFSET_INIT(zram_compressor, "zram", "compressor");
> +	if (THIS_KERNEL_VERSION >= LINUX(6, 2, 0))
> +		MEMBER_OFFSET_INIT(zram_comp_algs, "zram", "comp_algs");
> +	else
> +		MEMBER_OFFSET_INIT(zram_compressor, "zram", "compressor");

Kernel patches can be backported to kernels older than 6.2.0, please 
don't use the kernel version if possible.  So, for example:

   MEMBER_OFFSET_INIT(zram_compressor, "zram", "compressor");
   if (INVALID_MEMBER(zram_compressor))
       MEMBER_OFFSET_INIT(zram_comp_algs, "zram", "comp_algs");

>   	MEMBER_OFFSET_INIT(zram_table_flag, "zram_table_entry", "flags");
>   	if (INVALID_MEMBER(zram_table_flag))
>   		MEMBER_OFFSET_INIT(zram_table_flag, "zram_table_entry", "value");
> @@ -2782,6 +2787,8 @@ zram_init(void)
>   
>   	ZRAM_FLAG_SHIFT = 1 << zram_flag_shift;
>   	ZRAM_FLAG_SAME_BIT = 1 << (zram_flag_shift+1);
> +	ZRAM_COMP_PRIORITY_BIT1 = ZRAM_FLAG_SHIFT + 7;
> +	ZRAM_COMP_PRIORITY_MASK = 0x3;
>   
>   	if (CRASHDEBUG(1))
>   		fprintf(fp, "zram_flag_shift: %ld\n", zram_flag_shift);
> @@ -2980,13 +2987,17 @@ try_zram_decompress(ulonglong pte_val, unsigned char *buf, ulong len, ulonglong
>   	unsigned char *outbuf = NULL;
>   	ulong zram, zram_table_entry, sector, index, entry, flags, size,
>   		outsize, off;
> +	int comp_alg_unavail;
>   
> -	if (INVALID_MEMBER(zram_compressor)) {
> +	comp_alg_unavail = (THIS_KERNEL_VERSION >= LINUX(6, 2, 0))
> +		? INVALID_MEMBER(zram_comp_algs) : INVALID_MEMBER(zram_compressor);

Same as above, for example, this works?

   if (INVALID_MEMBER(zram_comp_algs) && INVALID_MEMBER(zram_compressor))

> +	if (comp_alg_unavail) {
>   		zram_init();
> -		if (INVALID_MEMBER(zram_compressor)) {
> -			error(WARNING,
> -			      "Some pages are swapped out to zram. "
> -			      "Please run mod -s zram.\n");
> +		comp_alg_unavail = (THIS_KERNEL_VERSION >= LINUX(6, 2, 0))
> +			? INVALID_MEMBER(zram_comp_algs) : INVALID_MEMBER(zram_compressor);
> +		if (comp_alg_unavail) {
> +			error(WARNING, "some pages are swapped out to zram. "
> +				"please run mod -s zram.\n");
>   			return 0;
>   		}
>   	}
> @@ -2997,8 +3008,29 @@ try_zram_decompress(ulonglong pte_val, unsigned char *buf, ulong len, ulonglong
>   	if (!get_disk_name_private_data(pte_val, vaddr, NULL, &zram))
>   		return 0;
>   
> -	readmem(zram + OFFSET(zram_compressor), KVADDR, name,
> -		sizeof(name), "zram compressor", FAULT_ON_ERROR);
> +	if (THIS_KERNEL_VERSION >= LINUX(2, 6, 0)) {
> +		swp_offset = (ulonglong)__swp_offset(pte_val);
> +	} else {
> +		swp_offset = (ulonglong)SWP_OFFSET(pte_val);
> +	}
> +
> +	sector = swp_offset << (PAGESHIFT() - 9);
> +	index = sector >> SECTORS_PER_PAGE_SHIFT;
> +	readmem(zram, KVADDR, &zram_table_entry,
> +		sizeof(void *), "zram_table_entry", FAULT_ON_ERROR);
> +	zram_table_entry += (index * SIZE(zram_table_entry));
> +	readmem(zram_table_entry + OFFSET(zram_table_flag), KVADDR, &flags,
> +		sizeof(void *), "zram_table_flag", FAULT_ON_ERROR);
> +	if (THIS_KERNEL_VERSION >= LINUX(6, 2, 0)) {

Same as above.

Thanks,
Kazu

> +		ulong comp_alg_addr;
> +		uint32_t prio = (flags >> ZRAM_COMP_PRIORITY_BIT1) & ZRAM_COMP_PRIORITY_MASK;
> +		readmem(zram + OFFSET(zram_comp_algs) + sizeof(const char *) * prio, KVADDR,
> +			&comp_alg_addr, sizeof(comp_alg_addr), "zram comp_algs", FAULT_ON_ERROR);
> +		read_string(comp_alg_addr, name, sizeof(name));
> +	} else {
> +		readmem(zram + OFFSET(zram_compressor), KVADDR, name, sizeof(name),
> +			"zram compressor", FAULT_ON_ERROR);
> +	}
>   	if (STREQ(name, "lzo")) {
>   #ifdef LZO
>   		if (!(dd->flags & LZO_SUPPORTED)) {
> @@ -3019,12 +3051,6 @@ try_zram_decompress(ulonglong pte_val, unsigned char *buf, ulong len, ulonglong
>   		return 0;
>   	}
>   
> -	if (THIS_KERNEL_VERSION >= LINUX(2, 6, 0)) {
> -		swp_offset = (ulonglong)__swp_offset(pte_val);
> -	} else {
> -		swp_offset = (ulonglong)SWP_OFFSET(pte_val);
> -	}
> -
>   	zram_buf = (unsigned char *)GETBUF(PAGESIZE());
>   	/* lookup page from swap cache */
>   	off = PAGEOFFSET(vaddr);
> @@ -3034,15 +3060,8 @@ try_zram_decompress(ulonglong pte_val, unsigned char *buf, ulong len, ulonglong
>   		goto out;
>   	}
>   
> -	sector = swp_offset << (PAGESHIFT() - 9);
> -	index = sector >> SECTORS_PER_PAGE_SHIFT;
> -	readmem(zram, KVADDR, &zram_table_entry,
> -		sizeof(void *), "zram_table_entry", FAULT_ON_ERROR);
> -	zram_table_entry += (index * SIZE(zram_table_entry));
>   	readmem(zram_table_entry, KVADDR, &entry,
>   		sizeof(void *), "entry of table", FAULT_ON_ERROR);
> -	readmem(zram_table_entry + OFFSET(zram_table_flag), KVADDR, &flags,
> -		sizeof(void *), "zram_table_flag", FAULT_ON_ERROR);
>   	if (!entry || (flags & ZRAM_FLAG_SAME_BIT)) {
>   		int count;
>   		ulong *same_buf = (ulong *)GETBUF(PAGESIZE());
--
Crash-utility mailing list -- devel@xxxxxxxxxxxxxxxxxxxxxxxxxxx
To unsubscribe send an email to devel-leave@xxxxxxxxxxxxxxxxxxxxxxxxxxx
%(web_page_url)slistinfo%(cgiext)s/%(_internal_name)s
Contribution Guidelines: https://github.com/crash-utility/crash/wiki




[Index of Archives]     [Fedora Development]     [Fedora Desktop]     [Fedora SELinux]     [Yosemite News]     [KDE Users]     [Fedora Tools]

 

Powered by Linux