diff options
author | Benjamin Herrenschmidt <benh@kernel.crashing.org> | 2014-01-12 17:49:17 -0500 |
---|---|---|
committer | Benjamin Herrenschmidt <benh@kernel.crashing.org> | 2014-01-12 17:49:17 -0500 |
commit | 10348f5976830e5d8f74e8abb04a9a057a5e8478 (patch) | |
tree | e1a0c5e5a9abe98f3799126c1b45333030024b33 | |
parent | f991db1cf1bdca43675b5d2df0af991719727029 (diff) |
powerpc: Check return value of instance-to-package OF call
On PA-Semi firmware, the instance-to-package callback doesn't seem
to be implemented. We didn't check for error, however, thus
subsequently passed the -1 value returned into stdout_node to
thins like prom_getprop etc...
Thus caused the firmware to load values around 0 (physical) internally
as node structures. It somewhat "worked" as long as we had a NULL in the
right place (address 8) at the beginning of the kernel, we didn't "see"
the bug. But commit 5c0484e25ec03243d4c2f2d4416d4a13efc77f6a
"powerpc: Endian safe trampoline" changed the kernel entry point causing
that old bug to now cause a crash early during boot.
This fixes booting on PA-Semi board by properly checking the return
value from instance-to-package.
Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Tested-by: Olof Johansson <olof@lixom.net>
---
-rw-r--r-- | arch/powerpc/kernel/prom_init.c | 22 |
1 files changed, 13 insertions, 9 deletions
diff --git a/arch/powerpc/kernel/prom_init.c b/arch/powerpc/kernel/prom_init.c index cb64a6e1dc51..078145acf7fb 100644 --- a/arch/powerpc/kernel/prom_init.c +++ b/arch/powerpc/kernel/prom_init.c | |||
@@ -1986,19 +1986,23 @@ static void __init prom_init_stdout(void) | |||
1986 | /* Get the full OF pathname of the stdout device */ | 1986 | /* Get the full OF pathname of the stdout device */ |
1987 | memset(path, 0, 256); | 1987 | memset(path, 0, 256); |
1988 | call_prom("instance-to-path", 3, 1, prom.stdout, path, 255); | 1988 | call_prom("instance-to-path", 3, 1, prom.stdout, path, 255); |
1989 | stdout_node = call_prom("instance-to-package", 1, 1, prom.stdout); | ||
1990 | val = cpu_to_be32(stdout_node); | ||
1991 | prom_setprop(prom.chosen, "/chosen", "linux,stdout-package", | ||
1992 | &val, sizeof(val)); | ||
1993 | prom_printf("OF stdout device is: %s\n", of_stdout_device); | 1989 | prom_printf("OF stdout device is: %s\n", of_stdout_device); |
1994 | prom_setprop(prom.chosen, "/chosen", "linux,stdout-path", | 1990 | prom_setprop(prom.chosen, "/chosen", "linux,stdout-path", |
1995 | path, strlen(path) + 1); | 1991 | path, strlen(path) + 1); |
1996 | 1992 | ||
1997 | /* If it's a display, note it */ | 1993 | /* instance-to-package fails on PA-Semi */ |
1998 | memset(type, 0, sizeof(type)); | 1994 | stdout_node = call_prom("instance-to-package", 1, 1, prom.stdout); |
1999 | prom_getprop(stdout_node, "device_type", type, sizeof(type)); | 1995 | if (stdout_node != PROM_ERROR) { |
2000 | if (strcmp(type, "display") == 0) | 1996 | val = cpu_to_be32(stdout_node); |
2001 | prom_setprop(stdout_node, path, "linux,boot-display", NULL, 0); | 1997 | prom_setprop(prom.chosen, "/chosen", "linux,stdout-package", |
1998 | &val, sizeof(val)); | ||
1999 | |||
2000 | /* If it's a display, note it */ | ||
2001 | memset(type, 0, sizeof(type)); | ||
2002 | prom_getprop(stdout_node, "device_type", type, sizeof(type)); | ||
2003 | if (strcmp(type, "display") == 0) | ||
2004 | prom_setprop(stdout_node, path, "linux,boot-display", NULL, 0); | ||
2005 | } | ||
2002 | } | 2006 | } |
2003 | 2007 | ||
2004 | static int __init prom_find_machine_type(void) | 2008 | static int __init prom_find_machine_type(void) |