diff options
author | Pavel Roskin <proski@gnu.org> | 2006-04-07 04:10:55 -0400 |
---|---|---|
committer | John W. Linville <linville@tuxdriver.com> | 2006-04-24 16:15:52 -0400 |
commit | c6fb2e9abef894efc4870e4c1e3aa4365b830a11 (patch) | |
tree | ab262b6f480665fa6ea5b9bdc2a6d6383b0dc2f2 | |
parent | 3d529962217c3fec36f53f270a37e132b9763c65 (diff) |
[PATCH] orinoco: support PCI suspend/resume for Nortel, PLX and TMD adaptors
Copy PCI suspend/resume functions from orinoco_pci.c.
Signed-off-by: Pavel Roskin <proski@gnu.org>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
-rw-r--r-- | drivers/net/wireless/orinoco_nortel.c | 87 | ||||
-rw-r--r-- | drivers/net/wireless/orinoco_plx.c | 79 | ||||
-rw-r--r-- | drivers/net/wireless/orinoco_tmd.c | 79 |
3 files changed, 241 insertions, 4 deletions
diff --git a/drivers/net/wireless/orinoco_nortel.c b/drivers/net/wireless/orinoco_nortel.c index d1a670b35338..3fff013f6788 100644 --- a/drivers/net/wireless/orinoco_nortel.c +++ b/drivers/net/wireless/orinoco_nortel.c | |||
@@ -263,6 +263,83 @@ static void __devexit nortel_pci_remove_one(struct pci_dev *pdev) | |||
263 | pci_disable_device(pdev); | 263 | pci_disable_device(pdev); |
264 | } | 264 | } |
265 | 265 | ||
266 | static int orinoco_nortel_suspend(struct pci_dev *pdev, pm_message_t state) | ||
267 | { | ||
268 | struct net_device *dev = pci_get_drvdata(pdev); | ||
269 | struct orinoco_private *priv = netdev_priv(dev); | ||
270 | unsigned long flags; | ||
271 | int err; | ||
272 | |||
273 | err = orinoco_lock(priv, &flags); | ||
274 | if (err) { | ||
275 | printk(KERN_ERR "%s: cannot lock hardware for suspend\n", | ||
276 | dev->name); | ||
277 | return err; | ||
278 | } | ||
279 | |||
280 | err = __orinoco_down(dev); | ||
281 | if (err) | ||
282 | printk(KERN_WARNING "%s: error %d bringing interface down " | ||
283 | "for suspend\n", dev->name, err); | ||
284 | |||
285 | netif_device_detach(dev); | ||
286 | |||
287 | priv->hw_unavailable++; | ||
288 | |||
289 | orinoco_unlock(priv, &flags); | ||
290 | |||
291 | free_irq(pdev->irq, dev); | ||
292 | pci_save_state(pdev); | ||
293 | pci_disable_device(pdev); | ||
294 | pci_set_power_state(pdev, PCI_D3hot); | ||
295 | |||
296 | return 0; | ||
297 | } | ||
298 | |||
299 | static int orinoco_nortel_resume(struct pci_dev *pdev) | ||
300 | { | ||
301 | struct net_device *dev = pci_get_drvdata(pdev); | ||
302 | struct orinoco_private *priv = netdev_priv(dev); | ||
303 | unsigned long flags; | ||
304 | int err; | ||
305 | |||
306 | pci_set_power_state(pdev, 0); | ||
307 | pci_enable_device(pdev); | ||
308 | pci_restore_state(pdev); | ||
309 | |||
310 | err = request_irq(pdev->irq, orinoco_interrupt, SA_SHIRQ, | ||
311 | dev->name, dev); | ||
312 | if (err) { | ||
313 | printk(KERN_ERR "%s: cannot re-allocate IRQ on resume\n", | ||
314 | dev->name); | ||
315 | pci_disable_device(pdev); | ||
316 | return -EBUSY; | ||
317 | } | ||
318 | |||
319 | err = orinoco_reinit_firmware(dev); | ||
320 | if (err) { | ||
321 | printk(KERN_ERR "%s: error %d re-initializing firmware " | ||
322 | "on resume\n", dev->name, err); | ||
323 | return err; | ||
324 | } | ||
325 | |||
326 | spin_lock_irqsave(&priv->lock, flags); | ||
327 | |||
328 | netif_device_attach(dev); | ||
329 | |||
330 | priv->hw_unavailable--; | ||
331 | |||
332 | if (priv->open && (! priv->hw_unavailable)) { | ||
333 | err = __orinoco_up(dev); | ||
334 | if (err) | ||
335 | printk(KERN_ERR "%s: Error %d restarting card on resume\n", | ||
336 | dev->name, err); | ||
337 | } | ||
338 | |||
339 | spin_unlock_irqrestore(&priv->lock, flags); | ||
340 | |||
341 | return 0; | ||
342 | } | ||
266 | 343 | ||
267 | static struct pci_device_id nortel_pci_id_table[] = { | 344 | static struct pci_device_id nortel_pci_id_table[] = { |
268 | /* Nortel emobility PCI */ | 345 | /* Nortel emobility PCI */ |
@@ -275,10 +352,12 @@ static struct pci_device_id nortel_pci_id_table[] = { | |||
275 | MODULE_DEVICE_TABLE(pci, nortel_pci_id_table); | 352 | MODULE_DEVICE_TABLE(pci, nortel_pci_id_table); |
276 | 353 | ||
277 | static struct pci_driver nortel_pci_driver = { | 354 | static struct pci_driver nortel_pci_driver = { |
278 | .name = DRIVER_NAME, | 355 | .name = DRIVER_NAME, |
279 | .id_table = nortel_pci_id_table, | 356 | .id_table = nortel_pci_id_table, |
280 | .probe = nortel_pci_init_one, | 357 | .probe = nortel_pci_init_one, |
281 | .remove = __devexit_p(nortel_pci_remove_one), | 358 | .remove = __devexit_p(nortel_pci_remove_one), |
359 | .suspend = orinoco_nortel_suspend, | ||
360 | .resume = orinoco_nortel_resume, | ||
282 | }; | 361 | }; |
283 | 362 | ||
284 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION | 363 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION |
diff --git a/drivers/net/wireless/orinoco_plx.c b/drivers/net/wireless/orinoco_plx.c index 210e73776545..3fe7a2f37896 100644 --- a/drivers/net/wireless/orinoco_plx.c +++ b/drivers/net/wireless/orinoco_plx.c | |||
@@ -343,6 +343,83 @@ static void __devexit orinoco_plx_remove_one(struct pci_dev *pdev) | |||
343 | pci_disable_device(pdev); | 343 | pci_disable_device(pdev); |
344 | } | 344 | } |
345 | 345 | ||
346 | static int orinoco_plx_suspend(struct pci_dev *pdev, pm_message_t state) | ||
347 | { | ||
348 | struct net_device *dev = pci_get_drvdata(pdev); | ||
349 | struct orinoco_private *priv = netdev_priv(dev); | ||
350 | unsigned long flags; | ||
351 | int err; | ||
352 | |||
353 | err = orinoco_lock(priv, &flags); | ||
354 | if (err) { | ||
355 | printk(KERN_ERR "%s: cannot lock hardware for suspend\n", | ||
356 | dev->name); | ||
357 | return err; | ||
358 | } | ||
359 | |||
360 | err = __orinoco_down(dev); | ||
361 | if (err) | ||
362 | printk(KERN_WARNING "%s: error %d bringing interface down " | ||
363 | "for suspend\n", dev->name, err); | ||
364 | |||
365 | netif_device_detach(dev); | ||
366 | |||
367 | priv->hw_unavailable++; | ||
368 | |||
369 | orinoco_unlock(priv, &flags); | ||
370 | |||
371 | free_irq(pdev->irq, dev); | ||
372 | pci_save_state(pdev); | ||
373 | pci_disable_device(pdev); | ||
374 | pci_set_power_state(pdev, PCI_D3hot); | ||
375 | |||
376 | return 0; | ||
377 | } | ||
378 | |||
379 | static int orinoco_plx_resume(struct pci_dev *pdev) | ||
380 | { | ||
381 | struct net_device *dev = pci_get_drvdata(pdev); | ||
382 | struct orinoco_private *priv = netdev_priv(dev); | ||
383 | unsigned long flags; | ||
384 | int err; | ||
385 | |||
386 | pci_set_power_state(pdev, 0); | ||
387 | pci_enable_device(pdev); | ||
388 | pci_restore_state(pdev); | ||
389 | |||
390 | err = request_irq(pdev->irq, orinoco_interrupt, SA_SHIRQ, | ||
391 | dev->name, dev); | ||
392 | if (err) { | ||
393 | printk(KERN_ERR "%s: cannot re-allocate IRQ on resume\n", | ||
394 | dev->name); | ||
395 | pci_disable_device(pdev); | ||
396 | return -EBUSY; | ||
397 | } | ||
398 | |||
399 | err = orinoco_reinit_firmware(dev); | ||
400 | if (err) { | ||
401 | printk(KERN_ERR "%s: error %d re-initializing firmware " | ||
402 | "on resume\n", dev->name, err); | ||
403 | return err; | ||
404 | } | ||
405 | |||
406 | spin_lock_irqsave(&priv->lock, flags); | ||
407 | |||
408 | netif_device_attach(dev); | ||
409 | |||
410 | priv->hw_unavailable--; | ||
411 | |||
412 | if (priv->open && (! priv->hw_unavailable)) { | ||
413 | err = __orinoco_up(dev); | ||
414 | if (err) | ||
415 | printk(KERN_ERR "%s: Error %d restarting card on resume\n", | ||
416 | dev->name, err); | ||
417 | } | ||
418 | |||
419 | spin_unlock_irqrestore(&priv->lock, flags); | ||
420 | |||
421 | return 0; | ||
422 | } | ||
346 | 423 | ||
347 | static struct pci_device_id orinoco_plx_pci_id_table[] = { | 424 | static struct pci_device_id orinoco_plx_pci_id_table[] = { |
348 | {0x111a, 0x1023, PCI_ANY_ID, PCI_ANY_ID,}, /* Siemens SpeedStream SS1023 */ | 425 | {0x111a, 0x1023, PCI_ANY_ID, PCI_ANY_ID,}, /* Siemens SpeedStream SS1023 */ |
@@ -369,6 +446,8 @@ static struct pci_driver orinoco_plx_driver = { | |||
369 | .id_table = orinoco_plx_pci_id_table, | 446 | .id_table = orinoco_plx_pci_id_table, |
370 | .probe = orinoco_plx_init_one, | 447 | .probe = orinoco_plx_init_one, |
371 | .remove = __devexit_p(orinoco_plx_remove_one), | 448 | .remove = __devexit_p(orinoco_plx_remove_one), |
449 | .suspend = orinoco_plx_suspend, | ||
450 | .resume = orinoco_plx_resume, | ||
372 | }; | 451 | }; |
373 | 452 | ||
374 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION | 453 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION |
diff --git a/drivers/net/wireless/orinoco_tmd.c b/drivers/net/wireless/orinoco_tmd.c index 5e68b7026186..b74807d4141f 100644 --- a/drivers/net/wireless/orinoco_tmd.c +++ b/drivers/net/wireless/orinoco_tmd.c | |||
@@ -215,6 +215,83 @@ static void __devexit orinoco_tmd_remove_one(struct pci_dev *pdev) | |||
215 | pci_disable_device(pdev); | 215 | pci_disable_device(pdev); |
216 | } | 216 | } |
217 | 217 | ||
218 | static int orinoco_tmd_suspend(struct pci_dev *pdev, pm_message_t state) | ||
219 | { | ||
220 | struct net_device *dev = pci_get_drvdata(pdev); | ||
221 | struct orinoco_private *priv = netdev_priv(dev); | ||
222 | unsigned long flags; | ||
223 | int err; | ||
224 | |||
225 | err = orinoco_lock(priv, &flags); | ||
226 | if (err) { | ||
227 | printk(KERN_ERR "%s: cannot lock hardware for suspend\n", | ||
228 | dev->name); | ||
229 | return err; | ||
230 | } | ||
231 | |||
232 | err = __orinoco_down(dev); | ||
233 | if (err) | ||
234 | printk(KERN_WARNING "%s: error %d bringing interface down " | ||
235 | "for suspend\n", dev->name, err); | ||
236 | |||
237 | netif_device_detach(dev); | ||
238 | |||
239 | priv->hw_unavailable++; | ||
240 | |||
241 | orinoco_unlock(priv, &flags); | ||
242 | |||
243 | free_irq(pdev->irq, dev); | ||
244 | pci_save_state(pdev); | ||
245 | pci_disable_device(pdev); | ||
246 | pci_set_power_state(pdev, PCI_D3hot); | ||
247 | |||
248 | return 0; | ||
249 | } | ||
250 | |||
251 | static int orinoco_tmd_resume(struct pci_dev *pdev) | ||
252 | { | ||
253 | struct net_device *dev = pci_get_drvdata(pdev); | ||
254 | struct orinoco_private *priv = netdev_priv(dev); | ||
255 | unsigned long flags; | ||
256 | int err; | ||
257 | |||
258 | pci_set_power_state(pdev, 0); | ||
259 | pci_enable_device(pdev); | ||
260 | pci_restore_state(pdev); | ||
261 | |||
262 | err = request_irq(pdev->irq, orinoco_interrupt, SA_SHIRQ, | ||
263 | dev->name, dev); | ||
264 | if (err) { | ||
265 | printk(KERN_ERR "%s: cannot re-allocate IRQ on resume\n", | ||
266 | dev->name); | ||
267 | pci_disable_device(pdev); | ||
268 | return -EBUSY; | ||
269 | } | ||
270 | |||
271 | err = orinoco_reinit_firmware(dev); | ||
272 | if (err) { | ||
273 | printk(KERN_ERR "%s: error %d re-initializing firmware " | ||
274 | "on resume\n", dev->name, err); | ||
275 | return err; | ||
276 | } | ||
277 | |||
278 | spin_lock_irqsave(&priv->lock, flags); | ||
279 | |||
280 | netif_device_attach(dev); | ||
281 | |||
282 | priv->hw_unavailable--; | ||
283 | |||
284 | if (priv->open && (! priv->hw_unavailable)) { | ||
285 | err = __orinoco_up(dev); | ||
286 | if (err) | ||
287 | printk(KERN_ERR "%s: Error %d restarting card on resume\n", | ||
288 | dev->name, err); | ||
289 | } | ||
290 | |||
291 | spin_unlock_irqrestore(&priv->lock, flags); | ||
292 | |||
293 | return 0; | ||
294 | } | ||
218 | 295 | ||
219 | static struct pci_device_id orinoco_tmd_pci_id_table[] = { | 296 | static struct pci_device_id orinoco_tmd_pci_id_table[] = { |
220 | {0x15e8, 0x0131, PCI_ANY_ID, PCI_ANY_ID,}, /* NDC and OEMs, e.g. pheecom */ | 297 | {0x15e8, 0x0131, PCI_ANY_ID, PCI_ANY_ID,}, /* NDC and OEMs, e.g. pheecom */ |
@@ -228,6 +305,8 @@ static struct pci_driver orinoco_tmd_driver = { | |||
228 | .id_table = orinoco_tmd_pci_id_table, | 305 | .id_table = orinoco_tmd_pci_id_table, |
229 | .probe = orinoco_tmd_init_one, | 306 | .probe = orinoco_tmd_init_one, |
230 | .remove = __devexit_p(orinoco_tmd_remove_one), | 307 | .remove = __devexit_p(orinoco_tmd_remove_one), |
308 | .suspend = orinoco_tmd_suspend, | ||
309 | .resume = orinoco_tmd_resume, | ||
231 | }; | 310 | }; |
232 | 311 | ||
233 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION | 312 | static char version[] __initdata = DRIVER_NAME " " DRIVER_VERSION |