[OpenBIOS] [PATCH 08/11] ppc: use proper context when pre-loading kernels

Mark Cave-Ayland mark.cave-ayland at ilande.co.uk
Sat May 26 21:29:53 CEST 2018


Before the introduction of proper init-program contexts, OpenBIOS
used a simple assembler call_elf() function to execute the guest
kernel directly.

Switch over to using proper contexts via arch_init_program() which
enables us to remove the legacy call_elf() completely.

Signed-off-by: Mark Cave-Ayland <mark.cave-ayland at ilande.co.uk>
---
 arch/ppc/qemu/kernel.h |  1 -
 arch/ppc/qemu/main.c   | 11 ++++++++++-
 arch/ppc/qemu/switch.S | 43 -------------------------------------------
 3 files changed, 10 insertions(+), 45 deletions(-)

diff --git a/arch/ppc/qemu/kernel.h b/arch/ppc/qemu/kernel.h
index 3e25a56..0ded835 100644
--- a/arch/ppc/qemu/kernel.h
+++ b/arch/ppc/qemu/kernel.h
@@ -23,7 +23,6 @@ extern void		exit( int status ) __attribute__ ((noreturn));
 extern void 		flush_icache_range( char *start, char *stop );
 extern void 		flush_dcache_range( char *start, char *stop );
 extern char		of_rtas_start[], of_rtas_end[];
-extern void             call_elf( unsigned long arg1, unsigned long arg2, unsigned long elf_entry );
 
 /* methods.c */
 extern void		node_methods_init( const char *cpuname );
diff --git a/arch/ppc/qemu/main.c b/arch/ppc/qemu/main.c
index 44b1666..3c76e41 100644
--- a/arch/ppc/qemu/main.c
+++ b/arch/ppc/qemu/main.c
@@ -24,6 +24,8 @@
 #include "kernel.h"
 #include "drivers/drivers.h"
 #include "libopenbios/ofmem.h"
+#include "libopenbios/initprogram.h"
+#include "context.h"
 #define NO_QEMU_PROTOS
 #include "arch/common/fw_cfg.h"
 
@@ -45,6 +47,7 @@ static void check_preloaded_kernel(void)
     unsigned long kernel_image, kernel_size;
     unsigned long initrd_image, initrd_size;
     const char * kernel_cmdline;
+    volatile struct context *ctx = __context;
 
     kernel_size = fw_cfg_read_i32(FW_CFG_KERNEL_SIZE);
     if (kernel_size) {
@@ -61,7 +64,13 @@ static void check_preloaded_kernel(void)
 	       ph = find_dev("/chosen");
                set_property(ph, "bootargs", strdup(kernel_cmdline), strlen(kernel_cmdline) + 1);
         }
-        call_elf(initrd_image, initrd_size, kernel_image);
+
+        arch_init_program();
+        ctx->regs[REG_R3] = initrd_image;
+        ctx->regs[REG_R4] = initrd_size;
+        ctx->pc = kernel_image;
+
+        start_elf();
     }
 }
 
diff --git a/arch/ppc/qemu/switch.S b/arch/ppc/qemu/switch.S
index f1b120d..32a7bbf 100644
--- a/arch/ppc/qemu/switch.S
+++ b/arch/ppc/qemu/switch.S
@@ -17,49 +17,6 @@
   #endif
 #endif
 
-	/* According to IEEE 1275, PPC bindings:
-	 *
-	 * 	MSR = FP, ME + (DR|IR)
-	 *	r1 = stack (32 K + 32 bytes link area above)
-	 *	r5 = client interface handler
-	 *	r6 = address of client program arguments (unused)
-	 *	r7 = length of client program arguments (unused)
-         *
-         *      Yaboot and Linux use r3 and r4 for initrd address and size
-	 */
-
-	/* void call_elf( arg1, arg2, entry ) */
-_GLOBAL(call_elf):
-	mflr	r0
-	PPC_STLU r1, -STACKFRAME_MINSIZE(r1)
-	PPC_STL  r0, (STACKFRAME_MINSIZE + PPC_LR_STKOFF)(r1)
-	mtlr	r5
-	LOAD_REG_IMMEDIATE(r8, saved_stack)		// save our stack pointer
-	PPC_STL r1,0(r8)
-	mfsdr1	r1
-	addi	r1, r1, -32768		/* - 32 KiB exception stack */
-	addis	r1, r1, -1			/* - 64 KiB stack */
-	LOAD_REG_IMMEDIATE(r5, of_client_callback)	// r5 = callback
-	li	r6,0			// r6 = address of client program arguments (unused)
-	li	r7,0			// r7 = length of client program arguments (unused)
-	li	r0,MSR_FP | MSR_ME | MSR_DR | MSR_IR
-	MTMSRD(r0)
-	blrl
-
-#ifdef CONFIG_PPC64
-    /* Restore SF bit */
-    LOAD_REG_IMMEDIATE(r0, MSR_SF | MSR_FP | MSR_ME | MSR_DR | MSR_IR)
-    MTMSRD(r0)
-#endif
-	LOAD_REG_IMMEDIATE(r8, saved_stack)		// restore stack pointer
-	mr	r1,r8
-	PPC_LL r0, (STACKFRAME_MINSIZE + PPC_LR_STKOFF)(r1)
-	mtlr	r0
-	addi	r1, r1, STACKFRAME_MINSIZE
-	// XXX: should restore r12-r31 etc..
-	// we should not really come here though
-	blrl
-
 /*
  * Switch execution context
  * This saves registers in the stack, then
-- 
2.11.0




More information about the OpenBIOS mailing list