[PATCH v8 6/6] s390/vmcore: Use vmcore for zfcpdump

2013-07-23 Thread Michael Holzheu
This patch modifies the s390 copy_oldmem_page() and remap_oldmem_pfn_range()
function for zfcpdump to read from the HSA memory if memory below HSA_SIZE
bytes is requested. Otherwise real memory is used.

Signed-off-by: Michael Holzheu 
---
 arch/s390/Kconfig |   3 +-
 arch/s390/include/asm/sclp.h  |   1 +
 arch/s390/kernel/crash_dump.c | 122 +++---
 drivers/s390/char/zcore.c |   6 +--
 4 files changed, 110 insertions(+), 22 deletions(-)

diff --git a/arch/s390/Kconfig b/arch/s390/Kconfig
index 22f75b5..f88bdac 100644
--- a/arch/s390/Kconfig
+++ b/arch/s390/Kconfig
@@ -514,6 +514,7 @@ config CRASH_DUMP
bool "kernel crash dumps"
depends on 64BIT && SMP
select KEXEC
+   select ZFCPDUMP
help
  Generate crash dump after being started by kexec.
  Crash dump kernels are loaded in the main kernel with kexec-tools
@@ -524,7 +525,7 @@ config CRASH_DUMP
 config ZFCPDUMP
def_bool n
prompt "zfcpdump support"
-   select SMP
+   depends on SMP
help
  Select this option if you want to build an zfcpdump enabled kernel.
  Refer to  for more details on 
this.
diff --git a/arch/s390/include/asm/sclp.h b/arch/s390/include/asm/sclp.h
index 06a1361..7dc7f9c 100644
--- a/arch/s390/include/asm/sclp.h
+++ b/arch/s390/include/asm/sclp.h
@@ -56,5 +56,6 @@ bool sclp_has_linemode(void);
 bool sclp_has_vt220(void);
 int sclp_pci_configure(u32 fid);
 int sclp_pci_deconfigure(u32 fid);
+int memcpy_hsa(void *dest, unsigned long src, size_t count, int mode);
 
 #endif /* _ASM_S390_SCLP_H */
diff --git a/arch/s390/kernel/crash_dump.c b/arch/s390/kernel/crash_dump.c
index 3e77615..c84f33d 100644
--- a/arch/s390/kernel/crash_dump.c
+++ b/arch/s390/kernel/crash_dump.c
@@ -16,6 +16,7 @@
 #include 
 #include 
 #include 
+#include 
 
 #define PTR_ADD(x, y) (((char *) (x)) + ((unsigned long) (y)))
 #define PTR_SUB(x, y) (((char *) (x)) - ((unsigned long) (y)))
@@ -69,22 +70,41 @@ static ssize_t copy_page_real(void *buf, void *src, size_t 
csize)
 static void *elfcorehdr_newmem;
 
 /*
- * Copy one page from "oldmem"
+ * Copy one page from zfcpdump "oldmem"
+ *
+ * For pages below ZFCPDUMP_HSA_SIZE memory from the HSA is copied. Otherwise
+ * real memory copy is used.
+ */
+static ssize_t copy_oldmem_page_zfcpdump(char *buf, size_t csize,
+unsigned long src, int userbuf)
+{
+   int rc;
+
+   if (src < ZFCPDUMP_HSA_SIZE) {
+   rc = memcpy_hsa(buf, src, csize, userbuf);
+   } else {
+   if (userbuf)
+   rc = copy_to_user_real((void __force __user *) buf,
+  (void *) src, csize);
+   else
+   rc = memcpy_real(buf, (void *) src, csize);
+   }
+   return rc ? rc : csize;
+}
+
+/*
+ * Copy one page from kdump "oldmem"
  *
  * For the kdump reserved memory this functions performs a swap operation:
  *  - [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE] is mapped to [0 - OLDMEM_SIZE].
  *  - [0 - OLDMEM_SIZE] is mapped to [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE]
  */
