diff options
author | Jan Dumon <j.dumon@option.com> | 2009-04-01 18:57:20 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2009-04-02 19:31:43 -0400 |
commit | 3b7d2b319db0ba1f6208ca58b297fb419301f85a (patch) | |
tree | ec1ec255d2e3b5d513b7c0f5791a3f7154632e8c /drivers/net/usb | |
parent | b6bc978b361bb9da7526a78b0a247bdd34984282 (diff) |
hso: fix for crash when unplugging the device
Changed the order in which things are freed. This fixes an oops when
unplugging the device while network traffic is ongoing.
Signed-off-by: Jan Dumon <j.dumon@option.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/usb')
-rw-r--r-- | drivers/net/usb/hso.c | 19 |
1 files changed, 11 insertions, 8 deletions
diff --git a/drivers/net/usb/hso.c b/drivers/net/usb/hso.c index 28d1424a3110..779a0078fcde 100644 --- a/drivers/net/usb/hso.c +++ b/drivers/net/usb/hso.c | |||
@@ -5,6 +5,7 @@ | |||
5 | * Copyright (C) 2008 Option International | 5 | * Copyright (C) 2008 Option International |
6 | * Filip Aben <f.aben@option.com> | 6 | * Filip Aben <f.aben@option.com> |
7 | * Denis Joseph Barrow <d.barow@option.com> | 7 | * Denis Joseph Barrow <d.barow@option.com> |
8 | * Jan Dumon <j.dumon@option.com> | ||
8 | * Copyright (C) 2007 Andrew Bird (Sphere Systems Ltd) | 9 | * Copyright (C) 2007 Andrew Bird (Sphere Systems Ltd) |
9 | * <ajb@spheresystems.co.uk> | 10 | * <ajb@spheresystems.co.uk> |
10 | * Copyright (C) 2008 Greg Kroah-Hartman <gregkh@suse.de> | 11 | * Copyright (C) 2008 Greg Kroah-Hartman <gregkh@suse.de> |
@@ -2417,20 +2418,22 @@ static void hso_free_net_device(struct hso_device *hso_dev) | |||
2417 | if (!hso_net) | 2418 | if (!hso_net) |
2418 | return; | 2419 | return; |
2419 | 2420 | ||
2421 | remove_net_device(hso_net->parent); | ||
2422 | |||
2423 | if (hso_net->net) { | ||
2424 | unregister_netdev(hso_net->net); | ||
2425 | free_netdev(hso_net->net); | ||
2426 | } | ||
2427 | |||
2420 | /* start freeing */ | 2428 | /* start freeing */ |
2421 | for (i = 0; i < MUX_BULK_RX_BUF_COUNT; i++) { | 2429 | for (i = 0; i < MUX_BULK_RX_BUF_COUNT; i++) { |
2422 | usb_free_urb(hso_net->mux_bulk_rx_urb_pool[i]); | 2430 | usb_free_urb(hso_net->mux_bulk_rx_urb_pool[i]); |
2423 | kfree(hso_net->mux_bulk_rx_buf_pool[i]); | 2431 | kfree(hso_net->mux_bulk_rx_buf_pool[i]); |
2432 | hso_net->mux_bulk_rx_buf_pool[i] = NULL; | ||
2424 | } | 2433 | } |
2425 | usb_free_urb(hso_net->mux_bulk_tx_urb); | 2434 | usb_free_urb(hso_net->mux_bulk_tx_urb); |
2426 | kfree(hso_net->mux_bulk_tx_buf); | 2435 | kfree(hso_net->mux_bulk_tx_buf); |
2427 | 2436 | hso_net->mux_bulk_tx_buf = NULL; | |
2428 | remove_net_device(hso_net->parent); | ||
2429 | |||
2430 | if (hso_net->net) { | ||
2431 | unregister_netdev(hso_net->net); | ||
2432 | free_netdev(hso_net->net); | ||
2433 | } | ||
2434 | 2437 | ||
2435 | kfree(hso_dev); | 2438 | kfree(hso_dev); |
2436 | } | 2439 | } |
@@ -2620,12 +2623,12 @@ static void hso_free_tiomget(struct hso_serial *serial) | |||
2620 | { | 2623 | { |
2621 | struct hso_tiocmget *tiocmget = serial->tiocmget; | 2624 | struct hso_tiocmget *tiocmget = serial->tiocmget; |
2622 | if (tiocmget) { | 2625 | if (tiocmget) { |
2623 | kfree(tiocmget); | ||
2624 | if (tiocmget->urb) { | 2626 | if (tiocmget->urb) { |
2625 | usb_free_urb(tiocmget->urb); | 2627 | usb_free_urb(tiocmget->urb); |
2626 | tiocmget->urb = NULL; | 2628 | tiocmget->urb = NULL; |
2627 | } | 2629 | } |
2628 | serial->tiocmget = NULL; | 2630 | serial->tiocmget = NULL; |
2631 | kfree(tiocmget); | ||
2629 | 2632 | ||
2630 | } | 2633 | } |
2631 | } | 2634 | } |