1 /* sbus.c: SBus support routines.
3 * Copyright (C) 1995, 2006 David S. Miller (davem@davemloft.net)
6 #include <linux/kernel.h>
7 #include <linux/slab.h>
8 #include <linux/init.h>
9 #include <linux/device.h>
11 #include <asm/system.h>
14 #include <asm/oplib.h>
16 #include <asm/of_device.h>
21 show_sbusobppath_attr(struct device
* dev
, struct device_attribute
* attr
, char * buf
)
23 struct sbus_dev
*sbus
;
25 sbus
= to_sbus_device(dev
);
27 return snprintf (buf
, PAGE_SIZE
, "%s\n", sbus
->ofdev
.node
->full_name
);
30 static DEVICE_ATTR(obppath
, S_IRUSR
| S_IRGRP
| S_IROTH
, show_sbusobppath_attr
, NULL
);
32 struct sbus_bus
*sbus_root
;
34 static void __init
fill_sbus_device(struct device_node
*dp
, struct sbus_dev
*sdev
)
36 struct dev_archdata
*sd
;
41 sdev
->prom_node
= dp
->node
;
42 strcpy(sdev
->prom_name
, dp
->name
);
44 pval
= of_get_property(dp
, "reg", &len
);
45 sdev
->num_registers
= 0;
47 memcpy(sdev
->reg_addrs
, pval
, len
);
50 len
/ sizeof(struct linux_prom_registers
);
52 base
= (unsigned long) sdev
->reg_addrs
[0].phys_addr
;
54 /* Compute the slot number. */
55 if (base
>= SUN_SBUS_BVADDR
&& sparc_cpu_model
== sun4m
)
56 sdev
->slot
= sbus_dev_slot(base
);
58 sdev
->slot
= sdev
->reg_addrs
[0].which_io
;
61 pval
= of_get_property(dp
, "ranges", &len
);
62 sdev
->num_device_ranges
= 0;
64 memcpy(sdev
->device_ranges
, pval
, len
);
65 sdev
->num_device_ranges
=
66 len
/ sizeof(struct linux_prom_ranges
);
69 sbus_fill_device_irq(sdev
);
71 sd
= &sdev
->ofdev
.dev
.archdata
;
73 sd
->op
= &sdev
->ofdev
;
75 sdev
->ofdev
.node
= dp
;
77 sdev
->ofdev
.dev
.parent
= &sdev
->parent
->ofdev
.dev
;
79 sdev
->ofdev
.dev
.parent
= &sdev
->bus
->ofdev
.dev
;
80 sdev
->ofdev
.dev
.bus
= &sbus_bus_type
;
81 sprintf(sdev
->ofdev
.dev
.bus_id
, "sbus[%08x]", dp
->node
);
83 if (of_device_register(&sdev
->ofdev
) != 0)
84 printk(KERN_DEBUG
"sbus: device registration error for %s!\n",
85 dp
->path_component_name
);
87 /* WE HAVE BEEN INVADED BY ALIENS! */
88 err
= sysfs_create_file(&sdev
->ofdev
.dev
.kobj
, &dev_attr_obppath
.attr
);
91 static void __init
sbus_bus_ranges_init(struct device_node
*dp
, struct sbus_bus
*sbus
)
96 pval
= of_get_property(dp
, "ranges", &len
);
97 sbus
->num_sbus_ranges
= 0;
99 memcpy(sbus
->sbus_ranges
, pval
, len
);
100 sbus
->num_sbus_ranges
=
101 len
/ sizeof(struct linux_prom_ranges
);
103 sbus_arch_bus_ranges_init(dp
->parent
, sbus
);
107 static void __init
__apply_ranges_to_regs(struct linux_prom_ranges
*ranges
,
109 struct linux_prom_registers
*regs
,
115 for (regnum
= 0; regnum
< num_regs
; regnum
++) {
118 for (rngnum
= 0; rngnum
< num_ranges
; rngnum
++) {
119 if (regs
[regnum
].which_io
== ranges
[rngnum
].ot_child_space
)
122 if (rngnum
== num_ranges
) {
123 /* We used to flag this as an error. Actually
124 * some devices do not report the regs as we expect.
125 * For example, see SUNW,pln device. In that case
126 * the reg property is in a format internal to that
127 * node, ie. it is not in the SBUS register space
132 regs
[regnum
].which_io
= ranges
[rngnum
].ot_parent_space
;
133 regs
[regnum
].phys_addr
-= ranges
[rngnum
].ot_child_base
;
134 regs
[regnum
].phys_addr
+= ranges
[rngnum
].ot_parent_base
;
139 static void __init
__fixup_regs_sdev(struct sbus_dev
*sdev
)
141 if (sdev
->num_registers
!= 0) {
142 struct sbus_dev
*parent
= sdev
->parent
;
145 while (parent
!= NULL
) {
146 __apply_ranges_to_regs(parent
->device_ranges
,
147 parent
->num_device_ranges
,
149 sdev
->num_registers
);
151 parent
= parent
->parent
;
154 __apply_ranges_to_regs(sdev
->bus
->sbus_ranges
,
155 sdev
->bus
->num_sbus_ranges
,
157 sdev
->num_registers
);
159 for (i
= 0; i
< sdev
->num_registers
; i
++) {
160 struct resource
*res
= &sdev
->resource
[i
];
162 res
->start
= sdev
->reg_addrs
[i
].phys_addr
;
163 res
->end
= (res
->start
+
164 (unsigned long)sdev
->reg_addrs
[i
].reg_size
- 1UL);
165 res
->flags
= IORESOURCE_IO
|
166 (sdev
->reg_addrs
[i
].which_io
& 0xff);
171 static void __init
sbus_fixup_all_regs(struct sbus_dev
*first_sdev
)
173 struct sbus_dev
*sdev
;
175 for (sdev
= first_sdev
; sdev
; sdev
= sdev
->next
) {
177 sbus_fixup_all_regs(sdev
->child
);
178 __fixup_regs_sdev(sdev
);
182 /* We preserve the "probe order" of these bus and device lists to give
183 * the same ordering as the old code.
185 static void __init
sbus_insert(struct sbus_bus
*sbus
, struct sbus_bus
**root
)
188 root
= &(*root
)->next
;
193 static void __init
sdev_insert(struct sbus_dev
*sdev
, struct sbus_dev
**root
)
196 root
= &(*root
)->next
;
201 static void __init
walk_children(struct device_node
*dp
, struct sbus_dev
*parent
, struct sbus_bus
*sbus
)
205 struct sbus_dev
*sdev
;
207 sdev
= kzalloc(sizeof(struct sbus_dev
), GFP_ATOMIC
);
209 sdev_insert(sdev
, &parent
->child
);
212 sdev
->parent
= parent
;
213 sdev
->ofdev
.dev
.archdata
.iommu
=
214 sbus
->ofdev
.dev
.archdata
.iommu
;
215 sdev
->ofdev
.dev
.archdata
.stc
=
216 sbus
->ofdev
.dev
.archdata
.stc
;
218 fill_sbus_device(dp
, sdev
);
220 walk_children(dp
, sdev
, sbus
);
226 static void __init
build_one_sbus(struct device_node
*dp
, int num_sbus
)
228 struct sbus_bus
*sbus
;
229 unsigned int sbus_clock
;
230 struct device_node
*dev_dp
;
232 sbus
= kzalloc(sizeof(struct sbus_bus
), GFP_ATOMIC
);
236 sbus_insert(sbus
, &sbus_root
);
237 sbus
->prom_node
= dp
->node
;
239 sbus_setup_iommu(sbus
, dp
);
241 printk("sbus%d: ", num_sbus
);
243 sbus_clock
= of_getintprop_default(dp
, "clock-frequency",
245 sbus
->clock_freq
= sbus_clock
;
247 printk("Clock %d.%d MHz\n", (int) ((sbus_clock
/1000)/1000),
248 (int) (((sbus_clock
/1000)%1000 != 0) ?
249 (((sbus_clock
/1000)%1000) + 1000) : 0));
251 strcpy(sbus
->prom_name
, dp
->name
);
253 sbus_setup_arch_props(sbus
, dp
);
255 sbus_bus_ranges_init(dp
, sbus
);
257 sbus
->ofdev
.node
= dp
;
258 sbus
->ofdev
.dev
.parent
= NULL
;
259 sbus
->ofdev
.dev
.bus
= &sbus_bus_type
;
260 sprintf(sbus
->ofdev
.dev
.bus_id
, "sbus%d", num_sbus
);
262 if (of_device_register(&sbus
->ofdev
) != 0)
263 printk(KERN_DEBUG
"sbus: device registration error for %s!\n",
264 sbus
->ofdev
.dev
.bus_id
);
268 struct sbus_dev
*sdev
;
270 sdev
= kzalloc(sizeof(struct sbus_dev
), GFP_ATOMIC
);
272 sdev_insert(sdev
, &sbus
->devices
);
276 sdev
->ofdev
.dev
.archdata
.iommu
=
277 sbus
->ofdev
.dev
.archdata
.iommu
;
278 sdev
->ofdev
.dev
.archdata
.stc
=
279 sbus
->ofdev
.dev
.archdata
.stc
;
281 fill_sbus_device(dev_dp
, sdev
);
283 walk_children(dev_dp
, sdev
, sbus
);
285 dev_dp
= dev_dp
->sibling
;
288 sbus_fixup_all_regs(sbus
->devices
);
293 static int __init
sbus_init(void)
295 struct device_node
*dp
;
296 const char *sbus_name
= "sbus";
299 if (sbus_arch_preinit())
302 if (sparc_cpu_model
== sun4d
)
305 for_each_node_by_name(dp
, sbus_name
) {
306 build_one_sbus(dp
, num_sbus
);
311 sbus_arch_postinit();
316 subsys_initcall(sbus_init
);