patch-2.1.9 linux/arch/sparc/prom/tree.c

Next file: linux/drivers/Makefile
Previous file: linux/arch/sparc/prom/segment.c
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.1.8/linux/arch/sparc/prom/tree.c linux/arch/sparc/prom/tree.c
@@ -1,4 +1,4 @@
-/* $Id: tree.c,v 1.8 1996/04/04 16:31:09 tridge Exp $
+/* $Id: tree.c,v 1.12 1996/10/12 12:37:40 davem Exp $
  * tree.c: Basic device tree traversal/scanning for the Linux
  *         prom library.
  *
@@ -7,6 +7,9 @@
 
 #include <linux/config.h>
 #include <linux/string.h>
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
 
 #include <asm/openprom.h>
 #include <asm/oplib.h>
@@ -19,16 +22,31 @@
 int
 prom_getchild(int node)
 {
-	int cnode;
+	int cnode, ret;
+	unsigned long flags;
+
+	save_flags(flags); cli();
 
 #if CONFIG_AP1000
         printk("prom_getchild -> 0\n");
+	restore_flags(flags);
         return 0;
+#else
+	if(node == -1) {
+		ret = 0;
+	} else {
+		cnode = prom_nodeops->no_child(node);
+		if((cnode == 0) || (cnode == -1))
+			ret = 0;
+		else
+			ret = cnode;
+	}
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 #endif
-	if(node == -1) return 0;
-	cnode = prom_nodeops->no_child(node);
-	if((cnode == 0) || (cnode == -1)) return 0;
-	return cnode;
 }
 
 /* Return the next sibling of node 'node' or zero if no more siblings
@@ -37,16 +55,31 @@
 int
 prom_getsibling(int node)
 {
-	int sibnode;
+	int sibnode, ret;
+	unsigned long flags;
+
+	save_flags(flags); cli();
 
 #if CONFIG_AP1000
         printk("prom_getsibling -> 0\n");
+	restore_flags(flags);
         return 0;
+#else
+	if(node == -1) {
+		ret = 0;
+	} else {
+		sibnode = prom_nodeops->no_nextnode(node);
+		if((sibnode == 0) || (sibnode == -1))
+			ret = 0;
+		else
+			ret = sibnode;
+	}
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 #endif
-	if(node == -1) return 0;
-	sibnode = prom_nodeops->no_nextnode(node);
-	if((sibnode == 0) || (sibnode == -1)) return 0;
-	return sibnode;
 }
 
 /* Return the length in bytes of property 'prop' at node 'node'.
@@ -55,12 +88,25 @@
 int
 prom_getproplen(int node, char *prop)
 {
+	int ret;
+	unsigned long flags;
+
+	save_flags(flags); cli();
+
 #if CONFIG_AP1000
         printk("prom_getproplen(%s) -> -1\n",prop);
+	restore_flags(flags);
         return -1;
 #endif
-	if((!node) || (!prop)) return -1;
-	return prom_nodeops->no_proplen(node, prop);
+	if((!node) || (!prop))
+		ret = -1;
+	else
+		ret = prom_nodeops->no_proplen(node, prop);
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 }
 
 /* Acquire a property 'prop' at node 'node' and place it in
@@ -70,17 +116,28 @@
 int
 prom_getproperty(int node, char *prop, char *buffer, int bufsize)
 {
-	int plen;
+	int plen, ret;
+	unsigned long flags;
+
+	save_flags(flags); cli();
 
 #if CONFIG_AP1000
         printk("prom_getproperty(%s) -> -1\n",prop);
-        return -1;
+	restore_flags(flags);
+	return -1;
 #endif
 	plen = prom_getproplen(node, prop);
-	if((plen > bufsize) || (plen == 0) || (plen == -1)) return -1;
-
-	/* Ok, things seem all right. */
-	return prom_nodeops->no_getprop(node, prop, buffer);
+	if((plen > bufsize) || (plen == 0) || (plen == -1))
+		ret = -1;
+	else {
+		/* Ok, things seem all right. */
+		ret = prom_nodeops->no_getprop(node, prop, buffer);
+	}
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 }
 
 /* Acquire an integer property and return its value.  Returns -1
@@ -173,6 +230,7 @@
 int
 prom_searchsiblings(int node_start, char *nodename)
 {
+
 	int thisnode, error;
 
 	for(thisnode = node_start; thisnode;
@@ -187,13 +245,41 @@
 	return 0;
 }
 
+/* Gets name in the form prom v2+ uses it (name@x,yyyyy or name (if no reg)) */
+int 
+prom_getname (int node, char *buffer, int len)
+{
+	int i;
+	struct linux_prom_registers reg[PROMREG_MAX];
+	
+	i = prom_getproperty (node, "name", buffer, len);
+	if (i <= 0) return -1;
+	buffer [i] = 0;
+	len -= i;
+	i = prom_getproperty (node, "reg", (char *)reg, sizeof (reg));
+	if (i <= 0) return 0;
+	if (len < 11) return -1;
+	buffer = strchr (buffer, 0);
+	sprintf (buffer, "@%x,%x", reg[0].which_io, (uint)reg[0].phys_addr);
+	return 0;
+}
+
 /* Return the first property type for node 'node'.
  */
 char *
 prom_firstprop(int node)
 {
+	unsigned long flags;
+	char *ret;
+
 	if(node == -1) return "";
-	return prom_nodeops->no_nextprop(node, (char *) 0x0);
+	save_flags(flags); cli();
+	ret = prom_nodeops->no_nextprop(node, (char *) 0x0);
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 }
 
 /* Return the property type string after property type 'oprop'
@@ -203,8 +289,17 @@
 char *
 prom_nextprop(int node, char *oprop)
 {
+	char *ret;
+	unsigned long flags;
+
 	if(node == -1) return "";
-	return prom_nodeops->no_nextprop(node, oprop);
+	save_flags(flags); cli();
+	ret = prom_nodeops->no_nextprop(node, oprop);
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
 }
 
 int
@@ -226,7 +321,48 @@
 int
 prom_setprop(int node, char *pname, char *value, int size)
 {
+	unsigned long flags;
+	int ret;
+
 	if(size == 0) return 0;
 	if((pname == 0) || (value == 0)) return 0;
-	return prom_nodeops->no_setprop(node, pname, value, size);
+	save_flags(flags); cli();
+	ret = prom_nodeops->no_setprop(node, pname, value, size);
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+			     "r" (&current_set[smp_processor_id()]) :
+			     "memory");
+	restore_flags(flags);
+	return ret;
+}
+
+int
+prom_inst2pkg(int inst)
+{
+	int node;
+	unsigned long flags;
+	
+	save_flags(flags); cli();
+	node = (*romvec->pv_v2devops.v2_inst2pkg)(inst);
+	__asm__ __volatile__("ld [%0], %%g6\n\t" : :
+		"r" (&current_set[smp_processor_id()]) :
+		"memory");
+	restore_flags(flags);
+	if (node == -1) return 0;
+	return node;
+}
+
+/* Return 'node' assigned to a particular prom 'path'
+ * FIXME: Should work for v0 as well
+ */
+int
+prom_pathtoinode(char *path)
+{
+	int node, inst;
+	
+	inst = prom_devopen (path);
+	if (inst == -1) return 0;
+	node = prom_inst2pkg (inst);
+	prom_devclose (inst);
+	if (node == -1) return 0;
+	return node;
 }

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen, slshen@lbl.gov