aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDaniel Drake <dsd@gentoo.org>2008-07-03 23:30:49 -0400
committerJohn W. Linville <linville@tuxdriver.com>2008-07-08 14:16:03 -0400
commitf2cae6c5e41a979f85463aff60877b31fa3a383d (patch)
tree5cc72cc6a6bd4a424b093589dbcaad2843994dbf
parent6ef307bc561911c8cdda98ef3896b5982b602a43 (diff)
zd1211rw: beacon config error checking
Add some error checking to the new beacon configuration code. Signed-off-by: Daniel Drake <dsd@gentoo.org> Signed-off-by: John W. Linville <linville@tuxdriver.com>
-rw-r--r--drivers/net/wireless/zd1211rw/zd_mac.c62
1 files changed, 45 insertions, 17 deletions
diff --git a/drivers/net/wireless/zd1211rw/zd_mac.c b/drivers/net/wireless/zd1211rw/zd_mac.c
index 317c5e24f80c..665f76af2fec 100644
--- a/drivers/net/wireless/zd1211rw/zd_mac.c
+++ b/drivers/net/wireless/zd1211rw/zd_mac.c
@@ -405,43 +405,66 @@ static void cs_set_control(struct zd_mac *mac, struct zd_ctrlset *cs,
405 /* FIXME: Management frame? */ 405 /* FIXME: Management frame? */
406} 406}
407 407
408void zd_mac_config_beacon(struct ieee80211_hw *hw, struct sk_buff *beacon) 408static int zd_mac_config_beacon(struct ieee80211_hw *hw, struct sk_buff *beacon)
409{ 409{
410 struct zd_mac *mac = zd_hw_mac(hw); 410 struct zd_mac *mac = zd_hw_mac(hw);
411 int r;
411 u32 tmp, j = 0; 412 u32 tmp, j = 0;
412 /* 4 more bytes for tail CRC */ 413 /* 4 more bytes for tail CRC */
413 u32 full_len = beacon->len + 4; 414 u32 full_len = beacon->len + 4;
414 zd_iowrite32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, 0); 415
415 zd_ioread32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, &tmp); 416 r = zd_iowrite32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, 0);
417 if (r < 0)
418 return r;
419 r = zd_ioread32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, &tmp);
420 if (r < 0)
421 return r;
422
416 while (tmp & 0x2) { 423 while (tmp & 0x2) {
417 zd_ioread32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, &tmp); 424 r = zd_ioread32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, &tmp);
425 if (r < 0)
426 return r;
418 if ((++j % 100) == 0) { 427 if ((++j % 100) == 0) {
419 printk(KERN_ERR "CR_BCN_FIFO_SEMAPHORE not ready\n"); 428 printk(KERN_ERR "CR_BCN_FIFO_SEMAPHORE not ready\n");
420 if (j >= 500) { 429 if (j >= 500) {
421 printk(KERN_ERR "Giving up beacon config.\n"); 430 printk(KERN_ERR "Giving up beacon config.\n");
422 return; 431 return -ETIMEDOUT;
423 } 432 }
424 } 433 }
425 msleep(1); 434 msleep(1);
426 } 435 }
427 436
428 zd_iowrite32(&mac->chip, CR_BCN_FIFO, full_len - 1); 437 r = zd_iowrite32(&mac->chip, CR_BCN_FIFO, full_len - 1);
429 if (zd_chip_is_zd1211b(&mac->chip)) 438 if (r < 0)
430 zd_iowrite32(&mac->chip, CR_BCN_LENGTH, full_len - 1); 439 return r;
440 if (zd_chip_is_zd1211b(&mac->chip)) {
441 r = zd_iowrite32(&mac->chip, CR_BCN_LENGTH, full_len - 1);
442 if (r < 0)
443 return r;
444 }
431 445
432 for (j = 0 ; j < beacon->len; j++) 446 for (j = 0 ; j < beacon->len; j++) {
433 zd_iowrite32(&mac->chip, CR_BCN_FIFO, 447 r = zd_iowrite32(&mac->chip, CR_BCN_FIFO,
434 *((u8 *)(beacon->data + j))); 448 *((u8 *)(beacon->data + j)));
449 if (r < 0)
450 return r;
451 }
435 452
436 for (j = 0; j < 4; j++) 453 for (j = 0; j < 4; j++) {
437 zd_iowrite32(&mac->chip, CR_BCN_FIFO, 0x0); 454 r = zd_iowrite32(&mac->chip, CR_BCN_FIFO, 0x0);
455 if (r < 0)
456 return r;
457 }
458
459 r = zd_iowrite32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, 1);
460 if (r < 0)
461 return r;
438 462
439 zd_iowrite32(&mac->chip, CR_BCN_FIFO_SEMAPHORE, 1);
440 /* 802.11b/g 2.4G CCK 1Mb 463 /* 802.11b/g 2.4G CCK 1Mb
441 * 802.11a, not yet implemented, uses different values (see GPL vendor 464 * 802.11a, not yet implemented, uses different values (see GPL vendor
442 * driver) 465 * driver)
443 */ 466 */
444 zd_iowrite32(&mac->chip, CR_BCN_PLCP_CFG, 0x00000400 | 467 return zd_iowrite32(&mac->chip, CR_BCN_PLCP_CFG, 0x00000400 |
445 (full_len << 19)); 468 (full_len << 19));
446} 469}
447 470
@@ -699,15 +722,20 @@ static int zd_op_config_interface(struct ieee80211_hw *hw,
699{ 722{
700 struct zd_mac *mac = zd_hw_mac(hw); 723 struct zd_mac *mac = zd_hw_mac(hw);
701 int associated; 724 int associated;
725 int r;
702 726
703 if (mac->type == IEEE80211_IF_TYPE_MESH_POINT || 727 if (mac->type == IEEE80211_IF_TYPE_MESH_POINT ||
704 mac->type == IEEE80211_IF_TYPE_IBSS) { 728 mac->type == IEEE80211_IF_TYPE_IBSS) {
705 associated = true; 729 associated = true;
706 if (conf->beacon) { 730 if (conf->beacon) {
707 zd_mac_config_beacon(hw, conf->beacon); 731 r = zd_mac_config_beacon(hw, conf->beacon);
708 kfree_skb(conf->beacon); 732 if (r < 0)
709 zd_set_beacon_interval(&mac->chip, BCN_MODE_IBSS | 733 return r;
734 r = zd_set_beacon_interval(&mac->chip, BCN_MODE_IBSS |
710 hw->conf.beacon_int); 735 hw->conf.beacon_int);
736 if (r < 0)
737 return r;
738 kfree_skb(conf->beacon);
711 } 739 }
712 } else 740 } else
713 associated = is_valid_ether_addr(conf->bssid); 741 associated = is_valid_ether_addr(conf->bssid);