[PATCH] ignore huge OF properties

Anton Blanchard anton at samba.org
Tue Mar 16 18:06:50 EST 2004


Hi,

Im just about to commit this patch. We have some versions of firmware
out there that have huge OF properties. So huge that we end up overwriting
our initrd.

Place a 1MB limit and warn bitterly if its over this. Also fix a use
of package-to-path where the variable was 64bytes but we would pass in
a length of 255.

Anton

 forakpm-anton/arch/ppc64/kernel/prom.c |   36 ++++++++++++++++++++++++++++++---
 1 files changed, 33 insertions(+), 3 deletions(-)

diff -puN arch/ppc64/kernel/prom.c~ppc64-large_properties arch/ppc64/kernel/prom.c
--- forakpm/arch/ppc64/kernel/prom.c~ppc64-large_properties	2004-03-16 14:51:57.969341778 +1100
+++ forakpm-anton/arch/ppc64/kernel/prom.c	2004-03-16 16:58:57.881228283 +1100
@@ -61,6 +61,14 @@ extern const struct linux_logo logo_linu
 #endif

 /*
+ * Properties whose value is longer than this get excluded from our
+ * copy of the device tree. This value does need to be big enough to
+ * ensure that we don't lose things like the interrupt-map property
+ * on a PCI-PCI bridge.
+ */
+#define MAX_PROPERTY_LENGTH	(1UL * 1024 * 1024)
+
+/*
  * prom_init() is called very early on, before the kernel text
  * and data have been mapped to KERNELBASE.  At this point the code
  * is running at whatever address it has been loaded at, so
@@ -908,9 +916,11 @@ prom_initialize_tce_table(void)
 			*tce_entryp = tce_entry;
 		}

+		/* It seems OF doesn't null-terminate the path :-( */
+		memset(path, 0, sizeof(path));
 		/* Call OF to setup the TCE hardware */
 		if (call_prom(RELOC("package-to-path"), 3, 1, node,
-                             path, 255) <= 0) {
+                             path, sizeof(path)-1) <= 0) {
                         prom_print(RELOC("package-to-path failed\n"));
                 } else {
                         prom_print(RELOC("opened "));
@@ -1687,6 +1697,11 @@ check_display(unsigned long mem)
 		/* It seems OF doesn't null-terminate the path :-( */
 		path = (char *) mem;
 		memset(path, 0, 256);
+
+		/*
+		 * leave some room at the end of the path for appending extra
+		 * arguments
+		 */
 		if ((long) call_prom(RELOC("package-to-path"), 3, 1,
 				    node, path, 250) < 0)
 			continue;
@@ -1794,8 +1809,7 @@ copy_device_tree(unsigned long mem_start
 	return new_start;
 }

-__init
-static unsigned long
+static unsigned long __init
 inspect_node(phandle node, struct device_node *dad,
 	     unsigned long mem_start, unsigned long mem_end,
 	     struct device_node ***allnextpp)
@@ -1843,6 +1857,22 @@ inspect_node(phandle node, struct device
 				  valp, mem_end - mem_start);
 		if (pp->length < 0)
 			continue;
+		if (pp->length > MAX_PROPERTY_LENGTH) {
+			char path[128];
+
+			prom_print(RELOC("WARNING: ignoring large property "));
+			/* It seems OF doesn't null-terminate the path :-( */
+			memset(path, 0, sizeof(path));
+			if (call_prom(RELOC("package-to-path"), 3, 1, node,
+                            path, sizeof(path)-1) > 0)
+				prom_print(path);
+			prom_print(namep);
+			prom_print(RELOC(" length 0x"));
+			prom_print_hex(pp->length);
+			prom_print_nl();
+
+			continue;
+		}
 		mem_start = DOUBLEWORD_ALIGN(mem_start + pp->length);
 		*prev_propp = PTRUNRELOC(pp);
 		prev_propp = &pp->next;

** Sent via the linuxppc64-dev mail list. See http://lists.linuxppc.org/





More information about the Linuxppc64-dev mailing list