From c9e9be9d3afa44d8775583c36fcab3c0bc552fe7 Mon Sep 17 00:00:00 2001 From: nbd Date: Sat, 13 Oct 2007 10:02:27 +0000 Subject: Finally fix the annoying BCM4704 segfault issues (#2035) - tested with WL-500gP Thanks to jhansen and Wolfram Joost for the fixes and to ryd for the test hardware. Seems like the user space segfaults actually came from this patch: http://lkml.org/lkml/2006/12/12/158 git-svn-id: svn://svn.openwrt.org/openwrt/trunk@9285 3c298f89-4303-0410-b956-a3cf2f4a3e73 --- .../patches-2.6.23/120-b44_ssb_support.patch | 96 ++++++++++++---------- 1 file changed, 52 insertions(+), 44 deletions(-) (limited to 'target/linux/brcm47xx/patches-2.6.23/120-b44_ssb_support.patch') diff --git a/target/linux/brcm47xx/patches-2.6.23/120-b44_ssb_support.patch b/target/linux/brcm47xx/patches-2.6.23/120-b44_ssb_support.patch index e8114c6bb..06865cff3 100644 --- a/target/linux/brcm47xx/patches-2.6.23/120-b44_ssb_support.patch +++ b/target/linux/brcm47xx/patches-2.6.23/120-b44_ssb_support.patch @@ -1,7 +1,7 @@ Index: linux-2.6.23/drivers/net/b44.c =================================================================== ---- linux-2.6.23.orig/drivers/net/b44.c 2007-10-09 22:31:38.000000000 +0200 -+++ linux-2.6.23/drivers/net/b44.c 2007-10-13 02:46:38.946989430 +0200 +--- linux-2.6.23.orig/drivers/net/b44.c 2007-10-13 10:58:27.872607266 +0200 ++++ linux-2.6.23/drivers/net/b44.c 2007-10-13 11:00:46.916530927 +0200 @@ -1,7 +1,9 @@ -/* b44.c: Broadcom 4400 device driver. +/* b44.c: Broadcom 4400/47xx device driver. @@ -107,7 +107,7 @@ Index: linux-2.6.23/drivers/net/b44.c + unsigned long offset, + enum dma_data_direction dir) +{ -+ dma_sync_single_range_for_device(&sdev->dev, dma_base, ++ dma_sync_single_range_for_device(sdev->dev, dma_base, + offset & dma_desc_align_mask, + dma_desc_sync_size, dir); +} @@ -117,7 +117,7 @@ Index: linux-2.6.23/drivers/net/b44.c + unsigned long offset, + enum dma_data_direction dir) +{ -+ dma_sync_single_range_for_cpu(&sdev->dev, dma_base, ++ dma_sync_single_range_for_cpu(sdev->dev, dma_base, + offset & dma_desc_align_mask, + dma_desc_sync_size, dir); } @@ -370,7 +370,7 @@ Index: linux-2.6.23/drivers/net/b44.c BUG_ON(skb == NULL); - pci_unmap_single(bp->pdev, -+ dma_unmap_single(&bp->sdev->dev, ++ dma_unmap_single(bp->sdev->dev, pci_unmap_addr(rp, mapping), skb->len, - PCI_DMA_TODEVICE); @@ -383,7 +383,7 @@ Index: linux-2.6.23/drivers/net/b44.c return -ENOMEM; - mapping = pci_map_single(bp->pdev, skb->data, -+ mapping = dma_map_single(&bp->sdev->dev, skb->data, ++ mapping = dma_map_single(bp->sdev->dev, skb->data, RX_PKT_BUF_SZ, - PCI_DMA_FROMDEVICE); + DMA_FROM_DEVICE); @@ -395,13 +395,13 @@ Index: linux-2.6.23/drivers/net/b44.c /* Sigh... */ if (!dma_mapping_error(mapping)) - pci_unmap_single(bp->pdev, mapping, RX_PKT_BUF_SZ,PCI_DMA_FROMDEVICE); -+ dma_unmap_single(&bp->sdev->dev, mapping, RX_PKT_BUF_SZ,DMA_FROM_DEVICE); ++ dma_unmap_single(bp->sdev->dev, mapping, RX_PKT_BUF_SZ,DMA_FROM_DEVICE); dev_kfree_skb_any(skb); skb = __netdev_alloc_skb(bp->dev, RX_PKT_BUF_SZ, GFP_ATOMIC|GFP_DMA); if (skb == NULL) return -ENOMEM; - mapping = pci_map_single(bp->pdev, skb->data, -+ mapping = dma_map_single(&bp->sdev->dev, skb->data, ++ mapping = dma_map_single(bp->sdev->dev, skb->data, RX_PKT_BUF_SZ, - PCI_DMA_FROMDEVICE); + DMA_FROM_DEVICE); @@ -409,7 +409,7 @@ Index: linux-2.6.23/drivers/net/b44.c mapping + RX_PKT_BUF_SZ > DMA_30BIT_MASK) { if (!dma_mapping_error(mapping)) - pci_unmap_single(bp->pdev, mapping, RX_PKT_BUF_SZ,PCI_DMA_FROMDEVICE); -+ dma_unmap_single(&bp->sdev->dev, mapping, RX_PKT_BUF_SZ,DMA_FROM_DEVICE); ++ dma_unmap_single(bp->sdev->dev, mapping, RX_PKT_BUF_SZ,DMA_FROM_DEVICE); dev_kfree_skb_any(skb); return -ENOMEM; } @@ -451,7 +451,7 @@ Index: linux-2.6.23/drivers/net/b44.c + DMA_BIDIRECTIONAL); - pci_dma_sync_single_for_device(bp->pdev, le32_to_cpu(src_desc->addr), -+ dma_sync_single_for_device(&bp->sdev->dev, le32_to_cpu(src_desc->addr), ++ dma_sync_single_for_device(bp->sdev->dev, le32_to_cpu(src_desc->addr), RX_PKT_BUF_SZ, - PCI_DMA_FROMDEVICE); + DMA_FROM_DEVICE); @@ -463,7 +463,7 @@ Index: linux-2.6.23/drivers/net/b44.c u16 len; - pci_dma_sync_single_for_cpu(bp->pdev, map, -+ dma_sync_single_for_cpu(&bp->sdev->dev, map, ++ dma_sync_single_for_cpu(bp->sdev->dev, map, RX_PKT_BUF_SZ, - PCI_DMA_FROMDEVICE); + DMA_FROM_DEVICE); @@ -476,7 +476,7 @@ Index: linux-2.6.23/drivers/net/b44.c goto drop_it; - pci_unmap_single(bp->pdev, map, - skb_size, PCI_DMA_FROMDEVICE); -+ dma_unmap_single(&bp->sdev->dev, map, ++ dma_unmap_single(bp->sdev->dev, map, + skb_size, DMA_FROM_DEVICE); /* Leave out rx_header */ skb_put(skb, len + RX_PKT_OFFSET); @@ -486,14 +486,14 @@ Index: linux-2.6.23/drivers/net/b44.c } - mapping = pci_map_single(bp->pdev, skb->data, len, PCI_DMA_TODEVICE); -+ mapping = dma_map_single(&bp->sdev->dev, skb->data, len, DMA_TO_DEVICE); ++ mapping = dma_map_single(bp->sdev->dev, skb->data, len, DMA_TO_DEVICE); if (dma_mapping_error(mapping) || mapping + len > DMA_30BIT_MASK) { struct sk_buff *bounce_skb; /* Chip can't handle DMA to/from >1GB, use bounce buffer */ if (!dma_mapping_error(mapping)) - pci_unmap_single(bp->pdev, mapping, len, PCI_DMA_TODEVICE); -+ dma_unmap_single(&bp->sdev->dev, mapping, len, DMA_TO_DEVICE); ++ dma_unmap_single(bp->sdev->dev, mapping, len, DMA_TO_DEVICE); bounce_skb = __dev_alloc_skb(len, GFP_ATOMIC | GFP_DMA); if (!bounce_skb) @@ -501,13 +501,13 @@ Index: linux-2.6.23/drivers/net/b44.c - mapping = pci_map_single(bp->pdev, bounce_skb->data, - len, PCI_DMA_TODEVICE); -+ mapping = dma_map_single(&bp->sdev->dev, bounce_skb->data, ++ mapping = dma_map_single(bp->sdev->dev, bounce_skb->data, + len, DMA_TO_DEVICE); if (dma_mapping_error(mapping) || mapping + len > DMA_30BIT_MASK) { if (!dma_mapping_error(mapping)) - pci_unmap_single(bp->pdev, mapping, - len, PCI_DMA_TODEVICE); -+ dma_unmap_single(&bp->sdev->dev, mapping, ++ dma_unmap_single(bp->sdev->dev, mapping, + len, DMA_TO_DEVICE); dev_kfree_skb_any(bounce_skb); goto err_out; @@ -530,7 +530,7 @@ Index: linux-2.6.23/drivers/net/b44.c if (rp->skb == NULL) continue; - pci_unmap_single(bp->pdev, -+ dma_unmap_single(&bp->sdev->dev, ++ dma_unmap_single(bp->sdev->dev, pci_unmap_addr(rp, mapping), RX_PKT_BUF_SZ, - PCI_DMA_FROMDEVICE); @@ -543,7 +543,7 @@ Index: linux-2.6.23/drivers/net/b44.c if (rp->skb == NULL) continue; - pci_unmap_single(bp->pdev, -+ dma_unmap_single(&bp->sdev->dev, ++ dma_unmap_single(bp->sdev->dev, pci_unmap_addr(rp, mapping), rp->skb->len, - PCI_DMA_TODEVICE); @@ -558,7 +558,7 @@ Index: linux-2.6.23/drivers/net/b44.c - dma_sync_single_for_device(&bp->pdev->dev, bp->rx_ring_dma, - DMA_TABLE_BYTES, - PCI_DMA_BIDIRECTIONAL); -+ dma_sync_single_for_device(&bp->sdev->dev, bp->rx_ring_dma, ++ dma_sync_single_for_device(bp->sdev->dev, bp->rx_ring_dma, + DMA_TABLE_BYTES, + DMA_BIDIRECTIONAL); @@ -566,7 +566,7 @@ Index: linux-2.6.23/drivers/net/b44.c - dma_sync_single_for_device(&bp->pdev->dev, bp->tx_ring_dma, - DMA_TABLE_BYTES, - PCI_DMA_TODEVICE); -+ dma_sync_single_for_device(&bp->sdev->dev, bp->tx_ring_dma, ++ dma_sync_single_for_device(bp->sdev->dev, bp->tx_ring_dma, + DMA_TABLE_BYTES, + DMA_TO_DEVICE); @@ -579,13 +579,13 @@ Index: linux-2.6.23/drivers/net/b44.c - dma_unmap_single(&bp->pdev->dev, bp->rx_ring_dma, - DMA_TABLE_BYTES, - DMA_BIDIRECTIONAL); -+ dma_unmap_single(&bp->sdev->dev, bp->rx_ring_dma, ++ dma_unmap_single(bp->sdev->dev, bp->rx_ring_dma, + DMA_TABLE_BYTES, + DMA_BIDIRECTIONAL); kfree(bp->rx_ring); } else - pci_free_consistent(bp->pdev, DMA_TABLE_BYTES, -+ dma_free_coherent(&bp->sdev->dev, DMA_TABLE_BYTES, ++ dma_free_coherent(bp->sdev->dev, DMA_TABLE_BYTES, bp->rx_ring, bp->rx_ring_dma); bp->rx_ring = NULL; bp->flags &= ~B44_FLAG_RX_RING_HACK; @@ -595,13 +595,13 @@ Index: linux-2.6.23/drivers/net/b44.c - dma_unmap_single(&bp->pdev->dev, bp->tx_ring_dma, - DMA_TABLE_BYTES, - DMA_TO_DEVICE); -+ dma_unmap_single(&bp->sdev->dev, bp->tx_ring_dma, ++ dma_unmap_single(bp->sdev->dev, bp->tx_ring_dma, + DMA_TABLE_BYTES, + DMA_TO_DEVICE); kfree(bp->tx_ring); } else - pci_free_consistent(bp->pdev, DMA_TABLE_BYTES, -+ dma_free_coherent(&bp->sdev->dev, DMA_TABLE_BYTES, ++ dma_free_coherent(bp->sdev->dev, DMA_TABLE_BYTES, bp->tx_ring, bp->tx_ring_dma); bp->tx_ring = NULL; bp->flags &= ~B44_FLAG_TX_RING_HACK; @@ -610,7 +610,7 @@ Index: linux-2.6.23/drivers/net/b44.c size = DMA_TABLE_BYTES; - bp->rx_ring = pci_alloc_consistent(bp->pdev, size, &bp->rx_ring_dma); -+ bp->rx_ring = dma_alloc_coherent(&bp->sdev->dev, size, &bp->rx_ring_dma, GFP_ATOMIC); ++ bp->rx_ring = dma_alloc_coherent(bp->sdev->dev, size, &bp->rx_ring_dma, GFP_ATOMIC); if (!bp->rx_ring) { /* Allocation may have failed due to pci_alloc_consistent insisting on use of GFP_DMA, which is more restrictive @@ -621,7 +621,7 @@ Index: linux-2.6.23/drivers/net/b44.c - rx_ring_dma = dma_map_single(&bp->pdev->dev, rx_ring, - DMA_TABLE_BYTES, - DMA_BIDIRECTIONAL); -+ rx_ring_dma = dma_map_single(&bp->sdev->dev, rx_ring, ++ rx_ring_dma = dma_map_single(bp->sdev->dev, rx_ring, + DMA_TABLE_BYTES, + DMA_BIDIRECTIONAL); @@ -632,7 +632,7 @@ Index: linux-2.6.23/drivers/net/b44.c } - bp->tx_ring = pci_alloc_consistent(bp->pdev, size, &bp->tx_ring_dma); -+ bp->tx_ring = dma_alloc_coherent(&bp->sdev->dev, size, &bp->tx_ring_dma, GFP_ATOMIC); ++ bp->tx_ring = dma_alloc_coherent(bp->sdev->dev, size, &bp->tx_ring_dma, GFP_ATOMIC); if (!bp->tx_ring) { - /* Allocation may have failed due to pci_alloc_consistent + /* Allocation may have failed due to dma_alloc_coherent @@ -646,7 +646,7 @@ Index: linux-2.6.23/drivers/net/b44.c - tx_ring_dma = dma_map_single(&bp->pdev->dev, tx_ring, - DMA_TABLE_BYTES, - DMA_TO_DEVICE); -+ tx_ring_dma = dma_map_single(&bp->sdev->dev, tx_ring, ++ tx_ring_dma = dma_map_single(bp->sdev->dev, tx_ring, + DMA_TABLE_BYTES, + DMA_TO_DEVICE); @@ -1115,7 +1115,7 @@ Index: linux-2.6.23/drivers/net/b44.c if (!is_valid_ether_addr(&bp->dev->dev_addr[0])){ printk(KERN_ERR PFX "Invalid MAC address found in EEPROM\n"); -@@ -2086,26 +2282,20 @@ +@@ -2086,103 +2282,52 @@ memcpy(bp->dev->perm_addr, bp->dev->dev_addr, bp->dev->addr_len); @@ -1131,7 +1131,7 @@ Index: linux-2.6.23/drivers/net/b44.c */ - if (ssb_get_core_rev(bp) >= 7) -+ if (bp->sdev->dev->id.revision >= 7) ++ if (bp->sdev->id.revision >= 7) bp->flags |= B44_FLAG_B0_ANDLATER; -out: @@ -1144,8 +1144,8 @@ Index: linux-2.6.23/drivers/net/b44.c + const struct ssb_device_id *ent) { static int b44_version_printed = 0; - unsigned long b44reg_base, b44reg_len; -@@ -2113,76 +2303,32 @@ +- unsigned long b44reg_base, b44reg_len; + struct net_device *dev; struct b44 *bp; int err, i; @@ -1195,7 +1195,8 @@ Index: linux-2.6.23/drivers/net/b44.c - dev = alloc_etherdev(sizeof(*bp)); if (!dev) { - dev_err(&pdev->dev, "Etherdev alloc failed, aborting.\n"); +- dev_err(&pdev->dev, "Etherdev alloc failed, aborting.\n"); ++ dev_err(sdev->dev, "Etherdev alloc failed, aborting.\n"); err = -ENOMEM; - goto err_out_free_res; + goto out; @@ -1203,7 +1204,7 @@ Index: linux-2.6.23/drivers/net/b44.c SET_MODULE_OWNER(dev); - SET_NETDEV_DEV(dev,&pdev->dev); -+ SET_NETDEV_DEV(dev,&sdev->dev); ++ SET_NETDEV_DEV(dev,sdev->dev); /* No interesting netdevice features in this card... */ dev->features |= 0; @@ -1227,7 +1228,7 @@ Index: linux-2.6.23/drivers/net/b44.c bp->rx_pending = B44_DEF_RX_RING_PENDING; bp->tx_pending = B44_DEF_TX_RING_PENDING; -@@ -2201,16 +2347,16 @@ +@@ -2201,16 +2346,16 @@ dev->poll_controller = b44_poll_controller; #endif dev->change_mtu = b44_change_mtu; @@ -1240,20 +1241,20 @@ Index: linux-2.6.23/drivers/net/b44.c err = b44_get_invariants(bp); if (err) { - dev_err(&pdev->dev, -+ dev_err(&sdev->dev, ++ dev_err(sdev->dev, "Problem fetching invariants of chip, aborting.\n"); - goto err_out_iounmap; + goto err_out_free_dev; } bp->mii_if.dev = dev; -@@ -2229,61 +2375,52 @@ +@@ -2229,61 +2374,52 @@ err = register_netdev(dev); if (err) { - dev_err(&pdev->dev, "Cannot register net device, aborting.\n"); - goto err_out_iounmap; -+ dev_err(&sdev->dev, "Cannot register net device, aborting.\n"); ++ dev_err(sdev->dev, "Cannot register net device, aborting.\n"); + goto out; } @@ -1325,7 +1326,7 @@ Index: linux-2.6.23/drivers/net/b44.c del_timer_sync(&bp->timer); -@@ -2301,26 +2438,16 @@ +@@ -2301,33 +2437,22 @@ b44_init_hw(bp, B44_PARTIAL_RESET); b44_setup_wol(bp); } @@ -1355,7 +1356,14 @@ Index: linux-2.6.23/drivers/net/b44.c if (!netif_running(dev)) return 0; -@@ -2346,29 +2473,31 @@ + rc = request_irq(dev->irq, b44_interrupt, IRQF_SHARED, dev->name, dev); + if (rc) { + printk(KERN_ERR PFX "%s: request_irq failed\n", dev->name); +- pci_disable_device(pdev); + return rc; + } + +@@ -2346,29 +2471,31 @@ return 0; } @@ -1395,8 +1403,8 @@ Index: linux-2.6.23/drivers/net/b44.c module_init(b44_init); Index: linux-2.6.23/drivers/net/b44.h =================================================================== ---- linux-2.6.23.orig/drivers/net/b44.h 2007-10-09 22:31:38.000000000 +0200 -+++ linux-2.6.23/drivers/net/b44.h 2007-10-13 02:28:25.848697310 +0200 +--- linux-2.6.23.orig/drivers/net/b44.h 2007-10-13 10:58:27.880607722 +0200 ++++ linux-2.6.23/drivers/net/b44.h 2007-10-13 11:00:46.904530245 +0200 @@ -129,6 +129,7 @@ #define RXCONFIG_FLOW 0x00000020 /* Flow Control Enable */ #define RXCONFIG_FLOW_ACCEPT 0x00000040 /* Accept Unicast Flow Control Frame */ @@ -1522,8 +1530,8 @@ Index: linux-2.6.23/drivers/net/b44.h dma_addr_t rx_ring_dma, tx_ring_dma; Index: linux-2.6.23/drivers/net/Kconfig =================================================================== ---- linux-2.6.23.orig/drivers/net/Kconfig 2007-10-13 02:19:47.919182188 +0200 -+++ linux-2.6.23/drivers/net/Kconfig 2007-10-13 02:28:25.860697993 +0200 +--- linux-2.6.23.orig/drivers/net/Kconfig 2007-10-13 10:58:27.888608180 +0200 ++++ linux-2.6.23/drivers/net/Kconfig 2007-10-13 11:00:46.912530699 +0200 @@ -1577,7 +1577,7 @@ config B44 -- cgit v1.2.3