-ssize_t copy_oldmem_page(unsigned long pfn, char *buf,
-size_t csize, unsigned long offset, int userbuf)
+static ssize_t copy_oldmem_page_kdump(char *buf, size_t csize,
+ unsigned long src, int userbuf)
+
 {
-   unsigned long src;
int rc;
 
-   if (!csize)
-   return 0;
-
-   src = (pfn << PAGE_SHIFT) + offset;
if (src < OLDMEM_SIZE)
src += OLDMEM_BASE;
else if (src > OLDMEM_BASE &&
@@ -95,17 +115,35 @@ ssize_t copy_oldmem_page(unsigned long pfn, char *buf,
   (void *) src, csize);
else
rc = copy_page_real(buf, (void *) src, csize);
-   return (rc == 0) ? csize : rc;
+   return (rc == 0) ? rc : csize;
 }
 
 /*
- * Remap "oldmem"
+ * Copy one page from "oldmem"
+ */
+ssize_t copy_oldmem_page(unsigned long pfn, char *buf, size_t csize,
+unsigned long offset, int userbuf)
+{
+   unsigned long src;
+
+   if (!csize)
+   return 0;
+   src = (pfn << PAGE_SHIFT) + offset;
+   if (OLDMEM_BASE)
+   return copy_oldmem_page_kdump(buf, csize, src, userbuf);
+   else
+   return copy_oldmem_page_zfcpdump(buf, csize, src, userbuf);
+}
+
+/*
+ * Remap "oldmem" for kdump
  *
  * For the kdump reserved memory this functions performs a swap operation:
  * [0 - OLDMEM_SIZE] is mapped to [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE]
  */
-int remap_oldmem_pfn_range(struct vm_area_struct *vma, unsigned long from,
-  unsigned long pfn, unsigned long size, pgprot_t prot)
+static int remap_oldmem_pfn_range_kdump(struct vm_area_struct *vma,
+   unsigned long from, unsigned long 

[PATCH v8 6/6] s390/vmcore: Use vmcore for zfcpdump

2013-07-23 Thread Michael Holzheu
This patch modifies the s390 copy_oldmem_page() and remap_oldmem_pfn_range()
function for zfcpdump to read from the HSA memory if memory below HSA_SIZE
bytes is requested. Otherwise real memory is used.

Signed-off-by: Michael Holzheu holz...@linux.vnet.ibm.com
---
 arch/s390/Kconfig |   3 +-
 arch/s390/include/asm/sclp.h  |   1 +
 arch/s390/kernel/crash_dump.c | 122 +++---
 drivers/s390/char/zcore.c |   6 +--
 4 files changed, 110 insertions(+), 22 deletions(-)

diff --git a/arch/s390/Kconfig b/arch/s390/Kconfig
index 22f75b5..f88bdac 100644
--- a/arch/s390/Kconfig
+++ b/arch/s390/Kconfig
@@ -514,6 +514,7 @@ config CRASH_DUMP
bool kernel crash dumps
depends on 64BIT  SMP
select KEXEC
+   select ZFCPDUMP
help
  Generate crash dump after being started by kexec.
  Crash dump kernels are loaded in the main kernel with kexec-tools
@@ -524,7 +525,7 @@ config CRASH_DUMP
 config ZFCPDUMP
def_bool n
prompt zfcpdump support
-   select SMP
+   depends on SMP
help
  Select this option if you want to build an zfcpdump enabled kernel.
  Refer to file:Documentation/s390/zfcpdump.txt for more details on 
this.
diff --git a/arch/s390/include/asm/sclp.h b/arch/s390/include/asm/sclp.h
index 06a1361..7dc7f9c 100644
--- a/arch/s390/include/asm/sclp.h
+++ b/arch/s390/include/asm/sclp.h
@@ -56,5 +56,6 @@ bool sclp_has_linemode(void);
 bool sclp_has_vt220(void);
 int sclp_pci_configure(u32 fid);
 int sclp_pci_deconfigure(u32 fid);
+int memcpy_hsa(void *dest, unsigned long src, size_t count, int mode);
 
 #endif /* _ASM_S390_SCLP_H */
diff --git a/arch/s390/kernel/crash_dump.c b/arch/s390/kernel/crash_dump.c
index 3e77615..c84f33d 100644
--- a/arch/s390/kernel/crash_dump.c
+++ b/arch/s390/kernel/crash_dump.c
@@ -16,6 +16,7 @@
 #include asm/os_info.h
 #include asm/elf.h
 #include asm/ipl.h
+#include asm/sclp.h
 
 #define PTR_ADD(x, y) (((char *) (x)) + ((unsigned long) (y)))
 #define PTR_SUB(x, y) (((char *) (x)) - ((unsigned long) (y)))
@@ -69,22 +70,41 @@ static ssize_t copy_page_real(void *buf, void *src, size_t 
csize)
 static void *elfcorehdr_newmem;
 
 /*
- * Copy one page from oldmem
+ * Copy one page from zfcpdump oldmem
+ *
+ * For pages below ZFCPDUMP_HSA_SIZE memory from the HSA is copied. Otherwise
+ * real memory copy is used.
+ */
+static ssize_t copy_oldmem_page_zfcpdump(char *buf, size_t csize,
+unsigned long src, int userbuf)
+{
+   int rc;
+
+   if (src  ZFCPDUMP_HSA_SIZE) {
+   rc = memcpy_hsa(buf, src, csize, userbuf);
+   } else {
+   if (userbuf)
+   rc = copy_to_user_real((void __force __user *) buf,
+  (void *) src, csize);
+   else
+   rc = memcpy_real(buf, (void *) src, csize);
+   }
+   return rc ? rc : csize;
+}
+
+/*
+ * Copy one page from kdump oldmem
  *
  * For the kdump reserved memory this functions performs a swap operation:
  *  - [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE] is mapped to [0 - OLDMEM_SIZE].
  *  - [0 - OLDMEM_SIZE] is mapped to [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE]
  */
-ssize_t copy_oldmem_page(unsigned long pfn, char *buf,
-size_t csize, unsigned long offset, int userbuf)
+static ssize_t copy_oldmem_page_kdump(char *buf, size_t csize,
+ unsigned long src, int userbuf)
+
 {
-   unsigned long src;
int rc;
 
-   if (!csize)
-   return 0;
-
-   src = (pfn  PAGE_SHIFT) + offset;
if (src  OLDMEM_SIZE)
src += OLDMEM_BASE;
else if (src  OLDMEM_BASE 
@@ -95,17 +115,35 @@ ssize_t copy_oldmem_page(unsigned long pfn, char *buf,
   (void *) src, csize);
else
rc = copy_page_real(buf, (void *) src, csize);
-   return (rc == 0) ? csize : rc;
+   return (rc == 0) ? rc : csize;
 }
 
 /*
- * Remap oldmem
+ * Copy one page from oldmem
+ */
+ssize_t copy_oldmem_page(unsigned long pfn, char *buf, size_t csize,
+unsigned long offset, int userbuf)
+{
+   unsigned long src;
+
+   if (!csize)
+   return 0;
+   src = (pfn  PAGE_SHIFT) + offset;
+   if (OLDMEM_BASE)
+   return copy_oldmem_page_kdump(buf, csize, src, userbuf);
+   else
+   return copy_oldmem_page_zfcpdump(buf, csize, src, userbuf);
+}
+
+/*
+ * Remap oldmem for kdump
  *
  * For the kdump reserved memory this functions performs a swap operation:
  * [0 - OLDMEM_SIZE] is mapped to [OLDMEM_BASE - OLDMEM_BASE + OLDMEM_SIZE]
  */
-int remap_oldmem_pfn_range(struct vm_area_struct *vma, unsigned long from,
-  unsigned long pfn, unsigned long size, pgprot_t prot)
+static int remap_oldmem_pfn_range_kdump(struct vm_area_struct