[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] vexpress-a9 aborts when booting decompress code from a modi
From: |
Ilya Lipnitskiy |
Subject: |
[Qemu-devel] vexpress-a9 aborts when booting decompress code from a modified Linux kernel |
Date: |
Fri, 16 Oct 2015 10:21:46 -0700 |
Hi All,
I am running into a curious issue with QEMU ARM, maybe a Linux/QEMU
ARM expert could help before I filed a bug report. Is this a QEMU
problem or is there a fundamental problem with my kernel change? QEMU
builds before SHA 6ec1588e handle this kernel change just fine...
I'm seeing a very early CPU abort if I add L1 cache invalidation logic
in early Linux decompress code in arch/arm/boot/compressed/head.S.
Essentially, if I add a copy of v7_invalidate_l1 from
arch/arm/mm/cache-v7.S to __armv7_mmu_cache_on in head.S QEMU aborts
somewhere inside the new code. Please see the head.S patch below:
diff --git a/arch/arm/boot/compressed/head.S b/arch/arm/boot/compressed/head.S
index 06e983f..943541f 100644
--- a/arch/arm/boot/compressed/head.S
+++ b/arch/arm/boot/compressed/head.S
@@ -753,6 +753,29 @@ __armv4_mmu_cache_on:
__armv7_mmu_cache_on:
mov r12, lr
+@ r0: Primary Part Number of MIDR[15:4], read from HW
+@ r1: Primary Part Number of Cortex A9
+@ r3: Mask for Primary Part Number
+@ L1 dcache invalidation is needed for Cortex A9
+@ L1 dcache invalidation is not needed for Cortex A7 as HW does
d-cache invalidation during power ON
+
+ mrc 15, 0, r0, c0, c0, 0 @ Read Main ID [MIDR]
+ @ldr r0, =0xc090 @ Added for testing purpose
+ ldr r1, =0x0000c090 @ Cortex-A9 MPCore (ARMv7)
+ ldr r2, =0x0000fff0 @ Mask for Primary
Part Number [15:4]
+ ands r0, r0, r2 @ get the Primary Part Number
+ eors r0, r1 @ Test whether the core is A9
+ beq v7_invalidate @ Allow A9 to perform
L1 invalidate
+ bne l1_self_invalidated @ Only A9 requires L1
cache invalidate
+@ Invalidate L1
+v7_invalidate:
+ stmia sp, {r0-r4, lr}
+ bl v7_invalidate_l1 @ Allow A9 to perform
L1 invalidate
+ ldmia sp, {r0-r4, lr}
+
+@ Skip Invalidation, alreay validated in the HW
+l1_self_invalidated:
+
#ifdef CONFIG_MMU
mrc p15, 0, r11, c0, c1, 4 @ read ID_MMFR0
tst r11, #0xf @ VMSA
@@ -1253,6 +1276,43 @@ __armv3_mpu_cache_flush:
mcr p15, 0, r1, c7, c0, 0 @ invalidate whole cache v3
mov pc, lr
+
+ENTRY(v7_invalidate_l1)
+ mov r0, #0
+ mcr p15, 2, r0, c0, c0, 0
+ mrc p15, 1, r0, c0, c0, 0
+
+ ldr r1, =0x7fff
+ and r2, r1, r0, lsr #13
+
+ ldr r1, =0x3ff
+
+ and r3, r1, r0, lsr #3 @ NumWays - 1
+ add r2, r2, #1 @ NumSets
+
+ and r0, r0, #0x7
+ add r0, r0, #4 @ SetShift
+
+ clz r1, r3 @ WayShift
+ add r4, r3, #1 @ NumWays
+1: sub r2, r2, #1 @ NumSets--
+ mov r3, r4 @ Temp = NumWays
+2: subs r3, r3, #1 @ Temp--
+ mov r5, r3, lsl r1
+ mov r6, r2, lsl r0
+ orr r5, r5, r6 @ Reg = (Temp<<WayShift)|(NumSets<<SetShift)
+ mcr p15, 0, r5, c7, c6, 2
+ bgt 2b
+ cmp r2, #0
+ bgt 1b
+ dsb
+ isb
+ mov pc, lr
+ENDPROC(v7_invalidate_l1)
+
+/* end of d-cache invalidation
+*/
+
/*
* Various debugging routines for printing hex characters and
* memory, which again must be relocatable.
The modified kernel boots fine if I revert SHA 6ec1588e that aliases
NOR flash at address 0 for vexpress-a9:
commit 6ec1588e09770ac7e9c60194faff6101111fc7f0
Author: Peter Maydell <>
Date: Wed Jul 2 15:07:50 2014 +0100
hw/arm/vexpress: Alias NOR flash at 0 for vexpress-a9
Make the vexpress-a9 board alias the first NOR flash region at
address zero, like vexpress-a15. This makes "-bios" actually usable
on this board.
diff --git a/hw/arm/vexpress.c b/hw/arm/vexpress.c
index 3d83e6c..a88732c 100644
--- a/hw/arm/vexpress.c
+++ b/hw/arm/vexpress.c
@@ -84,6 +84,7 @@ enum {
};
static hwaddr motherboard_legacy_map[] = {
+ [VE_NORFLASHALIAS] = 0,
/* CS7: 0x10000000 .. 0x10020000 */
[VE_SYSREGS] = 0x10000000,
[VE_SP810] = 0x10001000,
@@ -114,7 +115,6 @@ static hwaddr motherboard_legacy_map[] = {
[VE_VIDEORAM] = 0x4c000000,
[VE_ETHERNET] = 0x4e000000,
[VE_USB] = 0x4f000000,
- [VE_NORFLASHALIAS] = -1, /* not present */
};
- [Qemu-devel] vexpress-a9 aborts when booting decompress code from a modified Linux kernel,
Ilya Lipnitskiy <=