Merge branch 'upstream-linus' of master.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6
* 'upstream-linus' of master.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6: (22 commits) [PATCH] ibmveth: Fix index increment calculation [PATCH] Fix timer race [PATCH] Remove useless comment from sb1250 [PATCH] ucc_geth: changes to ucc_geth driver as a result of qe_lib changes and bugfixes [PATCH] sky2: 88E803X transmit lockup [PATCH] e1000: Reset all functions after a PCI error [PATCH] WAN/pc300: handle, propagate minor errors [PATCH] Update smc91x driver with ARM Versatile board info [PATCH] wireless: WE-20 compatibility for ESSID and NICKN ioctls [PATCH] zd1211rw: fix build-break caused by association race fix [PATCH] sotftmac: fix a slab corruption in WEP restricted key association [PATCH] airo: check if need to freeze [PATCH] wireless: More WE-21 potential overflows... [PATCH] zd1201: Possible NULL dereference [PATCH] orinoco: fix WE-21 buffer overflow [PATCH] airo.c: check returned values [PATCH] bcm43xx-softmac: Fix system hang for x86-64 with >1GB RAM [PATCH] bcm43xx-softmac: check returned value from pci_enable_device [PATCH] softmac: Fix WX and association related races [PATCH] bcm43xx: fix race condition in periodic work handler ...
This commit is contained in:
commit
dcf234f3b0
29 changed files with 804 additions and 623 deletions
|
@ -2288,7 +2288,7 @@ config UGETH_TX_ON_DEMOND
|
|||
|
||||
config UGETH_HAS_GIGA
|
||||
bool
|
||||
depends on UCC_GETH && MPC836x
|
||||
depends on UCC_GETH && PPC_MPC836x
|
||||
|
||||
config MV643XX_ETH
|
||||
tristate "MV-643XX Ethernet support"
|
||||
|
|
|
@ -4914,10 +4914,6 @@ static pci_ers_result_t e1000_io_slot_reset(struct pci_dev *pdev)
|
|||
pci_enable_wake(pdev, PCI_D3hot, 0);
|
||||
pci_enable_wake(pdev, PCI_D3cold, 0);
|
||||
|
||||
/* Perform card reset only on one instance of the card */
|
||||
if (PCI_FUNC (pdev->devfn) != 0)
|
||||
return PCI_ERS_RESULT_RECOVERED;
|
||||
|
||||
e1000_reset(adapter);
|
||||
E1000_WRITE_REG(&adapter->hw, WUS, ~0);
|
||||
|
||||
|
|
|
@ -1017,7 +1017,7 @@ static void ioc3_init(struct net_device *dev)
|
|||
struct ioc3_private *ip = netdev_priv(dev);
|
||||
struct ioc3 *ioc3 = ip->regs;
|
||||
|
||||
del_timer(&ip->ioc3_timer); /* Kill if running */
|
||||
del_timer_sync(&ip->ioc3_timer); /* Kill if running */
|
||||
|
||||
ioc3_w_emcr(EMCR_RST); /* Reset */
|
||||
(void) ioc3_r_emcr(); /* Flush WB */
|
||||
|
@ -1081,7 +1081,7 @@ static int ioc3_close(struct net_device *dev)
|
|||
{
|
||||
struct ioc3_private *ip = netdev_priv(dev);
|
||||
|
||||
del_timer(&ip->ioc3_timer);
|
||||
del_timer_sync(&ip->ioc3_timer);
|
||||
|
||||
netif_stop_queue(dev);
|
||||
|
||||
|
|
|
@ -214,6 +214,7 @@ static struct pci_device_id rtl8169_pci_tbl[] = {
|
|||
{ PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8168), 0, 0, RTL_CFG_2 },
|
||||
{ PCI_DEVICE(PCI_VENDOR_ID_REALTEK, 0x8169), 0, 0, RTL_CFG_0 },
|
||||
{ PCI_DEVICE(PCI_VENDOR_ID_DLINK, 0x4300), 0, 0, RTL_CFG_0 },
|
||||
{ PCI_DEVICE(0x1259, 0xc107), 0, 0, RTL_CFG_0 },
|
||||
{ PCI_DEVICE(0x16ec, 0x0116), 0, 0, RTL_CFG_0 },
|
||||
{ PCI_VENDOR_ID_LINKSYS, 0x1032,
|
||||
PCI_ANY_ID, 0x0024, 0, 0, RTL_CFG_0 },
|
||||
|
@ -2700,6 +2701,7 @@ static void rtl8169_down(struct net_device *dev)
|
|||
struct rtl8169_private *tp = netdev_priv(dev);
|
||||
void __iomem *ioaddr = tp->mmio_addr;
|
||||
unsigned int poll_locked = 0;
|
||||
unsigned int intrmask;
|
||||
|
||||
rtl8169_delete_timer(dev);
|
||||
|
||||
|
@ -2738,8 +2740,11 @@ core_down:
|
|||
* 2) dev->change_mtu
|
||||
* -> rtl8169_poll can not be issued again and re-enable the
|
||||
* interruptions. Let's simply issue the IRQ down sequence again.
|
||||
*
|
||||
* No loop if hotpluged or major error (0xffff).
|
||||
*/
|
||||
if (RTL_R16(IntrMask))
|
||||
intrmask = RTL_R16(IntrMask);
|
||||
if (intrmask && (intrmask != 0xffff))
|
||||
goto core_down;
|
||||
|
||||
rtl8169_tx_clear(tp);
|
||||
|
|
|
@ -2903,7 +2903,7 @@ sbmac_init_module(void)
|
|||
|
||||
dev = alloc_etherdev(sizeof(struct sbmac_softc));
|
||||
if (!dev)
|
||||
return -ENOMEM; /* return ENOMEM */
|
||||
return -ENOMEM;
|
||||
|
||||
printk(KERN_DEBUG "sbmac: configuring MAC at %lx\n", port);
|
||||
|
||||
|
|
|
@ -699,16 +699,10 @@ static void sky2_mac_init(struct sky2_hw *hw, unsigned port)
|
|||
|
||||
}
|
||||
|
||||
/* Assign Ram Buffer allocation.
|
||||
* start and end are in units of 4k bytes
|
||||
* ram registers are in units of 64bit words
|
||||
*/
|
||||
static void sky2_ramset(struct sky2_hw *hw, u16 q, u8 startk, u8 endk)
|
||||
/* Assign Ram Buffer allocation in units of 64bit (8 bytes) */
|
||||
static void sky2_ramset(struct sky2_hw *hw, u16 q, u32 start, u32 end)
|
||||
{
|
||||
u32 start, end;
|
||||
|
||||
start = startk * 4096/8;
|
||||
end = (endk * 4096/8) - 1;
|
||||
pr_debug(PFX "q %d %#x %#x\n", q, start, end);
|
||||
|
||||
sky2_write8(hw, RB_ADDR(q, RB_CTRL), RB_RST_CLR);
|
||||
sky2_write32(hw, RB_ADDR(q, RB_START), start);
|
||||
|
@ -717,7 +711,7 @@ static void sky2_ramset(struct sky2_hw *hw, u16 q, u8 startk, u8 endk)
|
|||
sky2_write32(hw, RB_ADDR(q, RB_RP), start);
|
||||
|
||||
if (q == Q_R1 || q == Q_R2) {
|
||||
u32 space = (endk - startk) * 4096/8;
|
||||
u32 space = end - start + 1;
|
||||
u32 tp = space - space/4;
|
||||
|
||||
/* On receive queue's set the thresholds
|
||||
|
@ -1199,19 +1193,16 @@ static int sky2_up(struct net_device *dev)
|
|||
|
||||
sky2_mac_init(hw, port);
|
||||
|
||||
/* Determine available ram buffer space (in 4K blocks).
|
||||
* Note: not sure about the FE setting below yet
|
||||
*/
|
||||
if (hw->chip_id == CHIP_ID_YUKON_FE)
|
||||
ramsize = 4;
|
||||
/* Determine available ram buffer space in qwords. */
|
||||
ramsize = sky2_read8(hw, B2_E_0) * 4096/8;
|
||||
|
||||
if (ramsize > 6*1024/8)
|
||||
rxspace = ramsize - (ramsize + 2) / 3;
|
||||
else
|
||||
ramsize = sky2_read8(hw, B2_E_0);
|
||||
rxspace = ramsize / 2;
|
||||
|
||||
/* Give transmitter one third (rounded up) */
|
||||
rxspace = ramsize - (ramsize + 2) / 3;
|
||||
|
||||
sky2_ramset(hw, rxqaddr[port], 0, rxspace);
|
||||
sky2_ramset(hw, txqaddr[port], rxspace, ramsize);
|
||||
sky2_ramset(hw, rxqaddr[port], 0, rxspace-1);
|
||||
sky2_ramset(hw, txqaddr[port], rxspace, ramsize-1);
|
||||
|
||||
/* Make sure SyncQ is disabled */
|
||||
sky2_write8(hw, RB_ADDR(port == 0 ? Q_XS1 : Q_XS2, RB_CTRL),
|
||||
|
|
|
@ -416,6 +416,24 @@ static inline void LPD7_SMC_outsw (unsigned char* a, int r,
|
|||
|
||||
#define SMC_IRQ_FLAGS (0)
|
||||
|
||||
#elif defined(CONFIG_ARCH_VERSATILE)
|
||||
|
||||
#define SMC_CAN_USE_8BIT 1
|
||||
#define SMC_CAN_USE_16BIT 1
|
||||
#define SMC_CAN_USE_32BIT 1
|
||||
#define SMC_NOWAIT 1
|
||||
|
||||
#define SMC_inb(a, r) readb((a) + (r))
|
||||
#define SMC_inw(a, r) readw((a) + (r))
|
||||
#define SMC_inl(a, r) readl((a) + (r))
|
||||
#define SMC_outb(v, a, r) writeb(v, (a) + (r))
|
||||
#define SMC_outw(v, a, r) writew(v, (a) + (r))
|
||||
#define SMC_outl(v, a, r) writel(v, (a) + (r))
|
||||
#define SMC_insl(a, r, p, l) readsl((a) + (r), p, l)
|
||||
#define SMC_outsl(a, r, p, l) writesl((a) + (r), p, l)
|
||||
|
||||
#define SMC_IRQ_FLAGS (0)
|
||||
|
||||
#else
|
||||
|
||||
#define SMC_CAN_USE_8BIT 1
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -36,24 +36,24 @@
|
|||
#define ENET_INIT_PARAM_MAX_ENTRIES_RX 9
|
||||
#define ENET_INIT_PARAM_MAX_ENTRIES_TX 8
|
||||
|
||||
typedef struct ucc_mii_mng {
|
||||
struct ucc_mii_mng {
|
||||
u32 miimcfg; /* MII management configuration reg */
|
||||
u32 miimcom; /* MII management command reg */
|
||||
u32 miimadd; /* MII management address reg */
|
||||
u32 miimcon; /* MII management control reg */
|
||||
u32 miimstat; /* MII management status reg */
|
||||
u32 miimind; /* MII management indication reg */
|
||||
} __attribute__ ((packed)) ucc_mii_mng_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth {
|
||||
ucc_fast_t uccf;
|
||||
struct ucc_geth {
|
||||
struct ucc_fast uccf;
|
||||
|
||||
u32 maccfg1; /* mac configuration reg. 1 */
|
||||
u32 maccfg2; /* mac configuration reg. 2 */
|
||||
u32 ipgifg; /* interframe gap reg. */
|
||||
u32 hafdup; /* half-duplex reg. */
|
||||
u8 res1[0x10];
|
||||
ucc_mii_mng_t miimng; /* MII management structure */
|
||||
struct ucc_mii_mng miimng; /* MII management structure */
|
||||
u32 ifctl; /* interface control reg */
|
||||
u32 ifstat; /* interface statux reg */
|
||||
u32 macstnaddr1; /* mac station address part 1 reg */
|
||||
|
@ -111,7 +111,7 @@ typedef struct ucc_geth {
|
|||
u32 scar; /* Statistics carry register */
|
||||
u32 scam; /* Statistics caryy mask register */
|
||||
u8 res5[0x200 - 0x1c4];
|
||||
} __attribute__ ((packed)) ucc_geth_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* UCC GETH TEMODR Register */
|
||||
#define TEMODER_TX_RMON_STATISTICS_ENABLE 0x0100 /* enable Tx statistics
|
||||
|
@ -508,39 +508,39 @@ typedef struct ucc_geth {
|
|||
/* UCC GETH UDSR (Data Synchronization Register) */
|
||||
#define UDSR_MAGIC 0x067E
|
||||
|
||||
typedef struct ucc_geth_thread_data_tx {
|
||||
struct ucc_geth_thread_data_tx {
|
||||
u8 res0[104];
|
||||
} __attribute__ ((packed)) ucc_geth_thread_data_tx_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_thread_data_rx {
|
||||
struct ucc_geth_thread_data_rx {
|
||||
u8 res0[40];
|
||||
} __attribute__ ((packed)) ucc_geth_thread_data_rx_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* Send Queue Queue-Descriptor */
|
||||
typedef struct ucc_geth_send_queue_qd {
|
||||
struct ucc_geth_send_queue_qd {
|
||||
u32 bd_ring_base; /* pointer to BD ring base address */
|
||||
u8 res0[0x8];
|
||||
u32 last_bd_completed_address;/* initialize to last entry in BD ring */
|
||||
u8 res1[0x30];
|
||||
} __attribute__ ((packed)) ucc_geth_send_queue_qd_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_send_queue_mem_region {
|
||||
ucc_geth_send_queue_qd_t sqqd[NUM_TX_QUEUES];
|
||||
} __attribute__ ((packed)) ucc_geth_send_queue_mem_region_t;
|
||||
struct ucc_geth_send_queue_mem_region {
|
||||
struct ucc_geth_send_queue_qd sqqd[NUM_TX_QUEUES];
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_thread_tx_pram {
|
||||
struct ucc_geth_thread_tx_pram {
|
||||
u8 res0[64];
|
||||
} __attribute__ ((packed)) ucc_geth_thread_tx_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_thread_rx_pram {
|
||||
struct ucc_geth_thread_rx_pram {
|
||||
u8 res0[128];
|
||||
} __attribute__ ((packed)) ucc_geth_thread_rx_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
#define THREAD_RX_PRAM_ADDITIONAL_FOR_EXTENDED_FILTERING 64
|
||||
#define THREAD_RX_PRAM_ADDITIONAL_FOR_EXTENDED_FILTERING_8 64
|
||||
#define THREAD_RX_PRAM_ADDITIONAL_FOR_EXTENDED_FILTERING_16 96
|
||||
|
||||
typedef struct ucc_geth_scheduler {
|
||||
struct ucc_geth_scheduler {
|
||||
u16 cpucount0; /* CPU packet counter */
|
||||
u16 cpucount1; /* CPU packet counter */
|
||||
u16 cecount0; /* QE packet counter */
|
||||
|
@ -574,9 +574,9 @@ typedef struct ucc_geth_scheduler {
|
|||
/**< weight factor for queues */
|
||||
u32 minw; /* temporary variable handled by QE */
|
||||
u8 res1[0x70 - 0x64];
|
||||
} __attribute__ ((packed)) ucc_geth_scheduler_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_tx_firmware_statistics_pram {
|
||||
struct ucc_geth_tx_firmware_statistics_pram {
|
||||
u32 sicoltx; /* single collision */
|
||||
u32 mulcoltx; /* multiple collision */
|
||||
u32 latecoltxfr; /* late collision */
|
||||
|
@ -596,9 +596,9 @@ typedef struct ucc_geth_tx_firmware_statistics_pram {
|
|||
and 1518 octets */
|
||||
u32 txpktsjumbo; /* total packets (including bad) between 1024
|
||||
and MAXLength octets */
|
||||
} __attribute__ ((packed)) ucc_geth_tx_firmware_statistics_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_firmware_statistics_pram {
|
||||
struct ucc_geth_rx_firmware_statistics_pram {
|
||||
u32 frrxfcser; /* frames with crc error */
|
||||
u32 fraligner; /* frames with alignment error */
|
||||
u32 inrangelenrxer; /* in range length error */
|
||||
|
@ -630,33 +630,33 @@ typedef struct ucc_geth_rx_firmware_statistics_pram {
|
|||
replaced */
|
||||
u32 insertvlan; /* total frames that had their VLAN tag
|
||||
inserted */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_firmware_statistics_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_interrupt_coalescing_entry {
|
||||
struct ucc_geth_rx_interrupt_coalescing_entry {
|
||||
u32 interruptcoalescingmaxvalue; /* interrupt coalescing max
|
||||
value */
|
||||
u32 interruptcoalescingcounter; /* interrupt coalescing counter,
|
||||
initialize to
|
||||
interruptcoalescingmaxvalue */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_interrupt_coalescing_entry_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_interrupt_coalescing_table {
|
||||
ucc_geth_rx_interrupt_coalescing_entry_t coalescingentry[NUM_RX_QUEUES];
|
||||
struct ucc_geth_rx_interrupt_coalescing_table {
|
||||
struct ucc_geth_rx_interrupt_coalescing_entry coalescingentry[NUM_RX_QUEUES];
|
||||
/**< interrupt coalescing entry */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_interrupt_coalescing_table_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_prefetched_bds {
|
||||
qe_bd_t bd[NUM_BDS_IN_PREFETCHED_BDS]; /* prefetched bd */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_prefetched_bds_t;
|
||||
struct ucc_geth_rx_prefetched_bds {
|
||||
struct qe_bd bd[NUM_BDS_IN_PREFETCHED_BDS]; /* prefetched bd */
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_bd_queues_entry {
|
||||
struct ucc_geth_rx_bd_queues_entry {
|
||||
u32 bdbaseptr; /* BD base pointer */
|
||||
u32 bdptr; /* BD pointer */
|
||||
u32 externalbdbaseptr; /* external BD base pointer */
|
||||
u32 externalbdptr; /* external BD pointer */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_bd_queues_entry_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_tx_global_pram {
|
||||
struct ucc_geth_tx_global_pram {
|
||||
u16 temoder;
|
||||
u8 res0[0x38 - 0x02];
|
||||
u32 sqptr; /* a base pointer to send queue memory region */
|
||||
|
@ -670,15 +670,15 @@ typedef struct ucc_geth_tx_global_pram {
|
|||
u32 tqptr; /* a base pointer to the Tx Queues Memory
|
||||
Region */
|
||||
u8 res2[0x80 - 0x74];
|
||||
} __attribute__ ((packed)) ucc_geth_tx_global_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* structure representing Extended Filtering Global Parameters in PRAM */
|
||||
typedef struct ucc_geth_exf_global_pram {
|
||||
struct ucc_geth_exf_global_pram {
|
||||
u32 l2pcdptr; /* individual address filter, high */
|
||||
u8 res0[0x10 - 0x04];
|
||||
} __attribute__ ((packed)) ucc_geth_exf_global_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
typedef struct ucc_geth_rx_global_pram {
|
||||
struct ucc_geth_rx_global_pram {
|
||||
u32 remoder; /* ethernet mode reg. */
|
||||
u32 rqptr; /* base pointer to the Rx Queues Memory Region*/
|
||||
u32 res0[0x1];
|
||||
|
@ -710,12 +710,12 @@ typedef struct ucc_geth_rx_global_pram {
|
|||
u32 exfGlobalParam; /* base address for extended filtering global
|
||||
parameters */
|
||||
u8 res6[0x100 - 0xC4]; /* Initialize to zero */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_global_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
#define GRACEFUL_STOP_ACKNOWLEDGE_RX 0x01
|
||||
|
||||
/* structure representing InitEnet command */
|
||||
typedef struct ucc_geth_init_pram {
|
||||
struct ucc_geth_init_pram {
|
||||
u8 resinit1;
|
||||
u8 resinit2;
|
||||
u8 resinit3;
|
||||
|
@ -729,7 +729,7 @@ typedef struct ucc_geth_init_pram {
|
|||
u32 txglobal; /* tx global */
|
||||
u32 txthread[ENET_INIT_PARAM_MAX_ENTRIES_TX]; /* tx threads */
|
||||
u8 res3[0x1];
|
||||
} __attribute__ ((packed)) ucc_geth_init_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
#define ENET_INIT_PARAM_RGF_SHIFT (32 - 4)
|
||||
#define ENET_INIT_PARAM_TGF_SHIFT (32 - 8)
|
||||
|
@ -746,27 +746,27 @@ typedef struct ucc_geth_init_pram {
|
|||
#define ENET_INIT_PARAM_MAGIC_RES_INIT5 0x0400
|
||||
|
||||
/* structure representing 82xx Address Filtering Enet Address in PRAM */
|
||||
typedef struct ucc_geth_82xx_enet_address {
|
||||
struct ucc_geth_82xx_enet_address {
|
||||
u8 res1[0x2];
|
||||
u16 h; /* address (MSB) */
|
||||
u16 m; /* address */
|
||||
u16 l; /* address (LSB) */
|
||||
} __attribute__ ((packed)) ucc_geth_82xx_enet_address_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* structure representing 82xx Address Filtering PRAM */
|
||||
typedef struct ucc_geth_82xx_address_filtering_pram {
|
||||
struct ucc_geth_82xx_address_filtering_pram {
|
||||
u32 iaddr_h; /* individual address filter, high */
|
||||
u32 iaddr_l; /* individual address filter, low */
|
||||
u32 gaddr_h; /* group address filter, high */
|
||||
u32 gaddr_l; /* group address filter, low */
|
||||
ucc_geth_82xx_enet_address_t taddr;
|
||||
ucc_geth_82xx_enet_address_t paddr[NUM_OF_PADDRS];
|
||||
struct ucc_geth_82xx_enet_address taddr;
|
||||
struct ucc_geth_82xx_enet_address paddr[NUM_OF_PADDRS];
|
||||
u8 res0[0x40 - 0x38];
|
||||
} __attribute__ ((packed)) ucc_geth_82xx_address_filtering_pram_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* GETH Tx firmware statistics structure, used when calling
|
||||
UCC_GETH_GetStatistics. */
|
||||
typedef struct ucc_geth_tx_firmware_statistics {
|
||||
struct ucc_geth_tx_firmware_statistics {
|
||||
u32 sicoltx; /* single collision */
|
||||
u32 mulcoltx; /* multiple collision */
|
||||
u32 latecoltxfr; /* late collision */
|
||||
|
@ -786,11 +786,11 @@ typedef struct ucc_geth_tx_firmware_statistics {
|
|||
and 1518 octets */
|
||||
u32 txpktsjumbo; /* total packets (including bad) between 1024
|
||||
and MAXLength octets */
|
||||
} __attribute__ ((packed)) ucc_geth_tx_firmware_statistics_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* GETH Rx firmware statistics structure, used when calling
|
||||
UCC_GETH_GetStatistics. */
|
||||
typedef struct ucc_geth_rx_firmware_statistics {
|
||||
struct ucc_geth_rx_firmware_statistics {
|
||||
u32 frrxfcser; /* frames with crc error */
|
||||
u32 fraligner; /* frames with alignment error */
|
||||
u32 inrangelenrxer; /* in range length error */
|
||||
|
@ -822,11 +822,11 @@ typedef struct ucc_geth_rx_firmware_statistics {
|
|||
replaced */
|
||||
u32 insertvlan; /* total frames that had their VLAN tag
|
||||
inserted */
|
||||
} __attribute__ ((packed)) ucc_geth_rx_firmware_statistics_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* GETH hardware statistics structure, used when calling
|
||||
UCC_GETH_GetStatistics. */
|
||||
typedef struct ucc_geth_hardware_statistics {
|
||||
struct ucc_geth_hardware_statistics {
|
||||
u32 tx64; /* Total number of frames (including bad
|
||||
frames) transmitted that were exactly of the
|
||||
minimal length (64 for un tagged, 68 for
|
||||
|
@ -871,7 +871,7 @@ typedef struct ucc_geth_hardware_statistics {
|
|||
u32 rbca; /* Total number of frames received succesfully
|
||||
that had destination address equal to the
|
||||
broadcast address */
|
||||
} __attribute__ ((packed)) ucc_geth_hardware_statistics_t;
|
||||
} __attribute__ ((packed));
|
||||
|
||||
/* UCC GETH Tx errors returned via TxConf callback */
|
||||
#define TX_ERRORS_DEF 0x0200
|
||||
|
@ -1013,21 +1013,21 @@ typedef struct ucc_geth_hardware_statistics {
|
|||
(MIIMCFG_MANAGEMENT_CLOCK_DIVIDE_BY_112)
|
||||
|
||||
/* Ethernet speed */
|
||||
typedef enum enet_speed {
|
||||
enum enet_speed {
|
||||
ENET_SPEED_10BT, /* 10 Base T */
|
||||
ENET_SPEED_100BT, /* 100 Base T */
|
||||
ENET_SPEED_1000BT /* 1000 Base T */
|
||||
} enet_speed_e;
|
||||
};
|
||||
|
||||
/* Ethernet Address Type. */
|
||||
typedef enum enet_addr_type {
|
||||
enum enet_addr_type {
|
||||
ENET_ADDR_TYPE_INDIVIDUAL,
|
||||
ENET_ADDR_TYPE_GROUP,
|
||||
ENET_ADDR_TYPE_BROADCAST
|
||||
} enet_addr_type_e;
|
||||
};
|
||||
|
||||
/* TBI / MII Set Register */
|
||||
typedef enum enet_tbi_mii_reg {
|
||||
enum enet_tbi_mii_reg {
|
||||
ENET_TBI_MII_CR = 0x00, /* Control (CR ) */
|
||||
ENET_TBI_MII_SR = 0x01, /* Status (SR ) */
|
||||
ENET_TBI_MII_ANA = 0x04, /* AN advertisement (ANA ) */
|
||||
|
@ -1040,10 +1040,10 @@ typedef enum enet_tbi_mii_reg {
|
|||
ENET_TBI_MII_EXST = 0x0F, /* Extended status (EXST ) */
|
||||
ENET_TBI_MII_JD = 0x10, /* Jitter diagnostics (JD ) */
|
||||
ENET_TBI_MII_TBICON = 0x11 /* TBI control (TBICON ) */
|
||||
} enet_tbi_mii_reg_e;
|
||||
};
|
||||
|
||||
/* UCC GETH 82xx Ethernet Address Recognition Location */
|
||||
typedef enum ucc_geth_enet_address_recognition_location {
|
||||
enum ucc_geth_enet_address_recognition_location {
|
||||
UCC_GETH_ENET_ADDRESS_RECOGNITION_LOCATION_STATION_ADDRESS,/* station
|
||||
address */
|
||||
UCC_GETH_ENET_ADDRESS_RECOGNITION_LOCATION_PADDR_FIRST, /* additional
|
||||
|
@ -1065,10 +1065,10 @@ typedef enum ucc_geth_enet_address_recognition_location {
|
|||
UCC_GETH_ENET_ADDRESS_RECOGNITION_LOCATION_GROUP_HASH, /* group hash */
|
||||
UCC_GETH_ENET_ADDRESS_RECOGNITION_LOCATION_INDIVIDUAL_HASH /* individual
|
||||
hash */
|
||||
} ucc_geth_enet_address_recognition_location_e;
|
||||
};
|
||||
|
||||
/* UCC GETH vlan operation tagged */
|
||||
typedef enum ucc_geth_vlan_operation_tagged {
|
||||
enum ucc_geth_vlan_operation_tagged {
|
||||
UCC_GETH_VLAN_OPERATION_TAGGED_NOP = 0x0, /* Tagged - nop */
|
||||
UCC_GETH_VLAN_OPERATION_TAGGED_REPLACE_VID_PORTION_OF_Q_TAG
|
||||
= 0x1, /* Tagged - replace vid portion of q tag */
|
||||
|
@ -1076,18 +1076,18 @@ typedef enum ucc_geth_vlan_operation_tagged {
|
|||
= 0x2, /* Tagged - if vid0 replace vid with default value */
|
||||
UCC_GETH_VLAN_OPERATION_TAGGED_EXTRACT_Q_TAG_FROM_FRAME
|
||||
= 0x3 /* Tagged - extract q tag from frame */
|
||||
} ucc_geth_vlan_operation_tagged_e;
|
||||
};
|
||||
|
||||
/* UCC GETH vlan operation non-tagged */
|
||||
typedef enum ucc_geth_vlan_operation_non_tagged {
|
||||
enum ucc_geth_vlan_operation_non_tagged {
|
||||
UCC_GETH_VLAN_OPERATION_NON_TAGGED_NOP = 0x0, /* Non tagged - nop */
|
||||
UCC_GETH_VLAN_OPERATION_NON_TAGGED_Q_TAG_INSERT = 0x1 /* Non tagged -
|
||||
q tag insert
|
||||
*/
|
||||
} ucc_geth_vlan_operation_non_tagged_e;
|
||||
};
|
||||
|
||||
/* UCC GETH Rx Quality of Service Mode */
|
||||
typedef enum ucc_geth_qos_mode {
|
||||
enum ucc_geth_qos_mode {
|
||||
UCC_GETH_QOS_MODE_DEFAULT = 0x0, /* default queue */
|
||||
UCC_GETH_QOS_MODE_QUEUE_NUM_FROM_L2_CRITERIA = 0x1, /* queue
|
||||
determined
|
||||
|
@ -1097,11 +1097,11 @@ typedef enum ucc_geth_qos_mode {
|
|||
determined
|
||||
by L3
|
||||
criteria */
|
||||
} ucc_geth_qos_mode_e;
|
||||
};
|
||||
|
||||
/* UCC GETH Statistics Gathering Mode - These are bit flags, 'or' them together
|
||||
for combined functionality */
|
||||
typedef enum ucc_geth_statistics_gathering_mode {
|
||||
enum ucc_geth_statistics_gathering_mode {
|
||||
UCC_GETH_STATISTICS_GATHERING_MODE_NONE = 0x00000000, /* No
|
||||
statistics
|
||||
gathering */
|
||||
|
@ -1122,10 +1122,10 @@ typedef enum ucc_geth_statistics_gathering_mode {
|
|||
statistics
|
||||
gathering
|
||||
*/
|
||||
} ucc_geth_statistics_gathering_mode_e;
|
||||
};
|
||||
|
||||
/* UCC GETH Pad and CRC Mode - Note, Padding without CRC is not possible */
|
||||
typedef enum ucc_geth_maccfg2_pad_and_crc_mode {
|
||||
enum ucc_geth_maccfg2_pad_and_crc_mode {
|
||||
UCC_GETH_PAD_AND_CRC_MODE_NONE
|
||||
= MACCFG2_PAD_AND_CRC_MODE_NONE, /* Neither Padding
|
||||
short frames
|
||||
|
@ -1135,61 +1135,59 @@ typedef enum ucc_geth_maccfg2_pad_and_crc_mode {
|
|||
CRC only */
|
||||
UCC_GETH_PAD_AND_CRC_MODE_PAD_AND_CRC =
|
||||
MACCFG2_PAD_AND_CRC_MODE_PAD_AND_CRC
|
||||
} ucc_geth_maccfg2_pad_and_crc_mode_e;
|
||||
};
|
||||
|
||||
/* UCC GETH upsmr Flow Control Mode */
|
||||
typedef enum ucc_geth_flow_control_mode {
|
||||
enum ucc_geth_flow_control_mode {
|
||||
UPSMR_AUTOMATIC_FLOW_CONTROL_MODE_NONE = 0x00000000, /* No automatic
|
||||
flow control
|
||||
*/
|
||||
UPSMR_AUTOMATIC_FLOW_CONTROL_MODE_PAUSE_WHEN_EMERGENCY
|
||||
= 0x00004000 /* Send pause frame when RxFIFO reaches its
|
||||
emergency threshold */
|
||||
} ucc_geth_flow_control_mode_e;
|
||||
};
|
||||
|
||||
/* UCC GETH number of threads */
|
||||
typedef enum ucc_geth_num_of_threads {
|
||||
enum ucc_geth_num_of_threads {
|
||||
UCC_GETH_NUM_OF_THREADS_1 = 0x1, /* 1 */
|
||||
UCC_GETH_NUM_OF_THREADS_2 = 0x2, /* 2 */
|
||||
UCC_GETH_NUM_OF_THREADS_4 = 0x0, /* 4 */
|
||||
UCC_GETH_NUM_OF_THREADS_6 = 0x3, /* 6 */
|
||||
UCC_GETH_NUM_OF_THREADS_8 = 0x4 /* 8 */
|
||||
} ucc_geth_num_of_threads_e;
|
||||
};
|
||||
|
||||
/* UCC GETH number of station addresses */
|
||||
typedef enum ucc_geth_num_of_station_addresses {
|
||||
enum ucc_geth_num_of_station_addresses {
|
||||
UCC_GETH_NUM_OF_STATION_ADDRESSES_1, /* 1 */
|
||||
UCC_GETH_NUM_OF_STATION_ADDRESSES_5 /* 5 */
|
||||
} ucc_geth_num_of_station_addresses_e;
|
||||
|
||||
typedef u8 enet_addr_t[ENET_NUM_OCTETS_PER_ADDRESS];
|
||||
};
|
||||
|
||||
/* UCC GETH 82xx Ethernet Address Container */
|
||||
typedef struct enet_addr_container {
|
||||
enet_addr_t address; /* ethernet address */
|
||||
ucc_geth_enet_address_recognition_location_e location; /* location in
|
||||
struct enet_addr_container {
|
||||
u8 address[ENET_NUM_OCTETS_PER_ADDRESS]; /* ethernet address */
|
||||
enum ucc_geth_enet_address_recognition_location location; /* location in
|
||||
82xx address
|
||||
recognition
|
||||
hardware */
|
||||
struct list_head node;
|
||||
} enet_addr_container_t;
|
||||
};
|
||||
|
||||
#define ENET_ADDR_CONT_ENTRY(ptr) list_entry(ptr, enet_addr_container_t, node)
|
||||
#define ENET_ADDR_CONT_ENTRY(ptr) list_entry(ptr, struct enet_addr_container, node)
|
||||
|
||||
/* UCC GETH Termination Action Descriptor (TAD) structure. */
|
||||
typedef struct ucc_geth_tad_params {
|
||||
struct ucc_geth_tad_params {
|
||||
int rx_non_dynamic_extended_features_mode;
|
||||
int reject_frame;
|
||||
ucc_geth_vlan_operation_tagged_e vtag_op;
|
||||
ucc_geth_vlan_operation_non_tagged_e vnontag_op;
|
||||
ucc_geth_qos_mode_e rqos;
|
||||
enum ucc_geth_vlan_operation_tagged vtag_op;
|
||||
enum ucc_geth_vlan_operation_non_tagged vnontag_op;
|
||||
enum ucc_geth_qos_mode rqos;
|
||||
u8 vpri;
|
||||
u16 vid;
|
||||
} ucc_geth_tad_params_t;
|
||||
};
|
||||
|
||||
/* GETH protocol initialization structure */
|
||||
typedef struct ucc_geth_info {
|
||||
ucc_fast_info_t uf_info;
|
||||
struct ucc_geth_info {
|
||||
struct ucc_fast_info uf_info;
|
||||
u8 numQueuesTx;
|
||||
u8 numQueuesRx;
|
||||
int ipCheckSumCheck;
|
||||
|
@ -1251,51 +1249,51 @@ typedef struct ucc_geth_info {
|
|||
u8 iphoffset[TX_IP_OFFSET_ENTRY_MAX];
|
||||
u16 bdRingLenTx[NUM_TX_QUEUES];
|
||||
u16 bdRingLenRx[NUM_RX_QUEUES];
|
||||
enet_interface_e enet_interface;
|
||||
ucc_geth_num_of_station_addresses_e numStationAddresses;
|
||||
qe_fltr_largest_external_tbl_lookup_key_size_e
|
||||
enum enet_interface enet_interface;
|
||||
enum ucc_geth_num_of_station_addresses numStationAddresses;
|
||||
enum qe_fltr_largest_external_tbl_lookup_key_size
|
||||
largestexternallookupkeysize;
|
||||
ucc_geth_statistics_gathering_mode_e statisticsMode;
|
||||
ucc_geth_vlan_operation_tagged_e vlanOperationTagged;
|
||||
ucc_geth_vlan_operation_non_tagged_e vlanOperationNonTagged;
|
||||
ucc_geth_qos_mode_e rxQoSMode;
|
||||
ucc_geth_flow_control_mode_e aufc;
|
||||
ucc_geth_maccfg2_pad_and_crc_mode_e padAndCrc;
|
||||
ucc_geth_num_of_threads_e numThreadsTx;
|
||||
ucc_geth_num_of_threads_e numThreadsRx;
|
||||
qe_risc_allocation_e riscTx;
|
||||
qe_risc_allocation_e riscRx;
|
||||
} ucc_geth_info_t;
|
||||
enum ucc_geth_statistics_gathering_mode statisticsMode;
|
||||
enum ucc_geth_vlan_operation_tagged vlanOperationTagged;
|
||||
enum ucc_geth_vlan_operation_non_tagged vlanOperationNonTagged;
|
||||
enum ucc_geth_qos_mode rxQoSMode;
|
||||
enum ucc_geth_flow_control_mode aufc;
|
||||
enum ucc_geth_maccfg2_pad_and_crc_mode padAndCrc;
|
||||
enum ucc_geth_num_of_threads numThreadsTx;
|
||||
enum ucc_geth_num_of_threads numThreadsRx;
|
||||
enum qe_risc_allocation riscTx;
|
||||
enum qe_risc_allocation riscRx;
|
||||
};
|
||||
|
||||
/* structure representing UCC GETH */
|
||||
typedef struct ucc_geth_private {
|
||||
ucc_geth_info_t *ug_info;
|
||||
ucc_fast_private_t *uccf;
|
||||
struct ucc_geth_private {
|
||||
struct ucc_geth_info *ug_info;
|
||||
struct ucc_fast_private *uccf;
|
||||
struct net_device *dev;
|
||||
struct net_device_stats stats; /* linux network statistics */
|
||||
ucc_geth_t *ug_regs;
|
||||
ucc_geth_init_pram_t *p_init_enet_param_shadow;
|
||||
ucc_geth_exf_global_pram_t *p_exf_glbl_param;
|
||||
struct ucc_geth *ug_regs;
|
||||
struct ucc_geth_init_pram *p_init_enet_param_shadow;
|
||||
struct ucc_geth_exf_global_pram *p_exf_glbl_param;
|
||||
u32 exf_glbl_param_offset;
|
||||
ucc_geth_rx_global_pram_t *p_rx_glbl_pram;
|
||||
struct ucc_geth_rx_global_pram *p_rx_glbl_pram;
|
||||
u32 rx_glbl_pram_offset;
|
||||
ucc_geth_tx_global_pram_t *p_tx_glbl_pram;
|
||||
struct ucc_geth_tx_global_pram *p_tx_glbl_pram;
|
||||
u32 tx_glbl_pram_offset;
|
||||
ucc_geth_send_queue_mem_region_t *p_send_q_mem_reg;
|
||||
struct ucc_geth_send_queue_mem_region *p_send_q_mem_reg;
|
||||
u32 send_q_mem_reg_offset;
|
||||
ucc_geth_thread_data_tx_t *p_thread_data_tx;
|
||||
struct ucc_geth_thread_data_tx *p_thread_data_tx;
|
||||
u32 thread_dat_tx_offset;
|
||||
ucc_geth_thread_data_rx_t *p_thread_data_rx;
|
||||
struct ucc_geth_thread_data_rx *p_thread_data_rx;
|
||||
u32 thread_dat_rx_offset;
|
||||
ucc_geth_scheduler_t *p_scheduler;
|
||||
struct ucc_geth_scheduler *p_scheduler;
|
||||
u32 scheduler_offset;
|
||||
ucc_geth_tx_firmware_statistics_pram_t *p_tx_fw_statistics_pram;
|
||||
struct ucc_geth_tx_firmware_statistics_pram *p_tx_fw_statistics_pram;
|
||||
u32 tx_fw_statistics_pram_offset;
|
||||
ucc_geth_rx_firmware_statistics_pram_t *p_rx_fw_statistics_pram;
|
||||
struct ucc_geth_rx_firmware_statistics_pram *p_rx_fw_statistics_pram;
|
||||
u32 rx_fw_statistics_pram_offset;
|
||||
ucc_geth_rx_interrupt_coalescing_table_t *p_rx_irq_coalescing_tbl;
|
||||
struct ucc_geth_rx_interrupt_coalescing_table *p_rx_irq_coalescing_tbl;
|
||||
u32 rx_irq_coalescing_tbl_offset;
|
||||
ucc_geth_rx_bd_queues_entry_t *p_rx_bd_qs_tbl;
|
||||
struct ucc_geth_rx_bd_queues_entry *p_rx_bd_qs_tbl;
|
||||
u32 rx_bd_qs_tbl_offset;
|
||||
u8 *p_tx_bd_ring[NUM_TX_QUEUES];
|
||||
u32 tx_bd_ring_offset[NUM_TX_QUEUES];
|
||||
|
@ -1308,7 +1306,7 @@ typedef struct ucc_geth_private {
|
|||
u16 cpucount[NUM_TX_QUEUES];
|
||||
volatile u16 *p_cpucount[NUM_TX_QUEUES];
|
||||
int indAddrRegUsed[NUM_OF_PADDRS];
|
||||
enet_addr_t paddr[NUM_OF_PADDRS];
|
||||
u8 paddr[NUM_OF_PADDRS][ENET_NUM_OCTETS_PER_ADDRESS]; /* ethernet address */
|
||||
u8 numGroupAddrInHash;
|
||||
u8 numIndAddrInHash;
|
||||
u8 numIndAddrInReg;
|
||||
|
@ -1334,6 +1332,6 @@ typedef struct ucc_geth_private {
|
|||
int oldspeed;
|
||||
int oldduplex;
|
||||
int oldlink;
|
||||
} ucc_geth_private_t;
|
||||
};
|
||||
|
||||
#endif /* __UCC_GETH_H__ */
|
||||
|
|
|
@ -42,7 +42,6 @@
|
|||
|
||||
#include "ucc_geth.h"
|
||||
#include "ucc_geth_phy.h"
|
||||
#include <platforms/83xx/mpc8360e_pb.h>
|
||||
|
||||
#define ugphy_printk(level, format, arg...) \
|
||||
printk(level format "\n", ## arg)
|
||||
|
@ -72,16 +71,14 @@ static int genmii_read_status(struct ugeth_mii_info *mii_info);
|
|||
u16 phy_read(struct ugeth_mii_info *mii_info, u16 regnum);
|
||||
void phy_write(struct ugeth_mii_info *mii_info, u16 regnum, u16 val);
|
||||
|
||||
static u8 *bcsr_regs = NULL;
|
||||
|
||||
/* Write value to the PHY for this device to the register at regnum, */
|
||||
/* waiting until the write is done before it returns. All PHY */
|
||||
/* configuration has to be done through the TSEC1 MIIM regs */
|
||||
void write_phy_reg(struct net_device *dev, int mii_id, int regnum, int value)
|
||||
{
|
||||
ucc_geth_private_t *ugeth = netdev_priv(dev);
|
||||
ucc_mii_mng_t *mii_regs;
|
||||
enet_tbi_mii_reg_e mii_reg = (enet_tbi_mii_reg_e) regnum;
|
||||
struct ucc_geth_private *ugeth = netdev_priv(dev);
|
||||
struct ucc_mii_mng *mii_regs;
|
||||
enum enet_tbi_mii_reg mii_reg = (enum enet_tbi_mii_reg) regnum;
|
||||
u32 tmp_reg;
|
||||
|
||||
ugphy_vdbg("%s: IN", __FUNCTION__);
|
||||
|
@ -116,9 +113,9 @@ void write_phy_reg(struct net_device *dev, int mii_id, int regnum, int value)
|
|||
/* configuration has to be done through the TSEC1 MIIM regs */
|
||||
int read_phy_reg(struct net_device *dev, int mii_id, int regnum)
|
||||
{
|
||||
ucc_geth_private_t *ugeth = netdev_priv(dev);
|
||||
ucc_mii_mng_t *mii_regs;
|
||||
enet_tbi_mii_reg_e mii_reg = (enet_tbi_mii_reg_e) regnum;
|
||||
struct ucc_geth_private *ugeth = netdev_priv(dev);
|
||||
struct ucc_mii_mng *mii_regs;
|
||||
enum enet_tbi_mii_reg mii_reg = (enum enet_tbi_mii_reg) regnum;
|
||||
u32 tmp_reg;
|
||||
u16 value;
|
||||
|
||||
|
@ -634,11 +631,6 @@ static void dm9161_close(struct ugeth_mii_info *mii_info)
|
|||
|
||||
static int dm9161_ack_interrupt(struct ugeth_mii_info *mii_info)
|
||||
{
|
||||
/* FIXME: This lines are for BUG fixing in the mpc8325.
|
||||
Remove this from here when it's fixed */
|
||||
if (bcsr_regs == NULL)
|
||||
bcsr_regs = (u8 *) ioremap(BCSR_PHYS_ADDR, BCSR_SIZE);
|
||||
bcsr_regs[14] |= 0x40;
|
||||
ugphy_vdbg("%s: IN", __FUNCTION__);
|
||||
|
||||
/* Clear the interrupts by reading the reg */
|
||||
|
@ -650,12 +642,6 @@ Remove this from here when it's fixed */
|
|||
|
||||
static int dm9161_config_intr(struct ugeth_mii_info *mii_info)
|
||||
{
|
||||
/* FIXME: This lines are for BUG fixing in the mpc8325.
|
||||
Remove this from here when it's fixed */
|
||||
if (bcsr_regs == NULL) {
|
||||
bcsr_regs = (u8 *) ioremap(BCSR_PHYS_ADDR, BCSR_SIZE);
|
||||
bcsr_regs[14] &= ~0x40;
|
||||
}
|
||||
ugphy_vdbg("%s: IN", __FUNCTION__);
|
||||
|
||||
if (mii_info->interrupts == MII_INTERRUPT_ENABLED)
|
||||
|
|
|
@ -126,7 +126,7 @@ struct ugeth_mii_info {
|
|||
/* And management functions */
|
||||
struct phy_info *phyinfo;
|
||||
|
||||
ucc_mii_mng_t *mii_regs;
|
||||
struct ucc_mii_mng *mii_regs;
|
||||
|
||||
/* forced speed & duplex (no autoneg)
|
||||
* partner speed & duplex & pause (autoneg)
|
||||
|
|
|
@ -2867,7 +2867,6 @@ static int ch_config(pc300dev_t * d)
|
|||
uclong clktype = chan->conf.phys_settings.clock_type;
|
||||
ucshort encoding = chan->conf.proto_settings.encoding;
|
||||
ucshort parity = chan->conf.proto_settings.parity;
|
||||
int tmc, br;
|
||||
ucchar md0, md2;
|
||||
|
||||
/* Reset the channel */
|
||||
|
@ -2940,8 +2939,12 @@ static int ch_config(pc300dev_t * d)
|
|||
case PC300_RSV:
|
||||
case PC300_X21:
|
||||
if (clktype == CLOCK_INT || clktype == CLOCK_TXINT) {
|
||||
int tmc, br;
|
||||
|
||||
/* Calculate the clkrate parameters */
|
||||
tmc = clock_rate_calc(clkrate, card->hw.clock, &br);
|
||||
if (tmc < 0)
|
||||
return -EIO;
|
||||
cpc_writeb(scabase + M_REG(TMCT, ch), tmc);
|
||||
cpc_writeb(scabase + M_REG(TXS, ch),
|
||||
(TXS_DTRXC | TXS_IBRG | br));
|
||||
|
@ -3097,14 +3100,16 @@ static int cpc_attach(struct net_device *dev, unsigned short encoding,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void cpc_opench(pc300dev_t * d)
|
||||
static int cpc_opench(pc300dev_t * d)
|
||||
{
|
||||
pc300ch_t *chan = (pc300ch_t *) d->chan;
|
||||
pc300_t *card = (pc300_t *) chan->card;
|
||||
int ch = chan->channel;
|
||||
int ch = chan->channel, rc;
|
||||
void __iomem *scabase = card->hw.scabase;
|
||||
|
||||
ch_config(d);
|
||||
rc = ch_config(d);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
rx_config(d);
|
||||
|
||||
|
@ -3113,6 +3118,8 @@ static void cpc_opench(pc300dev_t * d)
|
|||
/* Assert RTS and DTR */
|
||||
cpc_writeb(scabase + M_REG(CTL, ch),
|
||||
cpc_readb(scabase + M_REG(CTL, ch)) & ~(CTL_RTS | CTL_DTR));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void cpc_closech(pc300dev_t * d)
|
||||
|
@ -3168,9 +3175,16 @@ int cpc_open(struct net_device *dev)
|
|||
}
|
||||
|
||||
sprintf(ifr.ifr_name, "%s", dev->name);
|
||||
cpc_opench(d);
|
||||
result = cpc_opench(d);
|
||||
if (result)
|
||||
goto err_out;
|
||||
|
||||
netif_start_queue(dev);
|
||||
return 0;
|
||||
|
||||
err_out:
|
||||
hdlc_close(dev);
|
||||
return result;
|
||||
}
|
||||
|
||||
static int cpc_close(struct net_device *dev)
|
||||
|
|
|
@ -2897,6 +2897,8 @@ static struct net_device *_init_airo_card( unsigned short irq, int port,
|
|||
goto err_out_map;
|
||||
}
|
||||
ai->wifidev = init_wifidev(ai, dev);
|
||||
if (!ai->wifidev)
|
||||
goto err_out_reg;
|
||||
|
||||
set_bit(FLAG_REGISTERED,&ai->flags);
|
||||
airo_print_info(dev->name, "MAC enabled %x:%x:%x:%x:%x:%x",
|
||||
|
@ -2908,11 +2910,18 @@ static struct net_device *_init_airo_card( unsigned short irq, int port,
|
|||
for( i = 0; i < MAX_FIDS; i++ )
|
||||
ai->fids[i] = transmit_allocate(ai,AIRO_DEF_MTU,i>=MAX_FIDS/2);
|
||||
|
||||
setup_proc_entry( dev, dev->priv ); /* XXX check for failure */
|
||||
if (setup_proc_entry(dev, dev->priv) < 0)
|
||||
goto err_out_wifi;
|
||||
|
||||
netif_start_queue(dev);
|
||||
SET_MODULE_OWNER(dev);
|
||||
return dev;
|
||||
|
||||
err_out_wifi:
|
||||
unregister_netdev(ai->wifidev);
|
||||
free_netdev(ai->wifidev);
|
||||
err_out_reg:
|
||||
unregister_netdev(dev);
|
||||
err_out_map:
|
||||
if (test_bit(FLAG_MPI,&ai->flags) && pci) {
|
||||
pci_free_consistent(pci, PCI_SHARED_LEN, ai->shared, ai->shared_dma);
|
||||
|
@ -3089,7 +3098,8 @@ static int airo_thread(void *data) {
|
|||
set_bit(JOB_AUTOWEP, &ai->jobs);
|
||||
break;
|
||||
}
|
||||
if (!kthread_should_stop()) {
|
||||
if (!kthread_should_stop() &&
|
||||
!freezing(current)) {
|
||||
unsigned long wake_at;
|
||||
if (!ai->expires || !ai->scan_timeout) {
|
||||
wake_at = max(ai->expires,
|
||||
|
@ -3101,7 +3111,8 @@ static int airo_thread(void *data) {
|
|||
schedule_timeout(wake_at - jiffies);
|
||||
continue;
|
||||
}
|
||||
} else if (!kthread_should_stop()) {
|
||||
} else if (!kthread_should_stop() &&
|
||||
!freezing(current)) {
|
||||
schedule();
|
||||
continue;
|
||||
}
|
||||
|
@ -4495,91 +4506,128 @@ static int setup_proc_entry( struct net_device *dev,
|
|||
apriv->proc_entry = create_proc_entry(apriv->proc_name,
|
||||
S_IFDIR|airo_perm,
|
||||
airo_entry);
|
||||
apriv->proc_entry->uid = proc_uid;
|
||||
apriv->proc_entry->gid = proc_gid;
|
||||
apriv->proc_entry->owner = THIS_MODULE;
|
||||
if (!apriv->proc_entry)
|
||||
goto fail;
|
||||
apriv->proc_entry->uid = proc_uid;
|
||||
apriv->proc_entry->gid = proc_gid;
|
||||
apriv->proc_entry->owner = THIS_MODULE;
|
||||
|
||||
/* Setup the StatsDelta */
|
||||
entry = create_proc_entry("StatsDelta",
|
||||
S_IFREG | (S_IRUGO&proc_perm),
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_stats_delta;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_statsdelta_ops);
|
||||
|
||||
/* Setup the Stats */
|
||||
entry = create_proc_entry("Stats",
|
||||
S_IFREG | (S_IRUGO&proc_perm),
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_stats;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_stats_ops);
|
||||
|
||||
/* Setup the Status */
|
||||
entry = create_proc_entry("Status",
|
||||
S_IFREG | (S_IRUGO&proc_perm),
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_status;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_status_ops);
|
||||
|
||||
/* Setup the Config */
|
||||
entry = create_proc_entry("Config",
|
||||
S_IFREG | proc_perm,
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_config;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_config_ops);
|
||||
|
||||
/* Setup the SSID */
|
||||
entry = create_proc_entry("SSID",
|
||||
S_IFREG | proc_perm,
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_ssid;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_SSID_ops);
|
||||
|
||||
/* Setup the APList */
|
||||
entry = create_proc_entry("APList",
|
||||
S_IFREG | proc_perm,
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_aplist;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_APList_ops);
|
||||
|
||||
/* Setup the BSSList */
|
||||
entry = create_proc_entry("BSSList",
|
||||
S_IFREG | proc_perm,
|
||||
apriv->proc_entry);
|
||||
if (!entry)
|
||||
goto fail_bsslist;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_BSSList_ops);
|
||||
|
||||
/* Setup the WepKey */
|
||||
entry = create_proc_entry("WepKey",
|
||||
S_IFREG | proc_perm,
|
||||
apriv->proc_entry);
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
if (!entry)
|
||||
goto fail_wepkey;
|
||||
entry->uid = proc_uid;
|
||||
entry->gid = proc_gid;
|
||||
entry->data = dev;
|
||||
entry->owner = THIS_MODULE;
|
||||
entry->owner = THIS_MODULE;
|
||||
SETPROC_OPS(entry, proc_wepkey_ops);
|
||||
|
||||
return 0;
|
||||
|
||||
fail_wepkey:
|
||||
remove_proc_entry("BSSList", apriv->proc_entry);
|
||||
fail_bsslist:
|
||||
remove_proc_entry("APList", apriv->proc_entry);
|
||||
fail_aplist:
|
||||
remove_proc_entry("SSID", apriv->proc_entry);
|
||||
fail_ssid:
|
||||
remove_proc_entry("Config", apriv->proc_entry);
|
||||
fail_config:
|
||||
remove_proc_entry("Status", apriv->proc_entry);
|
||||
fail_status:
|
||||
remove_proc_entry("Stats", apriv->proc_entry);
|
||||
fail_stats:
|
||||
remove_proc_entry("StatsDelta", apriv->proc_entry);
|
||||
fail_stats_delta:
|
||||
remove_proc_entry(apriv->proc_name, airo_entry);
|
||||
fail:
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
static int takedown_proc_entry( struct net_device *dev,
|
||||
|
@ -5924,7 +5972,6 @@ static int airo_get_essid(struct net_device *dev,
|
|||
|
||||
/* Get the current SSID */
|
||||
memcpy(extra, status_rid.SSID, status_rid.SSIDlen);
|
||||
extra[status_rid.SSIDlen] = '\0';
|
||||
/* If none, we may want to get the one that was set */
|
||||
|
||||
/* Push it out ! */
|
||||
|
|
|
@ -1678,11 +1678,9 @@ static int atmel_get_essid(struct net_device *dev,
|
|||
/* Get the current SSID */
|
||||
if (priv->new_SSID_size != 0) {
|
||||
memcpy(extra, priv->new_SSID, priv->new_SSID_size);
|
||||
extra[priv->new_SSID_size] = '\0';
|
||||
dwrq->length = priv->new_SSID_size;
|
||||
} else {
|
||||
memcpy(extra, priv->SSID, priv->SSID_size);
|
||||
extra[priv->SSID_size] = '\0';
|
||||
dwrq->length = priv->SSID_size;
|
||||
}
|
||||
|
||||
|
|
|
@ -705,11 +705,30 @@ int bcm43xx_dma_init(struct bcm43xx_private *bcm)
|
|||
struct bcm43xx_dmaring *ring;
|
||||
int err = -ENOMEM;
|
||||
int dma64 = 0;
|
||||
u32 sbtmstatehi;
|
||||
u64 mask = bcm43xx_get_supported_dma_mask(bcm);
|
||||
int nobits;
|
||||
|
||||
sbtmstatehi = bcm43xx_read32(bcm, BCM43xx_CIR_SBTMSTATEHIGH);
|
||||
if (sbtmstatehi & BCM43xx_SBTMSTATEHIGH_DMA64BIT)
|
||||
if (mask == DMA_64BIT_MASK) {
|
||||
dma64 = 1;
|
||||
nobits = 64;
|
||||
} else if (mask == DMA_32BIT_MASK)
|
||||
nobits = 32;
|
||||
else
|
||||
nobits = 30;
|
||||
err = pci_set_dma_mask(bcm->pci_dev, mask);
|
||||
err |= pci_set_consistent_dma_mask(bcm->pci_dev, mask);
|
||||
if (err) {
|
||||
#ifdef CONFIG_BCM43XX_PIO
|
||||
printk(KERN_WARNING PFX "DMA not supported on this device."
|
||||
" Falling back to PIO.\n");
|
||||
bcm->__using_pio = 1;
|
||||
return -ENOSYS;
|
||||
#else
|
||||
printk(KERN_ERR PFX "FATAL: DMA not supported and PIO not configured. "
|
||||
"Please recompile the driver with PIO support.\n");
|
||||
return -ENODEV;
|
||||
#endif /* CONFIG_BCM43XX_PIO */
|
||||
}
|
||||
|
||||
/* setup TX DMA channels. */
|
||||
ring = bcm43xx_setup_dmaring(bcm, 0, 1, dma64);
|
||||
|
@ -755,8 +774,7 @@ int bcm43xx_dma_init(struct bcm43xx_private *bcm)
|
|||
dma->rx_ring3 = ring;
|
||||
}
|
||||
|
||||
dprintk(KERN_INFO PFX "%s DMA initialized\n",
|
||||
dma64 ? "64-bit" : "32-bit");
|
||||
dprintk(KERN_INFO PFX "%d-bit DMA initialized\n", nobits);
|
||||
err = 0;
|
||||
out:
|
||||
return err;
|
||||
|
|
|
@ -314,6 +314,23 @@ int bcm43xx_dma_tx(struct bcm43xx_private *bcm,
|
|||
struct ieee80211_txb *txb);
|
||||
void bcm43xx_dma_rx(struct bcm43xx_dmaring *ring);
|
||||
|
||||
/* Helper function that returns the dma mask for this device. */
|
||||
static inline
|
||||
u64 bcm43xx_get_supported_dma_mask(struct bcm43xx_private *bcm)
|
||||
{
|
||||
int dma64 = bcm43xx_read32(bcm, BCM43xx_CIR_SBTMSTATEHIGH) &
|
||||
BCM43xx_SBTMSTATEHIGH_DMA64BIT;
|
||||
u16 mmio_base = bcm43xx_dmacontroller_base(dma64, 0);
|
||||
u32 mask = BCM43xx_DMA32_TXADDREXT_MASK;
|
||||
|
||||
if (dma64)
|
||||
return DMA_64BIT_MASK;
|
||||
bcm43xx_write32(bcm, mmio_base + BCM43xx_DMA32_TXCTL, mask);
|
||||
if (bcm43xx_read32(bcm, mmio_base + BCM43xx_DMA32_TXCTL) & mask)
|
||||
return DMA_32BIT_MASK;
|
||||
return DMA_30BIT_MASK;
|
||||
}
|
||||
|
||||
#else /* CONFIG_BCM43XX_DMA */
|
||||
|
||||
|
||||
|
|
|
@ -242,7 +242,7 @@ void bcm43xx_leds_update(struct bcm43xx_private *bcm, int activity)
|
|||
//TODO
|
||||
break;
|
||||
case BCM43xx_LED_ASSOC:
|
||||
if (bcm->softmac->associated)
|
||||
if (bcm->softmac->associnfo.associated)
|
||||
turn_on = 1;
|
||||
break;
|
||||
#ifdef CONFIG_BCM43XX_DEBUG
|
||||
|
|
|
@ -2925,10 +2925,13 @@ static int bcm43xx_wireless_core_init(struct bcm43xx_private *bcm,
|
|||
bcm43xx_write16(bcm, 0x043C, 0x000C);
|
||||
|
||||
if (active_wlcore) {
|
||||
if (bcm43xx_using_pio(bcm))
|
||||
if (bcm43xx_using_pio(bcm)) {
|
||||
err = bcm43xx_pio_init(bcm);
|
||||
else
|
||||
} else {
|
||||
err = bcm43xx_dma_init(bcm);
|
||||
if (err == -ENOSYS)
|
||||
err = bcm43xx_pio_init(bcm);
|
||||
}
|
||||
if (err)
|
||||
goto err_chip_cleanup;
|
||||
}
|
||||
|
@ -3164,12 +3167,12 @@ static void bcm43xx_periodic_work_handler(void *d)
|
|||
u32 savedirqs = 0;
|
||||
int badness;
|
||||
|
||||
mutex_lock(&bcm->mutex);
|
||||
badness = estimate_periodic_work_badness(bcm->periodic_state);
|
||||
if (badness > BADNESS_LIMIT) {
|
||||
/* Periodic work will take a long time, so we want it to
|
||||
* be preemtible.
|
||||
*/
|
||||
mutex_lock(&bcm->mutex);
|
||||
netif_tx_disable(bcm->net_dev);
|
||||
spin_lock_irqsave(&bcm->irq_lock, flags);
|
||||
bcm43xx_mac_suspend(bcm);
|
||||
|
@ -3182,7 +3185,6 @@ static void bcm43xx_periodic_work_handler(void *d)
|
|||
/* Periodic work should take short time, so we want low
|
||||
* locking overhead.
|
||||
*/
|
||||
mutex_lock(&bcm->mutex);
|
||||
spin_lock_irqsave(&bcm->irq_lock, flags);
|
||||
}
|
||||
|
||||
|
@ -3993,8 +3995,6 @@ static int bcm43xx_init_private(struct bcm43xx_private *bcm,
|
|||
struct net_device *net_dev,
|
||||
struct pci_dev *pci_dev)
|
||||
{
|
||||
int err;
|
||||
|
||||
bcm43xx_set_status(bcm, BCM43xx_STAT_UNINIT);
|
||||
bcm->ieee = netdev_priv(net_dev);
|
||||
bcm->softmac = ieee80211_priv(net_dev);
|
||||
|
@ -4012,22 +4012,8 @@ static int bcm43xx_init_private(struct bcm43xx_private *bcm,
|
|||
(void (*)(unsigned long))bcm43xx_interrupt_tasklet,
|
||||
(unsigned long)bcm);
|
||||
tasklet_disable_nosync(&bcm->isr_tasklet);
|
||||
if (modparam_pio) {
|
||||
if (modparam_pio)
|
||||
bcm->__using_pio = 1;
|
||||
} else {
|
||||
err = pci_set_dma_mask(pci_dev, DMA_30BIT_MASK);
|
||||
err |= pci_set_consistent_dma_mask(pci_dev, DMA_30BIT_MASK);
|
||||
if (err) {
|
||||
#ifdef CONFIG_BCM43XX_PIO
|
||||
printk(KERN_WARNING PFX "DMA not supported. Falling back to PIO.\n");
|
||||
bcm->__using_pio = 1;
|
||||
#else
|
||||
printk(KERN_ERR PFX "FATAL: DMA not supported and PIO not configured. "
|
||||
"Recompile the driver with PIO support, please.\n");
|
||||
return -ENODEV;
|
||||
#endif /* CONFIG_BCM43XX_PIO */
|
||||
}
|
||||
}
|
||||
bcm->rts_threshold = BCM43xx_DEFAULT_RTS_THRESHOLD;
|
||||
|
||||
/* default to sw encryption for now */
|
||||
|
@ -4208,7 +4194,11 @@ static int bcm43xx_resume(struct pci_dev *pdev)
|
|||
dprintk(KERN_INFO PFX "Resuming...\n");
|
||||
|
||||
pci_set_power_state(pdev, 0);
|
||||
pci_enable_device(pdev);
|
||||
err = pci_enable_device(pdev);
|
||||
if (err) {
|
||||
printk(KERN_ERR PFX "Failure with pci_enable_device!\n");
|
||||
return err;
|
||||
}
|
||||
pci_restore_state(pdev);
|
||||
|
||||
bcm43xx_chipset_attach(bcm);
|
||||
|
|
|
@ -847,7 +847,7 @@ static struct iw_statistics *bcm43xx_get_wireless_stats(struct net_device *net_d
|
|||
unsigned long flags;
|
||||
|
||||
wstats = &bcm->stats.wstats;
|
||||
if (!mac->associated) {
|
||||
if (!mac->associnfo.associated) {
|
||||
wstats->miss.beacon = 0;
|
||||
// bcm->ieee->ieee_stats.tx_retry_limit_exceeded = 0; // FIXME: should this be cleared here?
|
||||
wstats->discard.retries = 0;
|
||||
|
|
|
@ -2457,6 +2457,7 @@ void free_orinocodev(struct net_device *dev)
|
|||
/* Wireless extensions */
|
||||
/********************************************************************/
|
||||
|
||||
/* Return : < 0 -> error code ; >= 0 -> length */
|
||||
static int orinoco_hw_get_essid(struct orinoco_private *priv, int *active,
|
||||
char buf[IW_ESSID_MAX_SIZE+1])
|
||||
{
|
||||
|
@ -2501,9 +2502,9 @@ static int orinoco_hw_get_essid(struct orinoco_private *priv, int *active,
|
|||
len = le16_to_cpu(essidbuf.len);
|
||||
BUG_ON(len > IW_ESSID_MAX_SIZE);
|
||||
|
||||
memset(buf, 0, IW_ESSID_MAX_SIZE+1);
|
||||
memset(buf, 0, IW_ESSID_MAX_SIZE);
|
||||
memcpy(buf, p, len);
|
||||
buf[len] = '\0';
|
||||
err = len;
|
||||
|
||||
fail_unlock:
|
||||
orinoco_unlock(priv, &flags);
|
||||
|
@ -3027,17 +3028,18 @@ static int orinoco_ioctl_getessid(struct net_device *dev,
|
|||
|
||||
if (netif_running(dev)) {
|
||||
err = orinoco_hw_get_essid(priv, &active, essidbuf);
|
||||
if (err)
|
||||
if (err < 0)
|
||||
return err;
|
||||
erq->length = err;
|
||||
} else {
|
||||
if (orinoco_lock(priv, &flags) != 0)
|
||||
return -EBUSY;
|
||||
memcpy(essidbuf, priv->desired_essid, IW_ESSID_MAX_SIZE + 1);
|
||||
memcpy(essidbuf, priv->desired_essid, IW_ESSID_MAX_SIZE);
|
||||
erq->length = strlen(priv->desired_essid);
|
||||
orinoco_unlock(priv, &flags);
|
||||
}
|
||||
|
||||
erq->flags = 1;
|
||||
erq->length = strlen(essidbuf);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -3075,10 +3077,10 @@ static int orinoco_ioctl_getnick(struct net_device *dev,
|
|||
if (orinoco_lock(priv, &flags) != 0)
|
||||
return -EBUSY;
|
||||
|
||||
memcpy(nickbuf, priv->nick, IW_ESSID_MAX_SIZE+1);
|
||||
memcpy(nickbuf, priv->nick, IW_ESSID_MAX_SIZE);
|
||||
orinoco_unlock(priv, &flags);
|
||||
|
||||
nrq->length = strlen(nickbuf);
|
||||
nrq->length = strlen(priv->nick);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -1198,7 +1198,6 @@ static int ray_get_essid(struct net_device *dev,
|
|||
|
||||
/* Get the essid that was set */
|
||||
memcpy(extra, local->sparm.b5.a_current_ess_id, IW_ESSID_MAX_SIZE);
|
||||
extra[IW_ESSID_MAX_SIZE] = '\0';
|
||||
|
||||
/* Push it out ! */
|
||||
dwrq->length = strlen(extra);
|
||||
|
|
|
@ -193,10 +193,8 @@ static void zd1201_usbrx(struct urb *urb)
|
|||
struct sk_buff *skb;
|
||||
unsigned char type;
|
||||
|
||||
if (!zd) {
|
||||
free = 1;
|
||||
goto exit;
|
||||
}
|
||||
if (!zd)
|
||||
return;
|
||||
|
||||
switch(urb->status) {
|
||||
case -EILSEQ:
|
||||
|
|
|
@ -1099,7 +1099,7 @@ static void link_led_handler(void *p)
|
|||
int r;
|
||||
|
||||
spin_lock_irq(&mac->lock);
|
||||
is_associated = sm->associated != 0;
|
||||
is_associated = sm->associnfo.associated != 0;
|
||||
spin_unlock_irq(&mac->lock);
|
||||
|
||||
r = zd_chip_control_leds(chip,
|
||||
|
|
|
@ -63,13 +63,11 @@ struct ieee80211softmac_wpa {
|
|||
|
||||
/*
|
||||
* Information about association
|
||||
*
|
||||
* Do we need a lock for this?
|
||||
* We only ever use this structure inlined
|
||||
* into our global struct. I've used its lock,
|
||||
* but maybe we need a local one here?
|
||||
*/
|
||||
struct ieee80211softmac_assoc_info {
|
||||
|
||||
struct mutex mutex;
|
||||
|
||||
/*
|
||||
* This is the requested ESSID. It is written
|
||||
* only by the WX handlers.
|
||||
|
@ -99,12 +97,13 @@ struct ieee80211softmac_assoc_info {
|
|||
*
|
||||
* bssfixed is used for SIOCSIWAP.
|
||||
*/
|
||||
u8 static_essid:1,
|
||||
short_preamble_available:1,
|
||||
associating:1,
|
||||
assoc_wait:1,
|
||||
bssvalid:1,
|
||||
bssfixed:1;
|
||||
u8 static_essid;
|
||||
u8 short_preamble_available;
|
||||
u8 associating;
|
||||
u8 associated;
|
||||
u8 assoc_wait;
|
||||
u8 bssvalid;
|
||||
u8 bssfixed;
|
||||
|
||||
/* Scan retries remaining */
|
||||
int scan_retry;
|
||||
|
@ -229,12 +228,10 @@ struct ieee80211softmac_device {
|
|||
/* private stuff follows */
|
||||
/* this lock protects this structure */
|
||||
spinlock_t lock;
|
||||
|
||||
/* couple of flags */
|
||||
u8 scanning:1, /* protects scanning from being done multiple times at once */
|
||||
associated:1,
|
||||
running:1;
|
||||
|
||||
|
||||
u8 running; /* SoftMAC started? */
|
||||
u8 scanning;
|
||||
|
||||
struct ieee80211softmac_scaninfo *scaninfo;
|
||||
struct ieee80211softmac_assoc_info associnfo;
|
||||
struct ieee80211softmac_bss_info bssinfo;
|
||||
|
@ -250,7 +247,7 @@ struct ieee80211softmac_device {
|
|||
|
||||
/* we need to keep a list of network structs we copied */
|
||||
struct list_head network_list;
|
||||
|
||||
|
||||
/* This must be the last item so that it points to the data
|
||||
* allocated beyond this structure by alloc_ieee80211 */
|
||||
u8 priv[0];
|
||||
|
@ -295,7 +292,7 @@ static inline u8 ieee80211softmac_suggest_txrate(struct ieee80211softmac_device
|
|||
{
|
||||
struct ieee80211softmac_txrates *txrates = &mac->txrates;
|
||||
|
||||
if (!mac->associated)
|
||||
if (!mac->associnfo.associated)
|
||||
return txrates->mgt_mcast_rate;
|
||||
|
||||
/* We are associated, sending unicast frame */
|
||||
|
|
|
@ -748,11 +748,39 @@ static int ioctl_standard_call(struct net_device * dev,
|
|||
int extra_size;
|
||||
int user_length = 0;
|
||||
int err;
|
||||
int essid_compat = 0;
|
||||
|
||||
/* Calculate space needed by arguments. Always allocate
|
||||
* for max space. Easier, and won't last long... */
|
||||
extra_size = descr->max_tokens * descr->token_size;
|
||||
|
||||
/* Check need for ESSID compatibility for WE < 21 */
|
||||
switch (cmd) {
|
||||
case SIOCSIWESSID:
|
||||
case SIOCGIWESSID:
|
||||
case SIOCSIWNICKN:
|
||||
case SIOCGIWNICKN:
|
||||
if (iwr->u.data.length == descr->max_tokens + 1)
|
||||
essid_compat = 1;
|
||||
else if (IW_IS_SET(cmd) && (iwr->u.data.length != 0)) {
|
||||
char essid[IW_ESSID_MAX_SIZE + 1];
|
||||
|
||||
err = copy_from_user(essid, iwr->u.data.pointer,
|
||||
iwr->u.data.length *
|
||||
descr->token_size);
|
||||
if (err)
|
||||
return -EFAULT;
|
||||
|
||||
if (essid[iwr->u.data.length - 1] == '\0')
|
||||
essid_compat = 1;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
iwr->u.data.length -= essid_compat;
|
||||
|
||||
/* Check what user space is giving us */
|
||||
if(IW_IS_SET(cmd)) {
|
||||
/* Check NULL pointer */
|
||||
|
@ -795,7 +823,8 @@ static int ioctl_standard_call(struct net_device * dev,
|
|||
#endif /* WE_IOCTL_DEBUG */
|
||||
|
||||
/* Create the kernel buffer */
|
||||
extra = kmalloc(extra_size, GFP_KERNEL);
|
||||
/* kzalloc ensures NULL-termination for essid_compat */
|
||||
extra = kzalloc(extra_size, GFP_KERNEL);
|
||||
if (extra == NULL) {
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
@ -819,6 +848,8 @@ static int ioctl_standard_call(struct net_device * dev,
|
|||
/* Call the handler */
|
||||
ret = handler(dev, &info, &(iwr->u), extra);
|
||||
|
||||
iwr->u.data.length += essid_compat;
|
||||
|
||||
/* If we have something to return to the user */
|
||||
if (!ret && IW_IS_GET(cmd)) {
|
||||
/* Check if there is enough buffer up there */
|
||||
|
|
|
@ -48,7 +48,7 @@ ieee80211softmac_assoc(struct ieee80211softmac_device *mac, struct ieee80211soft
|
|||
dprintk(KERN_INFO PFX "sent association request!\n");
|
||||
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mac->associated = 0; /* just to make sure */
|
||||
mac->associnfo.associated = 0; /* just to make sure */
|
||||
|
||||
/* Set a timer for timeout */
|
||||
/* FIXME: make timeout configurable */
|
||||
|
@ -62,24 +62,22 @@ ieee80211softmac_assoc_timeout(void *d)
|
|||
{
|
||||
struct ieee80211softmac_device *mac = (struct ieee80211softmac_device *)d;
|
||||
struct ieee80211softmac_network *n;
|
||||
unsigned long flags;
|
||||
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
/* we might race against ieee80211softmac_handle_assoc_response,
|
||||
* so make sure only one of us does something */
|
||||
if (!mac->associnfo.associating) {
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
return;
|
||||
}
|
||||
if (!mac->associnfo.associating)
|
||||
goto out;
|
||||
mac->associnfo.associating = 0;
|
||||
mac->associnfo.bssvalid = 0;
|
||||
mac->associated = 0;
|
||||
mac->associnfo.associated = 0;
|
||||
|
||||
n = ieee80211softmac_get_network_by_bssid_locked(mac, mac->associnfo.bssid);
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
|
||||
dprintk(KERN_INFO PFX "assoc request timed out!\n");
|
||||
ieee80211softmac_call_events(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_TIMEOUT, n);
|
||||
out:
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -93,7 +91,7 @@ ieee80211softmac_disassoc(struct ieee80211softmac_device *mac)
|
|||
|
||||
netif_carrier_off(mac->dev);
|
||||
|
||||
mac->associated = 0;
|
||||
mac->associnfo.associated = 0;
|
||||
mac->associnfo.bssvalid = 0;
|
||||
mac->associnfo.associating = 0;
|
||||
ieee80211softmac_init_bss(mac);
|
||||
|
@ -107,7 +105,7 @@ ieee80211softmac_send_disassoc_req(struct ieee80211softmac_device *mac, u16 reas
|
|||
{
|
||||
struct ieee80211softmac_network *found;
|
||||
|
||||
if (mac->associnfo.bssvalid && mac->associated) {
|
||||
if (mac->associnfo.bssvalid && mac->associnfo.associated) {
|
||||
found = ieee80211softmac_get_network_by_bssid(mac, mac->associnfo.bssid);
|
||||
if (found)
|
||||
ieee80211softmac_send_mgt_frame(mac, found, IEEE80211_STYPE_DISASSOC, reason);
|
||||
|
@ -196,17 +194,18 @@ ieee80211softmac_assoc_work(void *d)
|
|||
int bssvalid;
|
||||
unsigned long flags;
|
||||
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
|
||||
if (!mac->associnfo.associating)
|
||||
goto out;
|
||||
|
||||
/* ieee80211_disassoc might clear this */
|
||||
bssvalid = mac->associnfo.bssvalid;
|
||||
|
||||
/* meh */
|
||||
if (mac->associated)
|
||||
if (mac->associnfo.associated)
|
||||
ieee80211softmac_send_disassoc_req(mac, WLAN_REASON_DISASSOC_STA_HAS_LEFT);
|
||||
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mac->associnfo.associating = 1;
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
|
||||
/* try to find the requested network in our list, if we found one already */
|
||||
if (bssvalid || mac->associnfo.bssfixed)
|
||||
found = ieee80211softmac_get_network_by_bssid(mac, mac->associnfo.bssid);
|
||||
|
@ -260,10 +259,8 @@ ieee80211softmac_assoc_work(void *d)
|
|||
|
||||
if (!found) {
|
||||
if (mac->associnfo.scan_retry > 0) {
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mac->associnfo.scan_retry--;
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
|
||||
|
||||
/* We know of no such network. Let's scan.
|
||||
* NB: this also happens if we had no memory to copy the network info...
|
||||
* Maybe we can hope to have more memory after scanning finishes ;)
|
||||
|
@ -272,19 +269,17 @@ ieee80211softmac_assoc_work(void *d)
|
|||
ieee80211softmac_notify(mac->dev, IEEE80211SOFTMAC_EVENT_SCAN_FINISHED, ieee80211softmac_assoc_notify_scan, NULL);
|
||||
if (ieee80211softmac_start_scan(mac))
|
||||
dprintk(KERN_INFO PFX "Associate: failed to initiate scan. Is device up?\n");
|
||||
return;
|
||||
goto out;
|
||||
} else {
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mac->associnfo.associating = 0;
|
||||
mac->associated = 0;
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
mac->associnfo.associated = 0;
|
||||
|
||||
dprintk(KERN_INFO PFX "Unable to find matching network after scan!\n");
|
||||
/* reset the retry counter for the next user request since we
|
||||
* break out and don't reschedule ourselves after this point. */
|
||||
mac->associnfo.scan_retry = IEEE80211SOFTMAC_ASSOC_SCAN_RETRY_LIMIT;
|
||||
ieee80211softmac_call_events(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_NET_NOT_FOUND, NULL);
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -297,7 +292,7 @@ ieee80211softmac_assoc_work(void *d)
|
|||
/* copy the ESSID for displaying it */
|
||||
mac->associnfo.associate_essid.len = found->essid.len;
|
||||
memcpy(mac->associnfo.associate_essid.data, found->essid.data, IW_ESSID_MAX_SIZE + 1);
|
||||
|
||||
|
||||
/* we found a network! authenticate (if necessary) and associate to it. */
|
||||
if (found->authenticating) {
|
||||
dprintk(KERN_INFO PFX "Already requested authentication, waiting...\n");
|
||||
|
@ -305,7 +300,7 @@ ieee80211softmac_assoc_work(void *d)
|
|||
mac->associnfo.assoc_wait = 1;
|
||||
ieee80211softmac_notify_internal(mac, IEEE80211SOFTMAC_EVENT_ANY, found, ieee80211softmac_assoc_notify_auth, NULL, GFP_KERNEL);
|
||||
}
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
if (!found->authenticated && !found->authenticating) {
|
||||
/* This relies on the fact that _auth_req only queues the work,
|
||||
|
@ -321,11 +316,14 @@ ieee80211softmac_assoc_work(void *d)
|
|||
mac->associnfo.assoc_wait = 0;
|
||||
ieee80211softmac_call_events(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_FAILED, found);
|
||||
}
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
/* finally! now we can start associating */
|
||||
mac->associnfo.assoc_wait = 0;
|
||||
ieee80211softmac_assoc(mac, found);
|
||||
|
||||
out:
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
}
|
||||
|
||||
/* call this to do whatever is necessary when we're associated */
|
||||
|
@ -341,7 +339,7 @@ ieee80211softmac_associated(struct ieee80211softmac_device *mac,
|
|||
mac->bssinfo.supported_rates = net->supported_rates;
|
||||
ieee80211softmac_recalc_txrates(mac);
|
||||
|
||||
mac->associated = 1;
|
||||
mac->associnfo.associated = 1;
|
||||
|
||||
mac->associnfo.short_preamble_available =
|
||||
(cap & WLAN_CAPABILITY_SHORT_PREAMBLE) != 0;
|
||||
|
@ -421,7 +419,7 @@ ieee80211softmac_handle_assoc_response(struct net_device * dev,
|
|||
dprintk(KERN_INFO PFX "associating failed (reason: 0x%x)!\n", status);
|
||||
mac->associnfo.associating = 0;
|
||||
mac->associnfo.bssvalid = 0;
|
||||
mac->associated = 0;
|
||||
mac->associnfo.associated = 0;
|
||||
ieee80211softmac_call_events_locked(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_FAILED, network);
|
||||
}
|
||||
|
||||
|
|
|
@ -304,7 +304,7 @@ ieee80211softmac_auth(struct ieee80211_auth **pkt,
|
|||
2 + /* Auth Transaction Seq */
|
||||
2 + /* Status Code */
|
||||
/* Challenge Text IE */
|
||||
is_shared_response ? 0 : 1 + 1 + net->challenge_len
|
||||
(is_shared_response ? 1 + 1 + net->challenge_len : 0)
|
||||
);
|
||||
if (unlikely((*pkt) == NULL))
|
||||
return 0;
|
||||
|
@ -475,8 +475,13 @@ int ieee80211softmac_handle_beacon(struct net_device *dev,
|
|||
{
|
||||
struct ieee80211softmac_device *mac = ieee80211_priv(dev);
|
||||
|
||||
if (mac->associated && memcmp(network->bssid, mac->associnfo.bssid, ETH_ALEN) == 0)
|
||||
ieee80211softmac_process_erp(mac, network->erp_value);
|
||||
/* This might race, but we don't really care and it's not worth
|
||||
* adding heavyweight locking in this fastpath.
|
||||
*/
|
||||
if (mac->associnfo.associated) {
|
||||
if (memcmp(network->bssid, mac->associnfo.bssid, ETH_ALEN) == 0)
|
||||
ieee80211softmac_process_erp(mac, network->erp_value);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -57,6 +57,7 @@ struct net_device *alloc_ieee80211softmac(int sizeof_priv)
|
|||
INIT_LIST_HEAD(&softmac->network_list);
|
||||
INIT_LIST_HEAD(&softmac->events);
|
||||
|
||||
mutex_init(&softmac->associnfo.mutex);
|
||||
INIT_WORK(&softmac->associnfo.work, ieee80211softmac_assoc_work, softmac);
|
||||
INIT_WORK(&softmac->associnfo.timeout, ieee80211softmac_assoc_timeout, softmac);
|
||||
softmac->start_scan = ieee80211softmac_start_scan_implementation;
|
||||
|
|
|
@ -73,13 +73,14 @@ ieee80211softmac_wx_set_essid(struct net_device *net_dev,
|
|||
struct ieee80211softmac_network *n;
|
||||
struct ieee80211softmac_auth_queue_item *authptr;
|
||||
int length = 0;
|
||||
unsigned long flags;
|
||||
|
||||
mutex_lock(&sm->associnfo.mutex);
|
||||
|
||||
/* Check if we're already associating to this or another network
|
||||
* If it's another network, cancel and start over with our new network
|
||||
* If it's our network, ignore the change, we're already doing it!
|
||||
*/
|
||||
if((sm->associnfo.associating || sm->associated) &&
|
||||
if((sm->associnfo.associating || sm->associnfo.associated) &&
|
||||
(data->essid.flags && data->essid.length)) {
|
||||
/* Get the associating network */
|
||||
n = ieee80211softmac_get_network_by_bssid(sm, sm->associnfo.bssid);
|
||||
|
@ -87,10 +88,9 @@ ieee80211softmac_wx_set_essid(struct net_device *net_dev,
|
|||
!memcmp(n->essid.data, extra, n->essid.len)) {
|
||||
dprintk(KERN_INFO PFX "Already associating or associated to "MAC_FMT"\n",
|
||||
MAC_ARG(sm->associnfo.bssid));
|
||||
return 0;
|
||||
goto out;
|
||||
} else {
|
||||
dprintk(KERN_INFO PFX "Canceling existing associate request!\n");
|
||||
spin_lock_irqsave(&sm->lock,flags);
|
||||
/* Cancel assoc work */
|
||||
cancel_delayed_work(&sm->associnfo.work);
|
||||
/* We don't have to do this, but it's a little cleaner */
|
||||
|
@ -98,14 +98,13 @@ ieee80211softmac_wx_set_essid(struct net_device *net_dev,
|
|||
cancel_delayed_work(&authptr->work);
|
||||
sm->associnfo.bssvalid = 0;
|
||||
sm->associnfo.bssfixed = 0;
|
||||
spin_unlock_irqrestore(&sm->lock,flags);
|
||||
flush_scheduled_work();
|
||||
sm->associnfo.associating = 0;
|
||||
sm->associnfo.associated = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
spin_lock_irqsave(&sm->lock, flags);
|
||||
|
||||
sm->associnfo.static_essid = 0;
|
||||
sm->associnfo.assoc_wait = 0;
|
||||
|
||||
|
@ -121,10 +120,12 @@ ieee80211softmac_wx_set_essid(struct net_device *net_dev,
|
|||
* If applicable, we have already copied the data in */
|
||||
sm->associnfo.req_essid.len = length;
|
||||
|
||||
sm->associnfo.associating = 1;
|
||||
/* queue lower level code to do work (if necessary) */
|
||||
schedule_work(&sm->associnfo.work);
|
||||
out:
|
||||
mutex_unlock(&sm->associnfo.mutex);
|
||||
|
||||
spin_unlock_irqrestore(&sm->lock, flags);
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_set_essid);
|
||||
|
@ -136,10 +137,8 @@ ieee80211softmac_wx_get_essid(struct net_device *net_dev,
|
|||
char *extra)
|
||||
{
|
||||
struct ieee80211softmac_device *sm = ieee80211_priv(net_dev);
|
||||
unsigned long flags;
|
||||
|
||||
/* avoid getting inconsistent information */
|
||||
spin_lock_irqsave(&sm->lock, flags);
|
||||
mutex_lock(&sm->associnfo.mutex);
|
||||
/* If all fails, return ANY (empty) */
|
||||
data->essid.length = 0;
|
||||
data->essid.flags = 0; /* active */
|
||||
|
@ -152,12 +151,13 @@ ieee80211softmac_wx_get_essid(struct net_device *net_dev,
|
|||
}
|
||||
|
||||
/* If we're associating/associated, return that */
|
||||
if (sm->associated || sm->associnfo.associating) {
|
||||
if (sm->associnfo.associated || sm->associnfo.associating) {
|
||||
data->essid.length = sm->associnfo.associate_essid.len;
|
||||
data->essid.flags = 1; /* active */
|
||||
memcpy(extra, sm->associnfo.associate_essid.data, sm->associnfo.associate_essid.len);
|
||||
}
|
||||
spin_unlock_irqrestore(&sm->lock, flags);
|
||||
mutex_unlock(&sm->associnfo.mutex);
|
||||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_get_essid);
|
||||
|
@ -322,15 +322,15 @@ ieee80211softmac_wx_get_wap(struct net_device *net_dev,
|
|||
{
|
||||
struct ieee80211softmac_device *mac = ieee80211_priv(net_dev);
|
||||
int err = 0;
|
||||
unsigned long flags;
|
||||
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
if (mac->associnfo.bssvalid)
|
||||
memcpy(data->ap_addr.sa_data, mac->associnfo.bssid, ETH_ALEN);
|
||||
else
|
||||
memset(data->ap_addr.sa_data, 0xff, ETH_ALEN);
|
||||
data->ap_addr.sa_family = ARPHRD_ETHER;
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_get_wap);
|
||||
|
@ -342,28 +342,27 @@ ieee80211softmac_wx_set_wap(struct net_device *net_dev,
|
|||
char *extra)
|
||||
{
|
||||
struct ieee80211softmac_device *mac = ieee80211_priv(net_dev);
|
||||
unsigned long flags;
|
||||
|
||||
/* sanity check */
|
||||
if (data->ap_addr.sa_family != ARPHRD_ETHER) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
if (is_broadcast_ether_addr(data->ap_addr.sa_data)) {
|
||||
/* the bssid we have is not to be fixed any longer,
|
||||
* and we should reassociate to the best AP. */
|
||||
mac->associnfo.bssfixed = 0;
|
||||
/* force reassociation */
|
||||
mac->associnfo.bssvalid = 0;
|
||||
if (mac->associated)
|
||||
if (mac->associnfo.associated)
|
||||
schedule_work(&mac->associnfo.work);
|
||||
} else if (is_zero_ether_addr(data->ap_addr.sa_data)) {
|
||||
/* the bssid we have is no longer fixed */
|
||||
mac->associnfo.bssfixed = 0;
|
||||
} else {
|
||||
if (!memcmp(mac->associnfo.bssid, data->ap_addr.sa_data, ETH_ALEN)) {
|
||||
if (mac->associnfo.associating || mac->associated) {
|
||||
if (mac->associnfo.associating || mac->associnfo.associated) {
|
||||
/* bssid unchanged and associated or associating - just return */
|
||||
goto out;
|
||||
}
|
||||
|
@ -378,7 +377,8 @@ ieee80211softmac_wx_set_wap(struct net_device *net_dev,
|
|||
}
|
||||
|
||||
out:
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_set_wap);
|
||||
|
@ -394,7 +394,8 @@ ieee80211softmac_wx_set_genie(struct net_device *dev,
|
|||
int err = 0;
|
||||
char *buf;
|
||||
int i;
|
||||
|
||||
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
/* bleh. shouldn't be locked for that kmalloc... */
|
||||
|
||||
|
@ -432,6 +433,8 @@ ieee80211softmac_wx_set_genie(struct net_device *dev,
|
|||
|
||||
out:
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_set_genie);
|
||||
|
@ -446,7 +449,8 @@ ieee80211softmac_wx_get_genie(struct net_device *dev,
|
|||
unsigned long flags;
|
||||
int err = 0;
|
||||
int space = wrqu->data.length;
|
||||
|
||||
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
spin_lock_irqsave(&mac->lock, flags);
|
||||
|
||||
wrqu->data.length = 0;
|
||||
|
@ -459,6 +463,8 @@ ieee80211softmac_wx_get_genie(struct net_device *dev,
|
|||
err = -E2BIG;
|
||||
}
|
||||
spin_unlock_irqrestore(&mac->lock, flags);
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_get_genie);
|
||||
|
@ -473,10 +479,13 @@ ieee80211softmac_wx_set_mlme(struct net_device *dev,
|
|||
struct iw_mlme *mlme = (struct iw_mlme *)extra;
|
||||
u16 reason = cpu_to_le16(mlme->reason_code);
|
||||
struct ieee80211softmac_network *net;
|
||||
int err = -EINVAL;
|
||||
|
||||
mutex_lock(&mac->associnfo.mutex);
|
||||
|
||||
if (memcmp(mac->associnfo.bssid, mlme->addr.sa_data, ETH_ALEN)) {
|
||||
printk(KERN_DEBUG PFX "wx_set_mlme: requested operation on net we don't use\n");
|
||||
return -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
switch (mlme->cmd) {
|
||||
|
@ -484,14 +493,22 @@ ieee80211softmac_wx_set_mlme(struct net_device *dev,
|
|||
net = ieee80211softmac_get_network_by_bssid_locked(mac, mlme->addr.sa_data);
|
||||
if (!net) {
|
||||
printk(KERN_DEBUG PFX "wx_set_mlme: we should know the net here...\n");
|
||||
return -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
return ieee80211softmac_deauth_req(mac, net, reason);
|
||||
case IW_MLME_DISASSOC:
|
||||
ieee80211softmac_send_disassoc_req(mac, reason);
|
||||
return 0;
|
||||
mac->associnfo.associated = 0;
|
||||
mac->associnfo.associating = 0;
|
||||
err = 0;
|
||||
goto out;
|
||||
default:
|
||||
return -EOPNOTSUPP;
|
||||
err = -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
out:
|
||||
mutex_unlock(&mac->associnfo.mutex);
|
||||
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ieee80211softmac_wx_set_mlme);
|
||||
|
|
Loading…
Reference in a new issue