aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
diff options
context:
space:
mode:
authorHante Meuleman <meuleman@broadcom.com>2012-11-14 21:46:18 -0500
committerJohn W. Linville <linville@tuxdriver.com>2012-11-16 14:28:59 -0500
commit37ac5780e08e4e3ce67e8355e52d71324e9c11cd (patch)
tree1b361725247c8b053c3f6405283250f9c8fcb482 /drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
parent1799ddf18597da5aa1319b089736aafd05481774 (diff)
brcmfmac: Handle mmc exceptions during init correct.
when brcmf_sdbrcm_probe_attach results in error then cleanup will result in null pointer access. In brcmf_sdbrcm_release and in brcmf_ops_sdio_remove. This patch fixes order of init and de-init. Reviewed-by: Arend Van Spriel <arend@broadcom.com> Reviewed-by: Pieter-Paul Giesberts <pieterpg@broadcom.com> Signed-off-by: Hante Meuleman <meuleman@broadcom.com> Signed-off-by: Franky Lin <frankyl@broadcom.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c')
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c17
1 files changed, 9 insertions, 8 deletions
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c b/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
index e2351a7969a7..40a37ac04970 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/dhd_sdio.c
@@ -3867,7 +3867,8 @@ static void brcmf_sdbrcm_release(struct brcmf_sdio *bus)
3867 brcmf_sdio_intr_unregister(bus->sdiodev); 3867 brcmf_sdio_intr_unregister(bus->sdiodev);
3868 3868
3869 cancel_work_sync(&bus->datawork); 3869 cancel_work_sync(&bus->datawork);
3870 destroy_workqueue(bus->brcmf_wq); 3870 if (bus->brcmf_wq)
3871 destroy_workqueue(bus->brcmf_wq);
3871 3872
3872 if (bus->sdiodev->bus_if->drvr) { 3873 if (bus->sdiodev->bus_if->drvr) {
3873 brcmf_detach(bus->sdiodev->dev); 3874 brcmf_detach(bus->sdiodev->dev);
@@ -3909,6 +3910,13 @@ void *brcmf_sdbrcm_probe(u32 regsva, struct brcmf_sdio_dev *sdiodev)
3909 bus->txminmax = BRCMF_TXMINMAX; 3910 bus->txminmax = BRCMF_TXMINMAX;
3910 bus->tx_seq = SDPCM_SEQUENCE_WRAP - 1; 3911 bus->tx_seq = SDPCM_SEQUENCE_WRAP - 1;
3911 3912
3913 INIT_WORK(&bus->datawork, brcmf_sdio_dataworker);
3914 bus->brcmf_wq = create_singlethread_workqueue("brcmf_wq");
3915 if (bus->brcmf_wq == NULL) {
3916 brcmf_dbg(ERROR, "insufficient memory to create txworkqueue\n");
3917 goto fail;
3918 }
3919
3912 /* attempt to attach to the dongle */ 3920 /* attempt to attach to the dongle */
3913 if (!(brcmf_sdbrcm_probe_attach(bus, regsva))) { 3921 if (!(brcmf_sdbrcm_probe_attach(bus, regsva))) {
3914 brcmf_dbg(ERROR, "brcmf_sdbrcm_probe_attach failed\n"); 3922 brcmf_dbg(ERROR, "brcmf_sdbrcm_probe_attach failed\n");
@@ -3920,13 +3928,6 @@ void *brcmf_sdbrcm_probe(u32 regsva, struct brcmf_sdio_dev *sdiodev)
3920 init_waitqueue_head(&bus->ctrl_wait); 3928 init_waitqueue_head(&bus->ctrl_wait);
3921 init_waitqueue_head(&bus->dcmd_resp_wait); 3929 init_waitqueue_head(&bus->dcmd_resp_wait);
3922 3930
3923 bus->brcmf_wq = create_singlethread_workqueue("brcmf_wq");
3924 if (bus->brcmf_wq == NULL) {
3925 brcmf_dbg(ERROR, "insufficient memory to create txworkqueue\n");
3926 goto fail;
3927 }
3928 INIT_WORK(&bus->datawork, brcmf_sdio_dataworker);
3929
3930 /* Set up the watchdog timer */ 3931 /* Set up the watchdog timer */
3931 init_timer(&bus->timer); 3932 init_timer(&bus->timer);
3932 bus->timer.data = (unsigned long)bus; 3933 bus->timer.data = (unsigned long)bus;