diff options
-rw-r--r-- | arch/sparc/Kconfig | 3 | ||||
-rw-r--r-- | arch/sparc64/Kconfig | 3 | ||||
-rw-r--r-- | arch/sparc64/kernel/ds.c | 19 | ||||
-rw-r--r-- | arch/sparc64/kernel/mdesc.c | 78 | ||||
-rw-r--r-- | arch/sparc64/kernel/vio.c | 94 | ||||
-rw-r--r-- | arch/sparc64/kernel/viohs.c | 30 | ||||
-rw-r--r-- | drivers/block/sunvdc.c | 97 | ||||
-rw-r--r-- | drivers/net/sunvnet.c | 260 | ||||
-rw-r--r-- | drivers/net/sunvnet.h | 4 | ||||
-rw-r--r-- | include/asm-sparc64/io.h | 5 | ||||
-rw-r--r-- | include/asm-sparc64/mdesc.h | 10 | ||||
-rw-r--r-- | include/asm-sparc64/vio.h | 2 |
12 files changed, 344 insertions, 261 deletions
diff --git a/arch/sparc/Kconfig b/arch/sparc/Kconfig index 73df7115325b..603d83ad65c8 100644 --- a/arch/sparc/Kconfig +++ b/arch/sparc/Kconfig | |||
@@ -21,6 +21,9 @@ config GENERIC_ISA_DMA | |||
21 | bool | 21 | bool |
22 | default y | 22 | default y |
23 | 23 | ||
24 | config ARCH_NO_VIRT_TO_BUS | ||
25 | def_bool y | ||
26 | |||
24 | source "init/Kconfig" | 27 | source "init/Kconfig" |
25 | 28 | ||
26 | menu "General machine setup" | 29 | menu "General machine setup" |
diff --git a/arch/sparc64/Kconfig b/arch/sparc64/Kconfig index b84b6af1241e..df6ee71894d1 100644 --- a/arch/sparc64/Kconfig +++ b/arch/sparc64/Kconfig | |||
@@ -62,6 +62,9 @@ config AUDIT_ARCH | |||
62 | bool | 62 | bool |
63 | default y | 63 | default y |
64 | 64 | ||
65 | config ARCH_NO_VIRT_TO_BUS | ||
66 | def_bool y | ||
67 | |||
65 | choice | 68 | choice |
66 | prompt "Kernel page size" | 69 | prompt "Kernel page size" |
67 | default SPARC64_PAGE_SIZE_8KB | 70 | default SPARC64_PAGE_SIZE_8KB |
diff --git a/arch/sparc64/kernel/ds.c b/arch/sparc64/kernel/ds.c index ba01533f4e03..fa1f04d756a2 100644 --- a/arch/sparc64/kernel/ds.c +++ b/arch/sparc64/kernel/ds.c | |||
@@ -1013,6 +1013,19 @@ static void ds_up(struct ds_info *dp) | |||
1013 | dp->hs_state = DS_HS_START; | 1013 | dp->hs_state = DS_HS_START; |
1014 | } | 1014 | } |
1015 | 1015 | ||
1016 | static void ds_reset(struct ds_info *dp) | ||
1017 | { | ||
1018 | int i; | ||
1019 | |||
1020 | dp->hs_state = 0; | ||
1021 | |||
1022 | for (i = 0; i < ARRAY_SIZE(ds_states); i++) { | ||
1023 | struct ds_cap_state *cp = &ds_states[i]; | ||
1024 | |||
1025 | cp->state = CAP_STATE_UNKNOWN; | ||
1026 | } | ||
1027 | } | ||
1028 | |||
1016 | static void ds_event(void *arg, int event) | 1029 | static void ds_event(void *arg, int event) |
1017 | { | 1030 | { |
1018 | struct ds_info *dp = arg; | 1031 | struct ds_info *dp = arg; |
@@ -1028,6 +1041,12 @@ static void ds_event(void *arg, int event) | |||
1028 | return; | 1041 | return; |
1029 | } | 1042 | } |
1030 | 1043 | ||
1044 | if (event == LDC_EVENT_RESET) { | ||
1045 | ds_reset(dp); | ||
1046 | spin_unlock_irqrestore(&ds_lock, flags); | ||
1047 | return; | ||
1048 | } | ||
1049 | |||
1031 | if (event != LDC_EVENT_DATA_READY) { | 1050 | if (event != LDC_EVENT_DATA_READY) { |
1032 | printk(KERN_WARNING PFX "Unexpected LDC event %d\n", event); | 1051 | printk(KERN_WARNING PFX "Unexpected LDC event %d\n", event); |
1033 | spin_unlock_irqrestore(&ds_lock, flags); | 1052 | spin_unlock_irqrestore(&ds_lock, flags); |
diff --git a/arch/sparc64/kernel/mdesc.c b/arch/sparc64/kernel/mdesc.c index de5310ffdb48..302ba5e5a0bb 100644 --- a/arch/sparc64/kernel/mdesc.c +++ b/arch/sparc64/kernel/mdesc.c | |||
@@ -137,7 +137,7 @@ static struct mdesc_handle *mdesc_kmalloc(unsigned int mdesc_size) | |||
137 | sizeof(struct mdesc_hdr) + | 137 | sizeof(struct mdesc_hdr) + |
138 | mdesc_size); | 138 | mdesc_size); |
139 | 139 | ||
140 | base = kmalloc(handle_size + 15, GFP_KERNEL); | 140 | base = kmalloc(handle_size + 15, GFP_KERNEL | __GFP_NOFAIL); |
141 | if (base) { | 141 | if (base) { |
142 | struct mdesc_handle *hp; | 142 | struct mdesc_handle *hp; |
143 | unsigned long addr; | 143 | unsigned long addr; |
@@ -214,18 +214,83 @@ void mdesc_release(struct mdesc_handle *hp) | |||
214 | } | 214 | } |
215 | EXPORT_SYMBOL(mdesc_release); | 215 | EXPORT_SYMBOL(mdesc_release); |
216 | 216 | ||
217 | static DEFINE_MUTEX(mdesc_mutex); | ||
218 | static struct mdesc_notifier_client *client_list; | ||
219 | |||
220 | void mdesc_register_notifier(struct mdesc_notifier_client *client) | ||
221 | { | ||
222 | u64 node; | ||
223 | |||
224 | mutex_lock(&mdesc_mutex); | ||
225 | client->next = client_list; | ||
226 | client_list = client; | ||
227 | |||
228 | mdesc_for_each_node_by_name(cur_mdesc, node, client->node_name) | ||
229 | client->add(cur_mdesc, node); | ||
230 | |||
231 | mutex_unlock(&mdesc_mutex); | ||
232 | } | ||
233 | |||
234 | /* Run 'func' on nodes which are in A but not in B. */ | ||
235 | static void invoke_on_missing(const char *name, | ||
236 | struct mdesc_handle *a, | ||
237 | struct mdesc_handle *b, | ||
238 | void (*func)(struct mdesc_handle *, u64)) | ||
239 | { | ||
240 | u64 node; | ||
241 | |||
242 | mdesc_for_each_node_by_name(a, node, name) { | ||
243 | const u64 *id = mdesc_get_property(a, node, "id", NULL); | ||
244 | int found = 0; | ||
245 | u64 fnode; | ||
246 | |||
247 | mdesc_for_each_node_by_name(b, fnode, name) { | ||
248 | const u64 *fid = mdesc_get_property(b, fnode, | ||
249 | "id", NULL); | ||
250 | |||
251 | if (*id == *fid) { | ||
252 | found = 1; | ||
253 | break; | ||
254 | } | ||
255 | } | ||
256 | if (!found) | ||
257 | func(a, node); | ||
258 | } | ||
259 | } | ||
260 | |||
261 | static void notify_one(struct mdesc_notifier_client *p, | ||
262 | struct mdesc_handle *old_hp, | ||
263 | struct mdesc_handle *new_hp) | ||
264 | { | ||
265 | invoke_on_missing(p->node_name, old_hp, new_hp, p->remove); | ||
266 | invoke_on_missing(p->node_name, new_hp, old_hp, p->add); | ||
267 | } | ||
268 | |||
269 | static void mdesc_notify_clients(struct mdesc_handle *old_hp, | ||
270 | struct mdesc_handle *new_hp) | ||
271 | { | ||
272 | struct mdesc_notifier_client *p = client_list; | ||
273 | |||
274 | while (p) { | ||
275 | notify_one(p, old_hp, new_hp); | ||
276 | p = p->next; | ||
277 | } | ||
278 | } | ||
279 | |||
217 | void mdesc_update(void) | 280 | void mdesc_update(void) |
218 | { | 281 | { |
219 | unsigned long len, real_len, status; | 282 | unsigned long len, real_len, status; |
220 | struct mdesc_handle *hp, *orig_hp; | 283 | struct mdesc_handle *hp, *orig_hp; |
221 | unsigned long flags; | 284 | unsigned long flags; |
222 | 285 | ||
286 | mutex_lock(&mdesc_mutex); | ||
287 | |||
223 | (void) sun4v_mach_desc(0UL, 0UL, &len); | 288 | (void) sun4v_mach_desc(0UL, 0UL, &len); |
224 | 289 | ||
225 | hp = mdesc_alloc(len, &kmalloc_mdesc_memops); | 290 | hp = mdesc_alloc(len, &kmalloc_mdesc_memops); |
226 | if (!hp) { | 291 | if (!hp) { |
227 | printk(KERN_ERR "MD: mdesc alloc fails\n"); | 292 | printk(KERN_ERR "MD: mdesc alloc fails\n"); |
228 | return; | 293 | goto out; |
229 | } | 294 | } |
230 | 295 | ||
231 | status = sun4v_mach_desc(__pa(&hp->mdesc), len, &real_len); | 296 | status = sun4v_mach_desc(__pa(&hp->mdesc), len, &real_len); |
@@ -234,18 +299,25 @@ void mdesc_update(void) | |||
234 | status); | 299 | status); |
235 | atomic_dec(&hp->refcnt); | 300 | atomic_dec(&hp->refcnt); |
236 | mdesc_free(hp); | 301 | mdesc_free(hp); |
237 | return; | 302 | goto out; |
238 | } | 303 | } |
239 | 304 | ||
240 | spin_lock_irqsave(&mdesc_lock, flags); | 305 | spin_lock_irqsave(&mdesc_lock, flags); |
241 | orig_hp = cur_mdesc; | 306 | orig_hp = cur_mdesc; |
242 | cur_mdesc = hp; | 307 | cur_mdesc = hp; |
308 | spin_unlock_irqrestore(&mdesc_lock, flags); | ||
243 | 309 | ||
310 | mdesc_notify_clients(orig_hp, hp); | ||
311 | |||
312 | spin_lock_irqsave(&mdesc_lock, flags); | ||
244 | if (atomic_dec_and_test(&orig_hp->refcnt)) | 313 | if (atomic_dec_and_test(&orig_hp->refcnt)) |
245 | mdesc_free(orig_hp); | 314 | mdesc_free(orig_hp); |
246 | else | 315 | else |
247 | list_add(&orig_hp->list, &mdesc_zombie_list); | 316 | list_add(&orig_hp->list, &mdesc_zombie_list); |
248 | spin_unlock_irqrestore(&mdesc_lock, flags); | 317 | spin_unlock_irqrestore(&mdesc_lock, flags); |
318 | |||
319 | out: | ||
320 | mutex_unlock(&mdesc_mutex); | ||
249 | } | 321 | } |
250 | 322 | ||
251 | static struct mdesc_elem *node_block(struct mdesc_hdr *mdesc) | 323 | static struct mdesc_elem *node_block(struct mdesc_hdr *mdesc) |
diff --git a/arch/sparc64/kernel/vio.c b/arch/sparc64/kernel/vio.c index 49569b44ea1f..8d3cc4fdb557 100644 --- a/arch/sparc64/kernel/vio.c +++ b/arch/sparc64/kernel/vio.c | |||
@@ -201,10 +201,11 @@ static void vio_fill_channel_info(struct mdesc_handle *hp, u64 mp, | |||
201 | static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, | 201 | static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, |
202 | struct device *parent) | 202 | struct device *parent) |
203 | { | 203 | { |
204 | const char *type, *compat; | 204 | const char *type, *compat, *bus_id_name; |
205 | struct device_node *dp; | 205 | struct device_node *dp; |
206 | struct vio_dev *vdev; | 206 | struct vio_dev *vdev; |
207 | int err, tlen, clen; | 207 | int err, tlen, clen; |
208 | const u64 *id; | ||
208 | 209 | ||
209 | type = mdesc_get_property(hp, mp, "device-type", &tlen); | 210 | type = mdesc_get_property(hp, mp, "device-type", &tlen); |
210 | if (!type) { | 211 | if (!type) { |
@@ -220,6 +221,16 @@ static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, | |||
220 | return NULL; | 221 | return NULL; |
221 | } | 222 | } |
222 | 223 | ||
224 | bus_id_name = type; | ||
225 | if (!strcmp(type, "domain-services-port")) | ||
226 | bus_id_name = "ds"; | ||
227 | |||
228 | if (strlen(bus_id_name) >= KOBJ_NAME_LEN - 4) { | ||
229 | printk(KERN_ERR "VIO: bus_id_name [%s] is too long.\n", | ||
230 | bus_id_name); | ||
231 | return NULL; | ||
232 | } | ||
233 | |||
223 | compat = mdesc_get_property(hp, mp, "device-type", &clen); | 234 | compat = mdesc_get_property(hp, mp, "device-type", &clen); |
224 | if (!compat) { | 235 | if (!compat) { |
225 | clen = 0; | 236 | clen = 0; |
@@ -249,7 +260,14 @@ static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, | |||
249 | 260 | ||
250 | vio_fill_channel_info(hp, mp, vdev); | 261 | vio_fill_channel_info(hp, mp, vdev); |
251 | 262 | ||
252 | snprintf(vdev->dev.bus_id, BUS_ID_SIZE, "%lx", mp); | 263 | id = mdesc_get_property(hp, mp, "id", NULL); |
264 | if (!id) | ||
265 | snprintf(vdev->dev.bus_id, BUS_ID_SIZE, "%s", | ||
266 | bus_id_name); | ||
267 | else | ||
268 | snprintf(vdev->dev.bus_id, BUS_ID_SIZE, "%s-%lu", | ||
269 | bus_id_name, *id); | ||
270 | |||
253 | vdev->dev.parent = parent; | 271 | vdev->dev.parent = parent; |
254 | vdev->dev.bus = &vio_bus_type; | 272 | vdev->dev.bus = &vio_bus_type; |
255 | vdev->dev.release = vio_dev_release; | 273 | vdev->dev.release = vio_dev_release; |
@@ -269,6 +287,8 @@ static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, | |||
269 | } | 287 | } |
270 | vdev->dp = dp; | 288 | vdev->dp = dp; |
271 | 289 | ||
290 | printk(KERN_ERR "VIO: Adding device %s\n", vdev->dev.bus_id); | ||
291 | |||
272 | err = device_register(&vdev->dev); | 292 | err = device_register(&vdev->dev); |
273 | if (err) { | 293 | if (err) { |
274 | printk(KERN_ERR "VIO: Could not register device %s, err=%d\n", | 294 | printk(KERN_ERR "VIO: Could not register device %s, err=%d\n", |
@@ -283,46 +303,46 @@ static struct vio_dev *vio_create_one(struct mdesc_handle *hp, u64 mp, | |||
283 | return vdev; | 303 | return vdev; |
284 | } | 304 | } |
285 | 305 | ||
286 | static void walk_tree(struct mdesc_handle *hp, u64 n, struct vio_dev *parent) | 306 | static void vio_add(struct mdesc_handle *hp, u64 node) |
287 | { | 307 | { |
288 | u64 a; | 308 | (void) vio_create_one(hp, node, &root_vdev->dev); |
289 | |||
290 | mdesc_for_each_arc(a, hp, n, MDESC_ARC_TYPE_FWD) { | ||
291 | struct vio_dev *vdev; | ||
292 | u64 target; | ||
293 | |||
294 | target = mdesc_arc_target(hp, a); | ||
295 | vdev = vio_create_one(hp, target, &parent->dev); | ||
296 | if (vdev) | ||
297 | walk_tree(hp, target, vdev); | ||
298 | } | ||
299 | } | 309 | } |
300 | 310 | ||
301 | static void create_devices(struct mdesc_handle *hp, u64 root) | 311 | static int vio_md_node_match(struct device *dev, void *arg) |
302 | { | 312 | { |
303 | u64 mp; | 313 | struct vio_dev *vdev = to_vio_dev(dev); |
304 | 314 | ||
305 | root_vdev = vio_create_one(hp, root, NULL); | 315 | if (vdev->mp == (u64) arg) |
306 | if (!root_vdev) { | 316 | return 1; |
307 | printk(KERN_ERR "VIO: Coult not create root device.\n"); | ||
308 | return; | ||
309 | } | ||
310 | 317 | ||
311 | walk_tree(hp, root, root_vdev); | 318 | return 0; |
319 | } | ||
320 | |||
321 | static void vio_remove(struct mdesc_handle *hp, u64 node) | ||
322 | { | ||
323 | struct device *dev; | ||
312 | 324 | ||
313 | /* Domain services is odd as it doesn't sit underneath the | 325 | dev = device_find_child(&root_vdev->dev, (void *) node, |
314 | * channel-devices node, so we plug it in manually. | 326 | vio_md_node_match); |
315 | */ | 327 | if (dev) { |
316 | mp = mdesc_node_by_name(hp, MDESC_NODE_NULL, "domain-services"); | 328 | printk(KERN_INFO "VIO: Removing device %s\n", dev->bus_id); |
317 | if (mp != MDESC_NODE_NULL) { | ||
318 | struct vio_dev *parent = vio_create_one(hp, mp, | ||
319 | &root_vdev->dev); | ||
320 | 329 | ||
321 | if (parent) | 330 | device_unregister(dev); |
322 | walk_tree(hp, mp, parent); | ||
323 | } | 331 | } |
324 | } | 332 | } |
325 | 333 | ||
334 | static struct mdesc_notifier_client vio_device_notifier = { | ||
335 | .add = vio_add, | ||
336 | .remove = vio_remove, | ||
337 | .node_name = "virtual-device-port", | ||
338 | }; | ||
339 | |||
340 | static struct mdesc_notifier_client vio_ds_notifier = { | ||
341 | .add = vio_add, | ||
342 | .remove = vio_remove, | ||
343 | .node_name = "domain-services-port", | ||
344 | }; | ||
345 | |||
326 | const char *channel_devices_node = "channel-devices"; | 346 | const char *channel_devices_node = "channel-devices"; |
327 | const char *channel_devices_compat = "SUNW,sun4v-channel-devices"; | 347 | const char *channel_devices_compat = "SUNW,sun4v-channel-devices"; |
328 | const char *cfg_handle_prop = "cfg-handle"; | 348 | const char *cfg_handle_prop = "cfg-handle"; |
@@ -381,11 +401,19 @@ static int __init vio_init(void) | |||
381 | 401 | ||
382 | cdev_cfg_handle = *cfg_handle; | 402 | cdev_cfg_handle = *cfg_handle; |
383 | 403 | ||
384 | create_devices(hp, root); | 404 | root_vdev = vio_create_one(hp, root, NULL); |
405 | err = -ENODEV; | ||
406 | if (!root_vdev) { | ||
407 | printk(KERN_ERR "VIO: Coult not create root device.\n"); | ||
408 | goto out_release; | ||
409 | } | ||
410 | |||
411 | mdesc_register_notifier(&vio_device_notifier); | ||
412 | mdesc_register_notifier(&vio_ds_notifier); | ||
385 | 413 | ||
386 | mdesc_release(hp); | 414 | mdesc_release(hp); |
387 | 415 | ||
388 | return 0; | 416 | return err; |
389 | 417 | ||
390 | out_release: | 418 | out_release: |
391 | mdesc_release(hp); | 419 | mdesc_release(hp); |
diff --git a/arch/sparc64/kernel/viohs.c b/arch/sparc64/kernel/viohs.c index 15613add45d1..09126fc338ba 100644 --- a/arch/sparc64/kernel/viohs.c +++ b/arch/sparc64/kernel/viohs.c | |||
@@ -78,6 +78,24 @@ static int start_handshake(struct vio_driver_state *vio) | |||
78 | return 0; | 78 | return 0; |
79 | } | 79 | } |
80 | 80 | ||
81 | static void flush_rx_dring(struct vio_driver_state *vio) | ||
82 | { | ||
83 | struct vio_dring_state *dr; | ||
84 | u64 ident; | ||
85 | |||
86 | BUG_ON(!(vio->dr_state & VIO_DR_STATE_RXREG)); | ||
87 | |||
88 | dr = &vio->drings[VIO_DRIVER_RX_RING]; | ||
89 | ident = dr->ident; | ||
90 | |||
91 | BUG_ON(!vio->desc_buf); | ||
92 | kfree(vio->desc_buf); | ||
93 | vio->desc_buf = NULL; | ||
94 | |||
95 | memset(dr, 0, sizeof(*dr)); | ||
96 | dr->ident = ident; | ||
97 | } | ||
98 | |||
81 | void vio_link_state_change(struct vio_driver_state *vio, int event) | 99 | void vio_link_state_change(struct vio_driver_state *vio, int event) |
82 | { | 100 | { |
83 | if (event == LDC_EVENT_UP) { | 101 | if (event == LDC_EVENT_UP) { |
@@ -98,6 +116,16 @@ void vio_link_state_change(struct vio_driver_state *vio, int event) | |||
98 | break; | 116 | break; |
99 | } | 117 | } |
100 | start_handshake(vio); | 118 | start_handshake(vio); |
119 | } else if (event == LDC_EVENT_RESET) { | ||
120 | vio->hs_state = VIO_HS_INVALID; | ||
121 | |||
122 | if (vio->dr_state & VIO_DR_STATE_RXREG) | ||
123 | flush_rx_dring(vio); | ||
124 | |||
125 | vio->dr_state = 0x00; | ||
126 | memset(&vio->ver, 0, sizeof(vio->ver)); | ||
127 | |||
128 | ldc_disconnect(vio->lp); | ||
101 | } | 129 | } |
102 | } | 130 | } |
103 | EXPORT_SYMBOL(vio_link_state_change); | 131 | EXPORT_SYMBOL(vio_link_state_change); |
@@ -396,6 +424,8 @@ static int process_dreg_info(struct vio_driver_state *vio, | |||
396 | if (vio->dr_state & VIO_DR_STATE_RXREG) | 424 | if (vio->dr_state & VIO_DR_STATE_RXREG) |
397 | goto send_nack; | 425 | goto send_nack; |
398 | 426 | ||
427 | BUG_ON(vio->desc_buf); | ||
428 | |||
399 | vio->desc_buf = kzalloc(pkt->descr_size, GFP_ATOMIC); | 429 | vio->desc_buf = kzalloc(pkt->descr_size, GFP_ATOMIC); |
400 | if (!vio->desc_buf) | 430 | if (!vio->desc_buf) |
401 | goto send_nack; | 431 | goto send_nack; |
diff --git a/drivers/block/sunvdc.c b/drivers/block/sunvdc.c index 0f5e3caf85d7..2288b55d916f 100644 --- a/drivers/block/sunvdc.c +++ b/drivers/block/sunvdc.c | |||
@@ -45,8 +45,6 @@ struct vdc_req_entry { | |||
45 | struct vdc_port { | 45 | struct vdc_port { |
46 | struct vio_driver_state vio; | 46 | struct vio_driver_state vio; |
47 | 47 | ||
48 | struct vdc *vp; | ||
49 | |||
50 | struct gendisk *disk; | 48 | struct gendisk *disk; |
51 | 49 | ||
52 | struct vdc_completion *cmp; | 50 | struct vdc_completion *cmp; |
@@ -72,8 +70,6 @@ struct vdc_port { | |||
72 | 70 | ||
73 | struct vio_disk_geom geom; | 71 | struct vio_disk_geom geom; |
74 | struct vio_disk_vtoc label; | 72 | struct vio_disk_vtoc label; |
75 | |||
76 | struct list_head list; | ||
77 | }; | 73 | }; |
78 | 74 | ||
79 | static inline struct vdc_port *to_vdc_port(struct vio_driver_state *vio) | 75 | static inline struct vdc_port *to_vdc_port(struct vio_driver_state *vio) |
@@ -81,15 +77,6 @@ static inline struct vdc_port *to_vdc_port(struct vio_driver_state *vio) | |||
81 | return container_of(vio, struct vdc_port, vio); | 77 | return container_of(vio, struct vdc_port, vio); |
82 | } | 78 | } |
83 | 79 | ||
84 | struct vdc { | ||
85 | /* Protects prot_list. */ | ||
86 | spinlock_t lock; | ||
87 | |||
88 | struct vio_dev *dev; | ||
89 | |||
90 | struct list_head port_list; | ||
91 | }; | ||
92 | |||
93 | /* Ordered from largest major to lowest */ | 80 | /* Ordered from largest major to lowest */ |
94 | static struct vio_version vdc_versions[] = { | 81 | static struct vio_version vdc_versions[] = { |
95 | { .major = 1, .minor = 0 }, | 82 | { .major = 1, .minor = 0 }, |
@@ -747,21 +734,23 @@ static struct vio_driver_ops vdc_vio_ops = { | |||
747 | .handshake_complete = vdc_handshake_complete, | 734 | .handshake_complete = vdc_handshake_complete, |
748 | }; | 735 | }; |
749 | 736 | ||
737 | static void print_version(void) | ||
738 | { | ||
739 | static int version_printed; | ||
740 | |||
741 | if (version_printed++ == 0) | ||
742 | printk(KERN_INFO "%s", version); | ||
743 | } | ||
744 | |||
750 | static int __devinit vdc_port_probe(struct vio_dev *vdev, | 745 | static int __devinit vdc_port_probe(struct vio_dev *vdev, |
751 | const struct vio_device_id *id) | 746 | const struct vio_device_id *id) |
752 | { | 747 | { |
753 | struct mdesc_handle *hp; | 748 | struct mdesc_handle *hp; |
754 | struct vdc_port *port; | 749 | struct vdc_port *port; |
755 | unsigned long flags; | ||
756 | struct vdc *vp; | ||
757 | const u64 *port_id; | 750 | const u64 *port_id; |
758 | int err; | 751 | int err; |
759 | 752 | ||
760 | vp = dev_get_drvdata(vdev->dev.parent); | 753 | print_version(); |
761 | if (!vp) { | ||
762 | printk(KERN_ERR PFX "Cannot find port parent vdc.\n"); | ||
763 | return -ENODEV; | ||
764 | } | ||
765 | 754 | ||
766 | hp = mdesc_grab(); | 755 | hp = mdesc_grab(); |
767 | 756 | ||
@@ -783,7 +772,6 @@ static int __devinit vdc_port_probe(struct vio_dev *vdev, | |||
783 | goto err_out_release_mdesc; | 772 | goto err_out_release_mdesc; |
784 | } | 773 | } |
785 | 774 | ||
786 | port->vp = vp; | ||
787 | port->dev_no = *port_id; | 775 | port->dev_no = *port_id; |
788 | 776 | ||
789 | if (port->dev_no >= 26) | 777 | if (port->dev_no >= 26) |
@@ -818,12 +806,6 @@ static int __devinit vdc_port_probe(struct vio_dev *vdev, | |||
818 | if (err) | 806 | if (err) |
819 | goto err_out_free_tx_ring; | 807 | goto err_out_free_tx_ring; |
820 | 808 | ||
821 | INIT_LIST_HEAD(&port->list); | ||
822 | |||
823 | spin_lock_irqsave(&vp->lock, flags); | ||
824 | list_add(&port->list, &vp->port_list); | ||
825 | spin_unlock_irqrestore(&vp->lock, flags); | ||
826 | |||
827 | dev_set_drvdata(&vdev->dev, port); | 809 | dev_set_drvdata(&vdev->dev, port); |
828 | 810 | ||
829 | mdesc_release(hp); | 811 | mdesc_release(hp); |
@@ -879,58 +861,6 @@ static struct vio_driver vdc_port_driver = { | |||
879 | } | 861 | } |
880 | }; | 862 | }; |
881 | 863 | ||
882 | static int __devinit vdc_probe(struct vio_dev *vdev, | ||
883 | const struct vio_device_id *id) | ||
884 | { | ||
885 | static int vdc_version_printed; | ||
886 | struct vdc *vp; | ||
887 | |||
888 | if (vdc_version_printed++ == 0) | ||
889 | printk(KERN_INFO "%s", version); | ||
890 | |||
891 | vp = kzalloc(sizeof(struct vdc), GFP_KERNEL); | ||
892 | if (!vp) | ||
893 | return -ENOMEM; | ||
894 | |||
895 | spin_lock_init(&vp->lock); | ||
896 | vp->dev = vdev; | ||
897 | INIT_LIST_HEAD(&vp->port_list); | ||
898 | |||
899 | dev_set_drvdata(&vdev->dev, vp); | ||
900 | |||
901 | return 0; | ||
902 | } | ||
903 | |||
904 | static int vdc_remove(struct vio_dev *vdev) | ||
905 | { | ||
906 | |||
907 | struct vdc *vp = dev_get_drvdata(&vdev->dev); | ||
908 | |||
909 | if (vp) { | ||
910 | kfree(vp); | ||
911 | dev_set_drvdata(&vdev->dev, NULL); | ||
912 | } | ||
913 | return 0; | ||
914 | } | ||
915 | |||
916 | static struct vio_device_id vdc_match[] = { | ||
917 | { | ||
918 | .type = "block", | ||
919 | }, | ||
920 | {}, | ||
921 | }; | ||
922 | MODULE_DEVICE_TABLE(vio, vdc_match); | ||
923 | |||
924 | static struct vio_driver vdc_driver = { | ||
925 | .id_table = vdc_match, | ||
926 | .probe = vdc_probe, | ||
927 | .remove = vdc_remove, | ||
928 | .driver = { | ||
929 | .name = "vdc", | ||
930 | .owner = THIS_MODULE, | ||
931 | } | ||
932 | }; | ||
933 | |||
934 | static int __init vdc_init(void) | 864 | static int __init vdc_init(void) |
935 | { | 865 | { |
936 | int err; | 866 | int err; |
@@ -940,19 +870,13 @@ static int __init vdc_init(void) | |||
940 | goto out_err; | 870 | goto out_err; |
941 | 871 | ||
942 | vdc_major = err; | 872 | vdc_major = err; |
943 | err = vio_register_driver(&vdc_driver); | ||
944 | if (err) | ||
945 | goto out_unregister_blkdev; | ||
946 | 873 | ||
947 | err = vio_register_driver(&vdc_port_driver); | 874 | err = vio_register_driver(&vdc_port_driver); |
948 | if (err) | 875 | if (err) |
949 | goto out_unregister_vdc; | 876 | goto out_unregister_blkdev; |
950 | 877 | ||
951 | return 0; | 878 | return 0; |
952 | 879 | ||
953 | out_unregister_vdc: | ||
954 | vio_unregister_driver(&vdc_driver); | ||
955 | |||
956 | out_unregister_blkdev: | 880 | out_unregister_blkdev: |
957 | unregister_blkdev(vdc_major, VDCBLK_NAME); | 881 | unregister_blkdev(vdc_major, VDCBLK_NAME); |
958 | vdc_major = 0; | 882 | vdc_major = 0; |
@@ -964,7 +888,6 @@ out_err: | |||
964 | static void __exit vdc_exit(void) | 888 | static void __exit vdc_exit(void) |
965 | { | 889 | { |
966 | vio_unregister_driver(&vdc_port_driver); | 890 | vio_unregister_driver(&vdc_port_driver); |
967 | vio_unregister_driver(&vdc_driver); | ||
968 | unregister_blkdev(vdc_major, VDCBLK_NAME); | 891 | unregister_blkdev(vdc_major, VDCBLK_NAME); |
969 | } | 892 | } |
970 | 893 | ||
diff --git a/drivers/net/sunvnet.c b/drivers/net/sunvnet.c index 8a667c13faef..b801e3b3a11a 100644 --- a/drivers/net/sunvnet.c +++ b/drivers/net/sunvnet.c | |||
@@ -12,6 +12,7 @@ | |||
12 | #include <linux/netdevice.h> | 12 | #include <linux/netdevice.h> |
13 | #include <linux/ethtool.h> | 13 | #include <linux/ethtool.h> |
14 | #include <linux/etherdevice.h> | 14 | #include <linux/etherdevice.h> |
15 | #include <linux/mutex.h> | ||
15 | 16 | ||
16 | #include <asm/vio.h> | 17 | #include <asm/vio.h> |
17 | #include <asm/ldc.h> | 18 | #include <asm/ldc.h> |
@@ -497,6 +498,8 @@ static void vnet_event(void *arg, int event) | |||
497 | vio_link_state_change(vio, event); | 498 | vio_link_state_change(vio, event); |
498 | spin_unlock_irqrestore(&vio->lock, flags); | 499 | spin_unlock_irqrestore(&vio->lock, flags); |
499 | 500 | ||
501 | if (event == LDC_EVENT_RESET) | ||
502 | vio_port_up(vio); | ||
500 | return; | 503 | return; |
501 | } | 504 | } |
502 | 505 | ||
@@ -875,6 +878,115 @@ err_out: | |||
875 | return err; | 878 | return err; |
876 | } | 879 | } |
877 | 880 | ||
881 | static LIST_HEAD(vnet_list); | ||
882 | static DEFINE_MUTEX(vnet_list_mutex); | ||
883 | |||
884 | static struct vnet * __devinit vnet_new(const u64 *local_mac) | ||
885 | { | ||
886 | struct net_device *dev; | ||
887 | struct vnet *vp; | ||
888 | int err, i; | ||
889 | |||
890 | dev = alloc_etherdev(sizeof(*vp)); | ||
891 | if (!dev) { | ||
892 | printk(KERN_ERR PFX "Etherdev alloc failed, aborting.\n"); | ||
893 | return ERR_PTR(-ENOMEM); | ||
894 | } | ||
895 | |||
896 | for (i = 0; i < ETH_ALEN; i++) | ||
897 | dev->dev_addr[i] = (*local_mac >> (5 - i) * 8) & 0xff; | ||
898 | |||
899 | memcpy(dev->perm_addr, dev->dev_addr, dev->addr_len); | ||
900 | |||
901 | vp = netdev_priv(dev); | ||
902 | |||
903 | spin_lock_init(&vp->lock); | ||
904 | vp->dev = dev; | ||
905 | |||
906 | INIT_LIST_HEAD(&vp->port_list); | ||
907 | for (i = 0; i < VNET_PORT_HASH_SIZE; i++) | ||
908 | INIT_HLIST_HEAD(&vp->port_hash[i]); | ||
909 | INIT_LIST_HEAD(&vp->list); | ||
910 | vp->local_mac = *local_mac; | ||
911 | |||
912 | dev->open = vnet_open; | ||
913 | dev->stop = vnet_close; | ||
914 | dev->set_multicast_list = vnet_set_rx_mode; | ||
915 | dev->set_mac_address = vnet_set_mac_addr; | ||
916 | dev->tx_timeout = vnet_tx_timeout; | ||
917 | dev->ethtool_ops = &vnet_ethtool_ops; | ||
918 | dev->watchdog_timeo = VNET_TX_TIMEOUT; | ||
919 | dev->change_mtu = vnet_change_mtu; | ||
920 | dev->hard_start_xmit = vnet_start_xmit; | ||
921 | |||
922 | err = register_netdev(dev); | ||
923 | if (err) { | ||
924 | printk(KERN_ERR PFX "Cannot register net device, " | ||
925 | "aborting.\n"); | ||
926 | goto err_out_free_dev; | ||
927 | } | ||
928 | |||
929 | printk(KERN_INFO "%s: Sun LDOM vnet ", dev->name); | ||
930 | |||
931 | for (i = 0; i < 6; i++) | ||
932 | printk("%2.2x%c", dev->dev_addr[i], i == 5 ? '\n' : ':'); | ||
933 | |||
934 | list_add(&vp->list, &vnet_list); | ||
935 | |||
936 | return vp; | ||
937 | |||
938 | err_out_free_dev: | ||
939 | free_netdev(dev); | ||
940 | |||
941 | return ERR_PTR(err); | ||
942 | } | ||
943 | |||
944 | static struct vnet * __devinit vnet_find_or_create(const u64 *local_mac) | ||
945 | { | ||
946 | struct vnet *iter, *vp; | ||
947 | |||
948 | mutex_lock(&vnet_list_mutex); | ||
949 | vp = NULL; | ||
950 | list_for_each_entry(iter, &vnet_list, list) { | ||
951 | if (iter->local_mac == *local_mac) { | ||
952 | vp = iter; | ||
953 | break; | ||
954 | } | ||
955 | } | ||
956 | if (!vp) | ||
957 | vp = vnet_new(local_mac); | ||
958 | mutex_unlock(&vnet_list_mutex); | ||
959 | |||
960 | return vp; | ||
961 | } | ||
962 | |||
963 | static const char *local_mac_prop = "local-mac-address"; | ||
964 | |||
965 | static struct vnet * __devinit vnet_find_parent(struct mdesc_handle *hp, | ||
966 | u64 port_node) | ||
967 | { | ||
968 | const u64 *local_mac = NULL; | ||
969 | u64 a; | ||
970 | |||
971 | mdesc_for_each_arc(a, hp, port_node, MDESC_ARC_TYPE_BACK) { | ||
972 | u64 target = mdesc_arc_target(hp, a); | ||
973 | const char *name; | ||
974 | |||
975 | name = mdesc_get_property(hp, target, "name", NULL); | ||
976 | if (!name || strcmp(name, "network")) | ||
977 | continue; | ||
978 | |||
979 | local_mac = mdesc_get_property(hp, target, | ||
980 | local_mac_prop, NULL); | ||
981 | if (local_mac) | ||
982 | break; | ||
983 | } | ||
984 | if (!local_mac) | ||
985 | return ERR_PTR(-ENODEV); | ||
986 | |||
987 | return vnet_find_or_create(local_mac); | ||
988 | } | ||
989 | |||
878 | static struct ldc_channel_config vnet_ldc_cfg = { | 990 | static struct ldc_channel_config vnet_ldc_cfg = { |
879 | .event = vnet_event, | 991 | .event = vnet_event, |
880 | .mtu = 64, | 992 | .mtu = 64, |
@@ -887,6 +999,14 @@ static struct vio_driver_ops vnet_vio_ops = { | |||
887 | .handshake_complete = vnet_handshake_complete, | 999 | .handshake_complete = vnet_handshake_complete, |
888 | }; | 1000 | }; |
889 | 1001 | ||
1002 | static void print_version(void) | ||
1003 | { | ||
1004 | static int version_printed; | ||
1005 | |||
1006 | if (version_printed++ == 0) | ||
1007 | printk(KERN_INFO "%s", version); | ||
1008 | } | ||
1009 | |||
890 | const char *remote_macaddr_prop = "remote-mac-address"; | 1010 | const char *remote_macaddr_prop = "remote-mac-address"; |
891 | 1011 | ||
892 | static int __devinit vnet_port_probe(struct vio_dev *vdev, | 1012 | static int __devinit vnet_port_probe(struct vio_dev *vdev, |
@@ -899,14 +1019,17 @@ static int __devinit vnet_port_probe(struct vio_dev *vdev, | |||
899 | const u64 *rmac; | 1019 | const u64 *rmac; |
900 | int len, i, err, switch_port; | 1020 | int len, i, err, switch_port; |
901 | 1021 | ||
902 | vp = dev_get_drvdata(vdev->dev.parent); | 1022 | print_version(); |
903 | if (!vp) { | ||
904 | printk(KERN_ERR PFX "Cannot find port parent vnet.\n"); | ||
905 | return -ENODEV; | ||
906 | } | ||
907 | 1023 | ||
908 | hp = mdesc_grab(); | 1024 | hp = mdesc_grab(); |
909 | 1025 | ||
1026 | vp = vnet_find_parent(hp, vdev->mp); | ||
1027 | if (IS_ERR(vp)) { | ||
1028 | printk(KERN_ERR PFX "Cannot find port parent vnet.\n"); | ||
1029 | err = PTR_ERR(vp); | ||
1030 | goto err_out_put_mdesc; | ||
1031 | } | ||
1032 | |||
910 | rmac = mdesc_get_property(hp, vdev->mp, remote_macaddr_prop, &len); | 1033 | rmac = mdesc_get_property(hp, vdev->mp, remote_macaddr_prop, &len); |
911 | err = -ENODEV; | 1034 | err = -ENODEV; |
912 | if (!rmac) { | 1035 | if (!rmac) { |
@@ -1025,139 +1148,14 @@ static struct vio_driver vnet_port_driver = { | |||
1025 | } | 1148 | } |
1026 | }; | 1149 | }; |
1027 | 1150 | ||
1028 | const char *local_mac_prop = "local-mac-address"; | ||
1029 | |||
1030 | static int __devinit vnet_probe(struct vio_dev *vdev, | ||
1031 | const struct vio_device_id *id) | ||
1032 | { | ||
1033 | static int vnet_version_printed; | ||
1034 | struct mdesc_handle *hp; | ||
1035 | struct net_device *dev; | ||
1036 | struct vnet *vp; | ||
1037 | const u64 *mac; | ||
1038 | int err, i, len; | ||
1039 | |||
1040 | if (vnet_version_printed++ == 0) | ||
1041 | printk(KERN_INFO "%s", version); | ||
1042 | |||
1043 | hp = mdesc_grab(); | ||
1044 | |||
1045 | mac = mdesc_get_property(hp, vdev->mp, local_mac_prop, &len); | ||
1046 | if (!mac) { | ||
1047 | printk(KERN_ERR PFX "vnet lacks %s property.\n", | ||
1048 | local_mac_prop); | ||
1049 | err = -ENODEV; | ||
1050 | goto err_out; | ||
1051 | } | ||
1052 | |||
1053 | dev = alloc_etherdev(sizeof(*vp)); | ||
1054 | if (!dev) { | ||
1055 | printk(KERN_ERR PFX "Etherdev alloc failed, aborting.\n"); | ||
1056 | err = -ENOMEM; | ||
1057 | goto err_out; | ||
1058 | } | ||
1059 | |||
1060 | for (i = 0; i < ETH_ALEN; i++) | ||
1061 | dev->dev_addr[i] = (*mac >> (5 - i) * 8) & 0xff; | ||
1062 | |||
1063 | memcpy(dev->perm_addr, dev->dev_addr, dev->addr_len); | ||
1064 | |||
1065 | SET_NETDEV_DEV(dev, &vdev->dev); | ||
1066 | |||
1067 | vp = netdev_priv(dev); | ||
1068 | |||
1069 | spin_lock_init(&vp->lock); | ||
1070 | vp->dev = dev; | ||
1071 | vp->vdev = vdev; | ||
1072 | |||
1073 | INIT_LIST_HEAD(&vp->port_list); | ||
1074 | for (i = 0; i < VNET_PORT_HASH_SIZE; i++) | ||
1075 | INIT_HLIST_HEAD(&vp->port_hash[i]); | ||
1076 | |||
1077 | dev->open = vnet_open; | ||
1078 | dev->stop = vnet_close; | ||
1079 | dev->set_multicast_list = vnet_set_rx_mode; | ||
1080 | dev->set_mac_address = vnet_set_mac_addr; | ||
1081 | dev->tx_timeout = vnet_tx_timeout; | ||
1082 | dev->ethtool_ops = &vnet_ethtool_ops; | ||
1083 | dev->watchdog_timeo = VNET_TX_TIMEOUT; | ||
1084 | dev->change_mtu = vnet_change_mtu; | ||
1085 | dev->hard_start_xmit = vnet_start_xmit; | ||
1086 | |||
1087 | err = register_netdev(dev); | ||
1088 | if (err) { | ||
1089 | printk(KERN_ERR PFX "Cannot register net device, " | ||
1090 | "aborting.\n"); | ||
1091 | goto err_out_free_dev; | ||
1092 | } | ||
1093 | |||
1094 | printk(KERN_INFO "%s: Sun LDOM vnet ", dev->name); | ||
1095 | |||
1096 | for (i = 0; i < 6; i++) | ||
1097 | printk("%2.2x%c", dev->dev_addr[i], i == 5 ? '\n' : ':'); | ||
1098 | |||
1099 | dev_set_drvdata(&vdev->dev, vp); | ||
1100 | |||
1101 | mdesc_release(hp); | ||
1102 | |||
1103 | return 0; | ||
1104 | |||
1105 | err_out_free_dev: | ||
1106 | free_netdev(dev); | ||
1107 | |||
1108 | err_out: | ||
1109 | mdesc_release(hp); | ||
1110 | return err; | ||
1111 | } | ||
1112 | |||
1113 | static int vnet_remove(struct vio_dev *vdev) | ||
1114 | { | ||
1115 | |||
1116 | struct vnet *vp = dev_get_drvdata(&vdev->dev); | ||
1117 | |||
1118 | if (vp) { | ||
1119 | /* XXX unregister port, or at least check XXX */ | ||
1120 | unregister_netdevice(vp->dev); | ||
1121 | dev_set_drvdata(&vdev->dev, NULL); | ||
1122 | } | ||
1123 | return 0; | ||
1124 | } | ||
1125 | |||
1126 | static struct vio_device_id vnet_match[] = { | ||
1127 | { | ||
1128 | .type = "network", | ||
1129 | }, | ||
1130 | {}, | ||
1131 | }; | ||
1132 | MODULE_DEVICE_TABLE(vio, vnet_match); | ||
1133 | |||
1134 | static struct vio_driver vnet_driver = { | ||
1135 | .id_table = vnet_match, | ||
1136 | .probe = vnet_probe, | ||
1137 | .remove = vnet_remove, | ||
1138 | .driver = { | ||
1139 | .name = "vnet", | ||
1140 | .owner = THIS_MODULE, | ||
1141 | } | ||
1142 | }; | ||
1143 | |||
1144 | static int __init vnet_init(void) | 1151 | static int __init vnet_init(void) |
1145 | { | 1152 | { |
1146 | int err = vio_register_driver(&vnet_driver); | 1153 | return vio_register_driver(&vnet_port_driver); |
1147 | |||
1148 | if (!err) { | ||
1149 | err = vio_register_driver(&vnet_port_driver); | ||
1150 | if (err) | ||
1151 | vio_unregister_driver(&vnet_driver); | ||
1152 | } | ||
1153 | |||
1154 | return err; | ||
1155 | } | 1154 | } |
1156 | 1155 | ||
1157 | static void __exit vnet_exit(void) | 1156 | static void __exit vnet_exit(void) |
1158 | { | 1157 | { |
1159 | vio_unregister_driver(&vnet_port_driver); | 1158 | vio_unregister_driver(&vnet_port_driver); |
1160 | vio_unregister_driver(&vnet_driver); | ||
1161 | } | 1159 | } |
1162 | 1160 | ||
1163 | module_init(vnet_init); | 1161 | module_init(vnet_init); |
diff --git a/drivers/net/sunvnet.h b/drivers/net/sunvnet.h index 1c887302d46d..7d3a0cac727b 100644 --- a/drivers/net/sunvnet.h +++ b/drivers/net/sunvnet.h | |||
@@ -60,11 +60,13 @@ struct vnet { | |||
60 | struct net_device *dev; | 60 | struct net_device *dev; |
61 | 61 | ||
62 | u32 msg_enable; | 62 | u32 msg_enable; |
63 | struct vio_dev *vdev; | ||
64 | 63 | ||
65 | struct list_head port_list; | 64 | struct list_head port_list; |
66 | 65 | ||
67 | struct hlist_head port_hash[VNET_PORT_HASH_SIZE]; | 66 | struct hlist_head port_hash[VNET_PORT_HASH_SIZE]; |
67 | |||
68 | struct list_head list; | ||
69 | u64 local_mac; | ||
68 | }; | 70 | }; |
69 | 71 | ||
70 | #endif /* _SUNVNET_H */ | 72 | #endif /* _SUNVNET_H */ |
diff --git a/include/asm-sparc64/io.h b/include/asm-sparc64/io.h index ad595b679842..9565a892801e 100644 --- a/include/asm-sparc64/io.h +++ b/include/asm-sparc64/io.h | |||
@@ -14,11 +14,6 @@ | |||
14 | #define __SLOW_DOWN_IO do { } while (0) | 14 | #define __SLOW_DOWN_IO do { } while (0) |
15 | #define SLOW_DOWN_IO do { } while (0) | 15 | #define SLOW_DOWN_IO do { } while (0) |
16 | 16 | ||
17 | extern unsigned long virt_to_bus_not_defined_use_pci_map(volatile void *addr); | ||
18 | #define virt_to_bus virt_to_bus_not_defined_use_pci_map | ||
19 | extern unsigned long bus_to_virt_not_defined_use_pci_map(volatile void *addr); | ||
20 | #define bus_to_virt bus_to_virt_not_defined_use_pci_map | ||
21 | |||
22 | /* BIO layer definitions. */ | 17 | /* BIO layer definitions. */ |
23 | extern unsigned long kern_base, kern_size; | 18 | extern unsigned long kern_base, kern_size; |
24 | #define page_to_phys(page) (page_to_pfn(page) << PAGE_SHIFT) | 19 | #define page_to_phys(page) (page_to_pfn(page) << PAGE_SHIFT) |
diff --git a/include/asm-sparc64/mdesc.h b/include/asm-sparc64/mdesc.h index e97c43133752..1acc7272e537 100644 --- a/include/asm-sparc64/mdesc.h +++ b/include/asm-sparc64/mdesc.h | |||
@@ -61,6 +61,16 @@ extern u64 mdesc_arc_target(struct mdesc_handle *hp, u64 arc); | |||
61 | 61 | ||
62 | extern void mdesc_update(void); | 62 | extern void mdesc_update(void); |
63 | 63 | ||
64 | struct mdesc_notifier_client { | ||
65 | void (*add)(struct mdesc_handle *handle, u64 node); | ||
66 | void (*remove)(struct mdesc_handle *handle, u64 node); | ||
67 | |||
68 | const char *node_name; | ||
69 | struct mdesc_notifier_client *next; | ||
70 | }; | ||
71 | |||
72 | extern void mdesc_register_notifier(struct mdesc_notifier_client *client); | ||
73 | |||
64 | extern void mdesc_fill_in_cpu_data(cpumask_t mask); | 74 | extern void mdesc_fill_in_cpu_data(cpumask_t mask); |
65 | 75 | ||
66 | extern void sun4v_mdesc_init(void); | 76 | extern void sun4v_mdesc_init(void); |
diff --git a/include/asm-sparc64/vio.h b/include/asm-sparc64/vio.h index 83c96422e9d6..c0a8d4ed5bcb 100644 --- a/include/asm-sparc64/vio.h +++ b/include/asm-sparc64/vio.h | |||
@@ -264,7 +264,7 @@ static inline u32 vio_dring_avail(struct vio_dring_state *dr, | |||
264 | ((dr->prod - dr->cons) & (ring_size - 1))); | 264 | ((dr->prod - dr->cons) & (ring_size - 1))); |
265 | } | 265 | } |
266 | 266 | ||
267 | #define VIO_MAX_TYPE_LEN 64 | 267 | #define VIO_MAX_TYPE_LEN 32 |
268 | #define VIO_MAX_COMPAT_LEN 64 | 268 | #define VIO_MAX_COMPAT_LEN 64 |
269 | 269 | ||
270 | struct vio_dev { | 270 | struct vio_dev { |