aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/rt2x00/rt2500usb.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless/rt2x00/rt2500usb.c')
-rw-r--r--drivers/net/wireless/rt2x00/rt2500usb.c179
1 files changed, 102 insertions, 77 deletions
diff --git a/drivers/net/wireless/rt2x00/rt2500usb.c b/drivers/net/wireless/rt2x00/rt2500usb.c
index 614600c5510d..f4e6f6eb7fb5 100644
--- a/drivers/net/wireless/rt2x00/rt2500usb.c
+++ b/drivers/net/wireless/rt2x00/rt2500usb.c
@@ -282,65 +282,20 @@ static void rt2500usb_config_bssid(struct rt2x00_dev *rt2x00dev, u8 *bssid)
282 rt2500usb_register_multiwrite(rt2x00dev, MAC_CSR5, &reg, sizeof(reg)); 282 rt2500usb_register_multiwrite(rt2x00dev, MAC_CSR5, &reg, sizeof(reg));
283} 283}
284 284
285static void rt2500usb_config_packet_filter(struct rt2x00_dev *rt2x00dev,
286 const unsigned int filter)
287{
288 int promisc = !!(filter & IFF_PROMISC);
289 int multicast = !!(filter & IFF_MULTICAST);
290 int broadcast = !!(filter & IFF_BROADCAST);
291 u16 reg;
292
293 rt2500usb_register_read(rt2x00dev, TXRX_CSR2, &reg);
294 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_NOT_TO_ME, !promisc);
295 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_MULTICAST, !multicast);
296 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_BROADCAST, !broadcast);
297 rt2500usb_register_write(rt2x00dev, TXRX_CSR2, reg);
298}
299
300static void rt2500usb_config_type(struct rt2x00_dev *rt2x00dev, const int type) 285static void rt2500usb_config_type(struct rt2x00_dev *rt2x00dev, const int type)
301{ 286{
287 struct interface *intf = &rt2x00dev->interface;
302 u16 reg; 288 u16 reg;
303 289
304 rt2500usb_register_write(rt2x00dev, TXRX_CSR19, 0); 290 rt2500usb_register_write(rt2x00dev, TXRX_CSR19, 0);
305 291
306 /* 292 /*
307 * Apply hardware packet filter.
308 */
309 rt2500usb_register_read(rt2x00dev, TXRX_CSR2, &reg);
310
311 if (!is_monitor_present(&rt2x00dev->interface) &&
312 (type == IEEE80211_IF_TYPE_IBSS || type == IEEE80211_IF_TYPE_STA))
313 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_TODS, 1);
314 else
315 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_TODS, 0);
316
317 /*
318 * If there is a non-monitor interface present
319 * the packet should be strict (even if a monitor interface is present!).
320 * When there is only 1 interface present which is in monitor mode
321 * we should start accepting _all_ frames.
322 */
323 if (is_interface_present(&rt2x00dev->interface)) {
324 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CRC, 1);
325 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_PHYSICAL, 1);
326 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CONTROL, 1);
327 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_VERSION_ERROR, 1);
328 } else if (is_monitor_present(&rt2x00dev->interface)) {
329 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CRC, 0);
330 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_PHYSICAL, 0);
331 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CONTROL, 0);
332 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_VERSION_ERROR, 0);
333 }
334
335 rt2500usb_register_write(rt2x00dev, TXRX_CSR2, reg);
336
337 /*
338 * Enable beacon config 293 * Enable beacon config
339 */ 294 */
340 rt2500usb_register_read(rt2x00dev, TXRX_CSR20, &reg); 295 rt2500usb_register_read(rt2x00dev, TXRX_CSR20, &reg);
341 rt2x00_set_field16(&reg, TXRX_CSR20_OFFSET, 296 rt2x00_set_field16(&reg, TXRX_CSR20_OFFSET,
342 (PREAMBLE + get_duration(IEEE80211_HEADER, 2)) >> 6); 297 (PREAMBLE + get_duration(IEEE80211_HEADER, 2)) >> 6);
343 if (type == IEEE80211_IF_TYPE_STA) 298 if (is_interface_type(intf, IEEE80211_IF_TYPE_STA))
344 rt2x00_set_field16(&reg, TXRX_CSR20_BCN_EXPECT_WINDOW, 0); 299 rt2x00_set_field16(&reg, TXRX_CSR20_BCN_EXPECT_WINDOW, 0);
345 else 300 else
346 rt2x00_set_field16(&reg, TXRX_CSR20_BCN_EXPECT_WINDOW, 2); 301 rt2x00_set_field16(&reg, TXRX_CSR20_BCN_EXPECT_WINDOW, 2);
@@ -354,20 +309,16 @@ static void rt2500usb_config_type(struct rt2x00_dev *rt2x00dev, const int type)
354 rt2500usb_register_write(rt2x00dev, TXRX_CSR18, reg); 309 rt2500usb_register_write(rt2x00dev, TXRX_CSR18, reg);
355 310
356 rt2500usb_register_read(rt2x00dev, TXRX_CSR19, &reg); 311 rt2500usb_register_read(rt2x00dev, TXRX_CSR19, &reg);
357 if (is_interface_present(&rt2x00dev->interface)) { 312 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_COUNT, 1);
358 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_COUNT, 1); 313 rt2x00_set_field16(&reg, TXRX_CSR19_TBCN, 1);
359 rt2x00_set_field16(&reg, TXRX_CSR19_TBCN, 1);
360 }
361
362 rt2x00_set_field16(&reg, TXRX_CSR19_BEACON_GEN, 0); 314 rt2x00_set_field16(&reg, TXRX_CSR19_BEACON_GEN, 0);
363 if (type == IEEE80211_IF_TYPE_IBSS || type == IEEE80211_IF_TYPE_AP) 315 if (is_interface_type(intf, IEEE80211_IF_TYPE_IBSS) ||
316 is_interface_type(intf, IEEE80211_IF_TYPE_AP))
364 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 2); 317 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 2);
365 else if (type == IEEE80211_IF_TYPE_STA) 318 else if (is_interface_type(intf, IEEE80211_IF_TYPE_STA))
366 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 1); 319 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 1);
367 else if (is_monitor_present(&rt2x00dev->interface) && 320 else
368 !is_interface_present(&rt2x00dev->interface))
369 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 0); 321 rt2x00_set_field16(&reg, TXRX_CSR19_TSF_SYNC, 0);
370
371 rt2500usb_register_write(rt2x00dev, TXRX_CSR19, reg); 322 rt2500usb_register_write(rt2x00dev, TXRX_CSR19, reg);
372} 323}
373 324
@@ -1084,7 +1035,7 @@ static int rt2500usb_set_device_state(struct rt2x00_dev *rt2x00dev,
1084 */ 1035 */
1085static void rt2500usb_write_tx_desc(struct rt2x00_dev *rt2x00dev, 1036static void rt2500usb_write_tx_desc(struct rt2x00_dev *rt2x00dev,
1086 struct data_desc *txd, 1037 struct data_desc *txd,
1087 struct data_entry_desc *desc, 1038 struct txdata_entry_desc *desc,
1088 struct ieee80211_hdr *ieee80211hdr, 1039 struct ieee80211_hdr *ieee80211hdr,
1089 unsigned int length, 1040 unsigned int length,
1090 struct ieee80211_tx_control *control) 1041 struct ieee80211_tx_control *control)
@@ -1156,8 +1107,8 @@ static void rt2500usb_kick_tx_queue(struct rt2x00_dev *rt2x00dev,
1156/* 1107/*
1157 * RX control handlers 1108 * RX control handlers
1158 */ 1109 */
1159static int rt2500usb_fill_rxdone(struct data_entry *entry, 1110static void rt2500usb_fill_rxdone(struct data_entry *entry,
1160 int *signal, int *rssi, int *ofdm, int *size) 1111 struct rxdata_entry_desc *desc)
1161{ 1112{
1162 struct urb *urb = entry->priv; 1113 struct urb *urb = entry->priv;
1163 struct data_desc *rxd = (struct data_desc *)(entry->skb->data + 1114 struct data_desc *rxd = (struct data_desc *)(entry->skb->data +
@@ -1169,21 +1120,22 @@ static int rt2500usb_fill_rxdone(struct data_entry *entry,
1169 rt2x00_desc_read(rxd, 0, &word0); 1120 rt2x00_desc_read(rxd, 0, &word0);
1170 rt2x00_desc_read(rxd, 1, &word1); 1121 rt2x00_desc_read(rxd, 1, &word1);
1171 1122
1172 if (rt2x00_get_field32(word0, RXD_W0_CRC_ERROR) || 1123 desc->flags = 0;
1173 rt2x00_get_field32(word0, RXD_W0_PHYSICAL_ERROR) || 1124 if (rt2x00_get_field32(word0, RXD_W0_CRC_ERROR))
1174 rt2x00_get_field32(word0, RXD_W0_CIPHER_ERROR)) 1125 desc->flags |= RX_FLAG_FAILED_FCS_CRC;
1175 return -EINVAL; 1126 if (rt2x00_get_field32(word0, RXD_W0_PHYSICAL_ERROR))
1127 desc->flags |= RX_FLAG_FAILED_PLCP_CRC;
1176 1128
1177 /* 1129 /*
1178 * Obtain the status about this packet. 1130 * Obtain the status about this packet.
1179 */ 1131 */
1180 *signal = rt2x00_get_field32(word1, RXD_W1_SIGNAL); 1132 desc->signal = rt2x00_get_field32(word1, RXD_W1_SIGNAL);
1181 *rssi = rt2x00_get_field32(word1, RXD_W1_RSSI) - 1133 desc->rssi = rt2x00_get_field32(word1, RXD_W1_RSSI) -
1182 entry->ring->rt2x00dev->rssi_offset; 1134 entry->ring->rt2x00dev->rssi_offset;
1183 *ofdm = rt2x00_get_field32(word0, RXD_W0_OFDM); 1135 desc->ofdm = rt2x00_get_field32(word0, RXD_W0_OFDM);
1184 *size = rt2x00_get_field32(word0, RXD_W0_DATABYTE_COUNT); 1136 desc->size = rt2x00_get_field32(word0, RXD_W0_DATABYTE_COUNT);
1185 1137
1186 return 0; 1138 return;
1187} 1139}
1188 1140
1189/* 1141/*
@@ -1549,9 +1501,7 @@ static void rt2500usb_probe_hw_mode(struct rt2x00_dev *rt2x00dev)
1549 rt2x00dev->hw->flags = 1501 rt2x00dev->hw->flags =
1550 IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE | 1502 IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
1551 IEEE80211_HW_RX_INCLUDES_FCS | 1503 IEEE80211_HW_RX_INCLUDES_FCS |
1552 IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING | 1504 IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
1553 IEEE80211_HW_MONITOR_DURING_OPER |
1554 IEEE80211_HW_NO_PROBE_FILTERING;
1555 rt2x00dev->hw->extra_tx_headroom = TXD_DESC_SIZE; 1505 rt2x00dev->hw->extra_tx_headroom = TXD_DESC_SIZE;
1556 rt2x00dev->hw->max_signal = MAX_SIGNAL; 1506 rt2x00dev->hw->max_signal = MAX_SIGNAL;
1557 rt2x00dev->hw->max_rssi = MAX_RX_SSI; 1507 rt2x00dev->hw->max_rssi = MAX_RX_SSI;
@@ -1621,10 +1571,8 @@ static int rt2500usb_probe_hw(struct rt2x00_dev *rt2x00dev)
1621 rt2500usb_probe_hw_mode(rt2x00dev); 1571 rt2500usb_probe_hw_mode(rt2x00dev);
1622 1572
1623 /* 1573 /*
1624 * USB devices require scheduled packet filter toggling 1574 * This device requires the beacon ring
1625 *This device requires the beacon ring
1626 */ 1575 */
1627 __set_bit(PACKET_FILTER_SCHEDULED, &rt2x00dev->flags);
1628 __set_bit(REQUIRE_BEACON_RING, &rt2x00dev->flags); 1576 __set_bit(REQUIRE_BEACON_RING, &rt2x00dev->flags);
1629 1577
1630 /* 1578 /*
@@ -1638,6 +1586,82 @@ static int rt2500usb_probe_hw(struct rt2x00_dev *rt2x00dev)
1638/* 1586/*
1639 * IEEE80211 stack callback functions. 1587 * IEEE80211 stack callback functions.
1640 */ 1588 */
1589static void rt2500usb_configure_filter(struct ieee80211_hw *hw,
1590 unsigned int changed_flags,
1591 unsigned int *total_flags,
1592 int mc_count,
1593 struct dev_addr_list *mc_list)
1594{
1595 struct rt2x00_dev *rt2x00dev = hw->priv;
1596 struct interface *intf = &rt2x00dev->interface;
1597 u16 reg;
1598
1599 /*
1600 * Mask off any flags we are going to ignore from
1601 * the total_flags field.
1602 */
1603 *total_flags &=
1604 FIF_ALLMULTI |
1605 FIF_FCSFAIL |
1606 FIF_PLCPFAIL |
1607 FIF_CONTROL |
1608 FIF_OTHER_BSS |
1609 FIF_PROMISC_IN_BSS;
1610
1611 /*
1612 * Apply some rules to the filters:
1613 * - Some filters imply different filters to be set.
1614 * - Some things we can't filter out at all.
1615 * - Some filters are set based on interface type.
1616 */
1617 if (mc_count)
1618 *total_flags |= FIF_ALLMULTI;
1619 if (changed_flags & FIF_OTHER_BSS ||
1620 changed_flags & FIF_PROMISC_IN_BSS)
1621 *total_flags |= FIF_PROMISC_IN_BSS | FIF_OTHER_BSS;
1622 if (is_interface_type(intf, IEEE80211_IF_TYPE_AP))
1623 *total_flags |= FIF_PROMISC_IN_BSS;
1624
1625 /*
1626 * Check if there is any work left for us.
1627 */
1628 if (intf->filter == *total_flags)
1629 return;
1630 intf->filter = *total_flags;
1631
1632 /*
1633 * When in atomic context, reschedule and let rt2x00lib
1634 * call this function again.
1635 */
1636 if (in_atomic()) {
1637 queue_work(rt2x00dev->hw->workqueue, &rt2x00dev->filter_work);
1638 return;
1639 }
1640
1641 /*
1642 * Start configuration steps.
1643 * Note that the version error will always be dropped
1644 * and broadcast frames will always be accepted since
1645 * there is no filter for it at this time.
1646 */
1647 rt2500usb_register_read(rt2x00dev, TXRX_CSR2, &reg);
1648 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CRC,
1649 !(*total_flags & FIF_FCSFAIL));
1650 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_PHYSICAL,
1651 !(*total_flags & FIF_PLCPFAIL));
1652 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_CONTROL,
1653 !(*total_flags & FIF_CONTROL));
1654 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_NOT_TO_ME,
1655 !(*total_flags & FIF_PROMISC_IN_BSS));
1656 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_TODS,
1657 !(*total_flags & FIF_PROMISC_IN_BSS));
1658 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_VERSION_ERROR, 1);
1659 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_MULTICAST,
1660 !(*total_flags & FIF_ALLMULTI));
1661 rt2x00_set_field16(&reg, TXRX_CSR2_DROP_BROADCAST, 0);
1662 rt2500usb_register_write(rt2x00dev, TXRX_CSR2, reg);
1663}
1664
1641static int rt2500usb_beacon_update(struct ieee80211_hw *hw, 1665static int rt2500usb_beacon_update(struct ieee80211_hw *hw,
1642 struct sk_buff *skb, 1666 struct sk_buff *skb,
1643 struct ieee80211_tx_control *control) 1667 struct ieee80211_tx_control *control)
@@ -1714,11 +1738,13 @@ static int rt2500usb_beacon_update(struct ieee80211_hw *hw,
1714 1738
1715static const struct ieee80211_ops rt2500usb_mac80211_ops = { 1739static const struct ieee80211_ops rt2500usb_mac80211_ops = {
1716 .tx = rt2x00mac_tx, 1740 .tx = rt2x00mac_tx,
1741 .start = rt2x00mac_start,
1742 .stop = rt2x00mac_stop,
1717 .add_interface = rt2x00mac_add_interface, 1743 .add_interface = rt2x00mac_add_interface,
1718 .remove_interface = rt2x00mac_remove_interface, 1744 .remove_interface = rt2x00mac_remove_interface,
1719 .config = rt2x00mac_config, 1745 .config = rt2x00mac_config,
1720 .config_interface = rt2x00mac_config_interface, 1746 .config_interface = rt2x00mac_config_interface,
1721 .set_multicast_list = rt2x00mac_set_multicast_list, 1747 .configure_filter = rt2500usb_configure_filter,
1722 .get_stats = rt2x00mac_get_stats, 1748 .get_stats = rt2x00mac_get_stats,
1723 .conf_tx = rt2x00mac_conf_tx, 1749 .conf_tx = rt2x00mac_conf_tx,
1724 .get_tx_stats = rt2x00mac_get_tx_stats, 1750 .get_tx_stats = rt2x00mac_get_tx_stats,
@@ -1739,7 +1765,6 @@ static const struct rt2x00lib_ops rt2500usb_rt2x00_ops = {
1739 .fill_rxdone = rt2500usb_fill_rxdone, 1765 .fill_rxdone = rt2500usb_fill_rxdone,
1740 .config_mac_addr = rt2500usb_config_mac_addr, 1766 .config_mac_addr = rt2500usb_config_mac_addr,
1741 .config_bssid = rt2500usb_config_bssid, 1767 .config_bssid = rt2500usb_config_bssid,
1742 .config_packet_filter = rt2500usb_config_packet_filter,
1743 .config_type = rt2500usb_config_type, 1768 .config_type = rt2500usb_config_type,
1744 .config = rt2500usb_config, 1769 .config = rt2500usb_config,
1745}; 1770};