Blob Blame History Raw
From 5bab3f22077843d68deba6a0b4775de98a6edff7 Mon Sep 17 00:00:00 2001
From: Bhupesh Sharma <bhsharma@redhat.com>
Date: Wed, 26 Dec 2018 16:16:30 +0530
Subject: [PATCH] arm64: Rework info->page_offset

    [PATCH] arm64: restore info->page_offset and implement paddr_to_vaddr_arm64()
    
    commit 94c97db3 (arm64: Get 'info->page_offset' from PT_LOAD segments
    to support KASLR boot cases) added a method to determine info->page_offset
    (PAGE_OFFSET) from PT_LOAD segments for arm64 platforms to support
    --mem-usage option, but its hardcoded condition did not work correctly
    on several systems.
    
    This patch restores the method to determine PAGE_OFFSET value, which
    is same as kernel's definition, and determine info->phys_offset from
    PT_LOAD by using PAGE_OFFSET. With these two values, implement
    paddr_to_vaddr_arm64() to support --mem-usage option.
    
    Tested-by: Bhupesh Sharma <bhsharma@redhat.com>
    Signed-off-by: Kazuhito Hagio <k-hagio@ab.jp.nec.com>

Signed-off-by: Bhupesh Sharma <bhsharma@redhat.com>
---
 arch/arm64.c   | 34 +++++++++++++++++++++++++++++-----
 makedumpfile.c |  4 ++++
 makedumpfile.h |  4 +++-
 3 files changed, 36 insertions(+), 6 deletions(-)

diff --git a/makedumpfile-1.6.4/arch/arm64.c b/makedumpfile-1.6.4/arch/arm64.c
index 302c18d1d8b6..053519359cbc 100644
--- a/makedumpfile-1.6.4/arch/arm64.c
+++ b/makedumpfile-1.6.4/arch/arm64.c
@@ -174,11 +174,35 @@ get_kvbase_arm64(void)
 int
 get_phys_base_arm64(void)
 {
-	info->phys_base = NUMBER(PHYS_OFFSET);
+	int i;
+	unsigned long long phys_start;
+	unsigned long long virt_start;
+
+	if (NUMBER(PHYS_OFFSET) != NOT_FOUND_NUMBER) {
+		info->phys_base = NUMBER(PHYS_OFFSET);
+		DEBUG_MSG("phys_base    : %lx (vmcoreinfo)\n",
+				info->phys_base);
+		return TRUE;
+	}
 
-	DEBUG_MSG("phys_base    : %lx\n", info->phys_base);
+	if (get_num_pt_loads() && PAGE_OFFSET) {
+		for (i = 0;
+		    get_pt_load(i, &phys_start, NULL, &virt_start, NULL);
+		    i++) {
+			if (virt_start != NOT_KV_ADDR
+			    && virt_start >= PAGE_OFFSET
+			    && phys_start != NOT_PADDR) {
+				info->phys_base = phys_start -
+					(virt_start & ~PAGE_OFFSET);
+				DEBUG_MSG("phys_base    : %lx (pt_load)\n",
+						info->phys_base);
+				return TRUE;
+			}
+		}
+	}
 
-	return TRUE;
+	ERRMSG("Cannot determine phys_base\n");
+	return FALSE;
 }
 
 unsigned long
@@ -332,8 +356,8 @@ get_versiondep_info_arm64(void)
 
 	info->page_offset = (0xffffffffffffffffUL) << (va_bits - 1);
 
-	DEBUG_MSG("page_offset=%lx, va_bits=%d\n", info->page_offset,
-			va_bits);
+	DEBUG_MSG("va_bits      : %d\n", va_bits);
+	DEBUG_MSG("page_offset  : %lx\n", info->page_offset);
 
 	return TRUE;
 }
diff --git a/makedumpfile-1.6.4/makedumpfile.c b/makedumpfile-1.6.4/makedumpfile.c
index 5fa945d30c72..c9a6efd35a24 100644
--- a/makedumpfile-1.6.4/makedumpfile.c
+++ b/makedumpfile-1.6.4/makedumpfile.c
@@ -11214,6 +11214,10 @@ int show_mem_usage(void)
 	if (!get_page_offset())
 		return FALSE;
 
+	/* paddr_to_vaddr() on arm64 needs phys_base. */
+	if (!get_phys_base())
+		return FALSE;
+
 	if (!get_sys_kernel_vmcoreinfo(&vmcoreinfo_addr, &vmcoreinfo_len))
 		return FALSE;
 
diff --git a/makedumpfile-1.6.4/makedumpfile.h b/makedumpfile-1.6.4/makedumpfile.h
index 593ed71dafe3..b30f62b6bdf2 100644
--- a/makedumpfile-1.6.4/makedumpfile.h
+++ b/makedumpfile-1.6.4/makedumpfile.h
@@ -972,9 +972,11 @@ int get_versiondep_info_arm64(void);
 int get_xen_basic_info_arm64(void);
 int get_xen_info_arm64(void);
 unsigned long get_kaslr_offset_arm64(unsigned long vaddr);
+#define paddr_to_vaddr_arm64(X) (((X) - info->phys_base) | PAGE_OFFSET)
+
 #define find_vmemmap()		stub_false()
 #define vaddr_to_paddr(X)	vaddr_to_paddr_arm64(X)
-#define paddr_to_vaddr(X)	paddr_to_vaddr_general(X)
+#define paddr_to_vaddr(X)	paddr_to_vaddr_arm64(X)
 #define get_phys_base()		get_phys_base_arm64()
 #define get_machdep_info()	get_machdep_info_arm64()
 #define get_versiondep_info()	get_versiondep_info_arm64()
-- 
2.7.4