Skip to content

Commit

Permalink
ARM: HYP/non-sec: Add MIDR check to detect unsupported CPUs
Browse files Browse the repository at this point in the history
Unlike 9d195a5, which had removed
the MIDR check against the "white list" of supported CPUs earlier,
now we introduce the "black list" of unsupported CPUs.

The current PSCI code is not compatible with the Cortex-A8 CPU used
in Allwinner A10/A13 SoCs because of making GIC and virtualization
support assumptions. Allwinner A10 and Allwinner A20 (with Cortex-A7
CPU, supported by PSCI) are pin compatible, they can be used as
drop-in replacements for each other and share the same PCB design:
   https://www.olimex.com/Products/OLinuXino/A10/A10-OLinuXino-LIME
   https://www.olimex.com/Products/OLinuXino/A20/A20-OLinuXino-LIME
The same u-boot binary binary can boot on Allwinner A10 and
Allwinner A20 with just minor tweaks applied.

This patch implements one of such necessary tweaks to allow the
PSCI code to be compiled in, but skip it if Cortex-A8 is detected
at runtime. The function 'armv7_init_nonsec()' now returns an error
in the case if Cortex-A8 is detected. Also an extra error check
is added for the 'armv7_init_nonsec()' call. If the board config
header file provides CONFIG_ARMV7_ALLOW_SECURE_MODE_FALLBACK define,
then the kernel is loaded in secure mode as a fallback. In the
case is this define is not provided, the failure to switch to
non-secure mode is treated as a fatal error and an appropriate
message is displayed.

Signed-off-by: Siarhei Siamashka <siarhei.siamashka@gmail.com>
  • Loading branch information
ssvb committed Sep 9, 2014
1 parent d15cdfb commit 6a4f292
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 3 deletions.
3 changes: 3 additions & 0 deletions arch/arm/cpu/armv7/virt-dt.c
Expand Up @@ -31,6 +31,9 @@ static int fdt_psci(void *fdt)
int nodeoff;
int tmp;

if (armv7_is_cpu_blacklisted_for_nonsec())
return 0;

nodeoff = fdt_path_offset(fdt, "/cpus");
if (nodeoff < 0) {
printf("couldn't find /cpus\n");
Expand Down
20 changes: 20 additions & 0 deletions arch/arm/cpu/armv7/virt-v7.c
Expand Up @@ -71,11 +71,31 @@ void __weak smp_kick_all_cpus(void)
kick_secondary_cpus_gic(gic_dist_addr);
}

/*
* Check the "black list" of CPUs, which are not supported by this code
*/
int armv7_is_cpu_blacklisted_for_nonsec(void)
{
unsigned midr;
asm("mrc p15, 0, %0, c0, c0, 0\n" : "=r"(midr));

/* Cortex-A8 is not supported yet */
if ((midr & MIDR_PRIMARY_PART_MASK) == MIDR_CORTEX_A8_PRIMARY_PART)
return 1;

return 0;
}

int armv7_init_nonsec(void)
{
unsigned int reg;
unsigned itlinesnr, i;

if (armv7_is_cpu_blacklisted_for_nonsec()) {
printf("nonsec: This CPU is not supported.\n");
return -1;
}

/* check whether the CPU supports the security extensions */
reg = read_id_pfr1();
if ((reg & 0xF0) == 0) {
Expand Down
5 changes: 5 additions & 0 deletions arch/arm/include/asm/armv7.h
Expand Up @@ -8,6 +8,10 @@
#ifndef ARMV7_H
#define ARMV7_H

/* Cortex-A8 revisions */
#define MIDR_CORTEX_A8_PRIMARY_PART 0x410FC080
#define MIDR_CORTEX_A8_R3P2 0x413FC082

/* Cortex-A9 revisions */
#define MIDR_CORTEX_A9_R0P1 0x410FC091
#define MIDR_CORTEX_A9_R1P2 0x411FC092
Expand Down Expand Up @@ -80,6 +84,7 @@ void v7_outer_cache_inval_range(u32 start, u32 end);

int armv7_init_nonsec(void);
int armv7_update_dt(void *fdt);
int armv7_is_cpu_blacklisted_for_nonsec(void);

/* defined in assembly file */
unsigned int _nonsec_init(void);
Expand Down
16 changes: 13 additions & 3 deletions arch/arm/lib/bootm.c
Expand Up @@ -283,9 +283,19 @@ static void boot_jump_linux(bootm_headers_t *images, int flag)

if (!fake) {
#if defined(CONFIG_ARMV7_NONSEC) || defined(CONFIG_ARMV7_VIRT)
armv7_init_nonsec();
secure_ram_addr(_do_nonsec_entry)(kernel_entry,
0, machid, r2);
if (armv7_init_nonsec()) {
printf("Switch to non-secure mode has failed - ");
#ifdef CONFIG_ARMV7_ALLOW_SECURE_MODE_FALLBACK
printf("booting the kernel in secure mode ...\n\n");
kernel_entry(0, machid, r2);
#else
printf("hanging ...\n");
hang();
#endif
} else {
secure_ram_addr(_do_nonsec_entry)(kernel_entry,
0, machid, r2);
}
#else
kernel_entry(0, machid, r2);
#endif
Expand Down

0 comments on commit 6a4f292

Please sign in to comment.